// File: /workspace/github_cpp_makefile_star2_O1/mmoanis[P]mpegts_demux/MpegTsDemux.cpp
// Function: MpegTsDemuxer::ReadPAT(unsigned char const*&, unsigned char const*)
bool MpegTsDemuxer::ReadPAT(Packet::const_iterator &p, Packet::const_iterator e)
{
    const uint8_t pointer = *p++;
    p += pointer; // Jump to table at pointer offset

    bool done = false; // Must get at least 1 Program

    // Tables can be repeated.
    while (p < e) {
        const uint8_t id = *p++;
        if (id == MPEGTS_STUFFING_BYTE) {
            if (!done) {
                cerr << "[ERROR]: PKT#" << m_pnum << " Empty PAT packet." << endl;
                return false;
            }
            // we are done, happy return
            return true;
        }
        else if (id == MPEGTS_TABLE_NIL) {
            if (!done) {
                cerr << "[ERROR]: PKT#" << m_pnum << " PAT packet has no associated PSI." << endl;
                return false;
            }
            return true;
        } else if (id != MPEGTS_TABLE_PAS) {
            cerr << "[ERROR]: PKT#" << m_pnum <<" Expected PAT SECTION=" << MPEGTS_TABLE_PAS << " found " << id << endl;
            return false;
        }

        const bool ssi = static_cast<bool> (*p&0x80); // PAT/PMT/CAT == 1
        if (!ssi) {
            cerr << "[ERROR]: PKT#" << m_pnum <<" PAT section syntax indicator not set." << endl;
            return false;
        }

        const bool pb = static_cast<bool> (*p&0x40); // PAT/PMT/CAT == 0
        if (pb) {
            cerr << "[ERROR]: PKT#" << m_pnum << " PAT private bit is set." << endl;
            return false;
        }

        if (((*p&0x30)>>4) != 0x03 ) {
            cerr << "[ERROR]: PKT#" << m_pnum <<" PAT PSI reserved bits not set." << endl;
            return false;
        }

        if (p + 1 >= e) {
            cerr << "[ERROR]: PKT#" << m_pnum << " PAT PSI not enough data." << endl;
            return false;
        }
        const uint16_t slength = uint16_t((p[0]&0x03)<<8) | uint16_t(p[1]);
        p += 2;
        if (p + slength >= e) {
            cerr << "[ERROR]: PKT#" << m_pnum <<" PAT bad section length." << endl;
            return false;
        }

        PacketSection section;
        if (!ReadSection(p, e, section))
            return false;

        // Read PAT, can be repeated
        if (!ReadPrograms(p, e))
            return false;

        // End of the section
        //uint32_t crc = uint32_t(p[0]<<24) | uint32_t(p[1]<<16) | uint32_t(p[2]<<8) | uint32_t(p[3]);
        //cout << "CRC: " << hex << crc << dec << endl;
        p += 4;
        done = true;
    }

    return done;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x18, %rsp
movq %rdx, %rbx
movq %rsi, %r14
movq %rdi, %r15
movq (%rsi), %rax
leaq 0x1(%rax), %rcx
movq %rcx, (%rsi)
movzbl (%rax), %ecx
addq %rcx, %rax
incq %rax
movq %rax, (%rsi)
movl $0x0, 0xc(%rsp)
movq (%r14), %rax
cmpq %rbx, %rax
jae 0x31d2
leaq 0x1(%rax), %rcx
movq %rcx, (%r14)
movzbl (%rax), %r12d
testl %r12d, %r12d
je 0x2eda
cmpl $0xff, %r12d
jne 0x2f26
testb $0x1, 0xc(%rsp)
je 0x2fd1
movb $0x1, %bpl
xorl %r13d, %r13d
jmp 0x31c7
movzbl (%rcx), %ecx
testb %cl, %cl
js 0x3012
movl $0xd, %edx
movq 0x50ff(%rip), %r12      # 0x7ff0
movq %r12, %rdi
leaq 0x237b(%rip), %rsi      # 0x5276
callq 0x2170
movq 0x90(%r15), %rsi
movq %r12, %rdi
callq 0x20c0
movq %rax, %rbp
movl $0x26, %edx
movq %rax, %rdi
leaq 0x238d(%rip), %rsi      # 0x52ae
jmp 0x3195
movl $0xd, %edx
movq 0x50be(%rip), %r13      # 0x7ff0
movq %r13, %rdi
leaq 0x233a(%rip), %rsi      # 0x5276
callq 0x2170
movq 0x90(%r15), %rsi
movq %r13, %rdi
callq 0x20c0
movq %rax, %rbp
movl $0x16, %edx
movq %rax, %rdi
leaq 0x2335(%rip), %rsi      # 0x5297
callq 0x2170
xorl %r13d, %r13d
movq %rbp, %rdi
xorl %esi, %esi
callq 0x21f0
movq %rax, %rbp
movl $0x7, %edx
movq %rax, %rdi
leaq 0x223d(%rip), %rsi      # 0x51c3
callq 0x2170
movb %r12b, 0xb(%rsp)
movl $0x1, %edx
movq %rbp, %rdi
leaq 0xb(%rsp), %rsi
callq 0x2170
movq %rax, %rbp
movq (%rax), %rax
movq -0x18(%rax), %rdi
addq %rbp, %rdi
movl $0xa, %esi
callq 0x2130
movsbl %al, %esi
movq %rbp, %rdi
callq 0x2030
movq %rax, %rdi
callq 0x20d0
jmp 0x31c5
movl $0xd, %edx
movq 0x5013(%rip), %r12      # 0x7ff0
movq %r12, %rdi
leaq 0x228f(%rip), %rsi      # 0x5276
callq 0x2170
movq 0x90(%r15), %rsi
movq %r12, %rdi
callq 0x20c0
movq %rax, %rbp
movl $0x12, %edx
movq %rax, %rdi
leaq 0x2277(%rip), %rsi      # 0x5284
jmp 0x3195
testb $0x40, %cl
jne 0x309c
movl %ecx, %edx
notl %edx
testb $0x30, %dl
jne 0x30dd
leaq 0x2(%rax), %rdx
cmpq %rbx, %rdx
jae 0x311b
andl $0x3, %ecx
shll $0x8, %ecx
movzbl 0x2(%rax), %edx
orq %rcx, %rdx
leaq 0x3(%rax), %rcx
movq %rcx, (%r14)
addq %rdx, %rax
addq $0x3, %rax
cmpq %rbx, %rax
jae 0x3159
movq %r15, %rdi
movq %r14, %rsi
movq %rbx, %rdx
leaq 0x12(%rsp), %rcx
callq 0x3b1e
testb %al, %al
je 0x31c2
movq %r15, %rdi
movq %r14, %rsi
movq %rbx, %rdx
callq 0x3c2c
testb %al, %al
je 0x31c2
addq $0x4, (%r14)
movb $0x1, %r13b
movb $0x1, %al
movl %eax, 0xc(%rsp)
jmp 0x31c7
movl $0xd, %edx
movq 0x4f48(%rip), %r12      # 0x7ff0
movq %r12, %rdi
leaq 0x21c4(%rip), %rsi      # 0x5276
callq 0x2170
movq 0x90(%r15), %rsi
movq %r12, %rdi
callq 0x20c0
movq %rax, %rbp
movl $0x18, %edx
movq %rax, %rdi
leaq 0x21fd(%rip), %rsi      # 0x52d5
jmp 0x3195
movl $0xd, %edx
movq 0x4f07(%rip), %r12      # 0x7ff0
movq %r12, %rdi
leaq 0x2183(%rip), %rsi      # 0x5276
callq 0x2170
movq 0x90(%r15), %rsi
movq %r12, %rdi
callq 0x20c0
movq %rax, %rbp
movl $0x1f, %edx
movq %rax, %rdi
leaq 0x21d5(%rip), %rsi      # 0x52ee
jmp 0x3195
movl $0xd, %edx
movq 0x4ec9(%rip), %r12      # 0x7ff0
movq %r12, %rdi
leaq 0x2145(%rip), %rsi      # 0x5276
callq 0x2170
movq 0x90(%r15), %rsi
movq %r12, %rdi
callq 0x20c0
movq %rax, %rbp
movl $0x19, %edx
movq %rax, %rdi
leaq 0x21b7(%rip), %rsi      # 0x530e
jmp 0x3195
movl $0xd, %edx
movq 0x4e8b(%rip), %r12      # 0x7ff0
movq %r12, %rdi
leaq 0x2107(%rip), %rsi      # 0x5276
callq 0x2170
movq 0x90(%r15), %rsi
movq %r12, %rdi
callq 0x20c0
movq %rax, %rbp
movl $0x18, %edx
movq %rax, %rdi
leaq 0x2193(%rip), %rsi      # 0x5328
callq 0x2170
movq (%rbp), %rax
movq -0x18(%rax), %rdi
addq %rbp, %rdi
movl $0xa, %esi
callq 0x2130
movsbl %al, %esi
movq %rbp, %rdi
callq 0x2030
movq %rax, %rdi
callq 0x20d0
xorl %r13d, %r13d
xorl %ebp, %ebp
testb %r13b, %r13b
jne 0x2e9f
jmp 0x31d6
movl 0xc(%rsp), %ebp
andb $0x1, %bpl
movl %ebp, %eax
addq $0x18, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
nop