// File: /workspace/github_cpp_makefile_star2_O2/canzarlab[P]Trajan/src/match.cpp
// Function: tree::tree(char const*, char const*)
tree(const char* filename, const char* mapname) : n(0), nb(0), r(-1)
    {
        ifstream file(filename), mapfile(mapname);
        if (!file || !mapfile)
            die();

        // map string indices to integers
        int node_idx; string node_name;
        while (mapfile >> node_idx >> node_name)
            m[node_name] = node_idx;
        n = m.size();

        // create reverse mapping
        rm.resize(n);
        for (auto [name, idx] : m)
            rm[idx] = name;

        // nroot[x] == 1 means x is not the root
        vector<int> nroot(MAXN);

        // read from file
        string sa, sb, type;
        while (file >> sa >> sb >> type)
        {
            if (type != "default")
                die();

            // directed edge sb->sa
            int x = m[sa], y = m[sb];
            adj[y].push_back(x);
            nroot[x] = 1;
        }

        // tree too big
        if (m.size() > MAXN)
            die();

        // find root
        for (uint i = 0; i < m.size(); ++i)
        {
            // found the root
            if (!nroot[i])
            {
                // multiple roots
                if (r != -1)
                    die();

                r = i;
            }
        }

        // tree has no root
        if (r == -1)
            die();

        // identify branching nodes
        function<void(int)> mark = [&] (int x)
        {
            for (int y : adj[x])
            {
                // fill the parent table
                par[y] = x;
                mark(y);
            }
            // x is a leaf/branching node - record finishing time
            if (adj[x].size() != 1)
                b[nb++] = x;
        };
        // root has no parent
        par[r] = -1;
        mark(r);

        // too many leaf/branching nodes
        if (nb > MAXLB)
            die();

        // obtain topological ordering
        reverse(b, b + nb);

        // create node->leaf/branching node index mapping
        memset(rb, -1, sizeof rb);
        for (int i = 0; i < nb; ++i)
            rb[b[i]] = i;

        // fill the table of immediate leaf/branching descendant masks
        function<mask(int)> child = [&] (int x)
        {
            mask msk = 0;
            for (int y : adj[x])
                msk |= child(y);

            // x is a leaf/branching node
            if (rb[x] != -1)
            {
                // record leaf/branching children mask
                ch[rb[x]] = msk;
                return in(rb[x]);
            }
            return msk;
        };
        child(r);

        // identify branching ancestors
        function<void(int, mask, int)> branch = [&] (int x, mask m, int p)
        {
            // x is a branching or leaf node
            if (rb[x] != -1)
            {
                // set branching ancestor mask
                ba[rb[x]] = m;
                m |= in(rb[x]);
                // set branching parent
                bp[rb[x]] = p;
                p = x;
            }
            for (int y : adj[x])
                branch(y, m, p);
        };
        branch(r, 0, -1);
    }

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x538, %rsp            # imm = 0x538
movq %rdx, %r14
movq %rsi, %r15
movq %rdi, %rbx
andl $0x0, 0x8(%rdi)
leaq 0x8(%rdi), %r13
andq $0x0, 0x10(%rdi)
movq %r13, 0x18(%rdi)
movq %r13, 0x20(%rdi)
addq $0x28, %rdi
leaq 0x30(%rbx), %r12
movl $0x5de8, %edx           # imm = 0x5DE8
movq %rdi, 0x38(%rsp)
xorl %esi, %esi
callq 0x3160
orl $-0x1, 0x5e10(%rbx)
leaq 0x330(%rsp), %rdi
pushq $0x8
popq %rdx
movq %r15, %rsi
callq 0x3400
leaq 0x128(%rsp), %rdi
pushq $0x8
popq %rdx
movq %r14, %rsi
callq 0x3400
movq %r12, 0x8(%rsp)
movq 0x330(%rsp), %rax
movq -0x18(%rax), %rax
testb $0x5, 0x350(%rsp,%rax)
jne 0x589b
movq 0x128(%rsp), %rax
movq -0x18(%rax), %rax
testb $0x5, 0x148(%rsp,%rax)
jne 0x589b
leaq 0x48(%rbx), %rax
movq %rax, 0x40(%rsp)
leaq 0xd8(%rsp), %rax
movq %rax, -0x10(%rax)
andq $0x0, -0x8(%rax)
movb $0x0, (%rax)
leaq 0x128(%rsp), %r14
leaq 0x14(%rsp), %r15
leaq 0xc8(%rsp), %r12
movq %r14, %rdi
movq %r15, %rsi
callq 0x3180
movq %rax, %rdi
movq %r12, %rsi
callq 0x3290
movq (%rax), %rcx
movq -0x18(%rcx), %rcx
testb $0x5, 0x20(%rax,%rcx)
jne 0x552b
movl 0x14(%rsp), %ebp
movq %rbx, %rdi
movq %r12, %rsi
callq 0x5de2
movl %ebp, (%rax)
jmp 0x54f4
movq 0x28(%rbx), %rax
movl %eax, 0x5e08(%rbx)
movslq %eax, %rsi
movq 0x8(%rsp), %r12
movq %r12, %rdi
callq 0x5e48
movq 0x18(%rbx), %r15
leaq 0x60(%rsp), %r14
cmpq %r13, %r15
je 0x558c
leaq 0x20(%r15), %rsi
movq %r14, %rdi
callq 0x5e78
movslq 0x80(%rsp), %rdi
shlq $0x5, %rdi
addq (%r12), %rdi
movq %r14, %rsi
callq 0x3150
movq %r14, %rdi
callq 0x3100
movq %r15, %rdi
callq 0x31a0
movq %rax, %r15
jmp 0x554e
leaq 0x48(%rsp), %rdi
leaq 0x60(%rsp), %rdx
movl $0x3e8, %esi            # imm = 0x3E8
callq 0x5e96
leaq 0x70(%rsp), %rax
movq %rax, -0x10(%rax)
andq $0x0, -0x8(%rax)
xorl %ecx, %ecx
movb %cl, (%rax)
leaq 0xb8(%rsp), %rax
movq %rax, -0x10(%rax)
andq $0x0, -0x8(%rax)
leaq 0x98(%rsp), %rdx
movq %rdx, -0x10(%rdx)
andq $0x0, -0x8(%rdx)
movb %cl, (%rax)
movb %cl, (%rdx)
leaq 0x330(%rsp), %r13
leaq 0x60(%rsp), %rbp
leaq 0xa8(%rsp), %r15
leaq 0x88(%rsp), %r14
leaq 0x4aec(%rip), %r12      # 0xa0e8
movq %r13, %rdi
movq %rbp, %rsi
callq 0x3290
movq %rax, %rdi
movq %r15, %rsi
callq 0x3290
movq %rax, %rdi
movq %r14, %rsi
callq 0x3290
movq (%rax), %rcx
movq -0x18(%rcx), %rcx
testb $0x5, 0x20(%rax,%rcx)
jne 0x5686
movq %r14, %rdi
movq %r12, %rsi
callq 0x5ee7
testb %al, %al
jne 0x585d
movq %rbx, %rdi
movq %rbp, %rsi
callq 0x5de2
movl (%rax), %eax
movl %eax, 0x18(%rsp)
movq %rbx, %rdi
movq %r15, %rsi
callq 0x5de2
movslq (%rax), %rax
imulq $0x18, %rax, %rdi
addq 0x40(%rsp), %rdi
leaq 0x18(%rsp), %rsi
callq 0x52ea
movslq 0x18(%rsp), %rax
movq 0x48(%rsp), %rcx
movl $0x1, (%rcx,%rax,4)
jmp 0x55fc
movq 0x38(%rsp), %rax
movq (%rax), %rcx
cmpq $0x3e8, %rcx            # imm = 0x3E8
ja 0x58b8
movl 0x5e10(%rbx), %eax
movq 0x48(%rsp), %rdx
xorl %esi, %esi
cmpl %ecx, %esi
jae 0x56c8
cmpl $0x0, (%rdx,%rsi,4)
jne 0x56c3
cmpl $-0x1, %eax
jne 0x587c
movl %esi, 0x5e10(%rbx)
movl %esi, %eax
incq %rsi
jmp 0x56a8
cmpl $-0x1, %eax
je 0x58d7
movq %rbx, 0x18(%rsp)
leaq 0x18(%rsp), %rdi
movq %rdi, 0x20(%rsp)
leaq 0xfe9(%rip), %rcx       # 0x66d0
movq %rcx, 0x30(%rsp)
leaq 0xfe3(%rip), %rcx       # 0x66d6
movq %rcx, 0x28(%rsp)
cltq
orl $-0x1, 0x5f14(%rbx,%rax,4)
movl 0x5e10(%rbx), %esi
callq 0x5ef2
movslq 0x5e0c(%rbx), %rax
cmpq $0x41, %rax
jge 0x58f6
leaq 0x5e14(%rbx), %rdi
leaq (%rbx,%rax,4), %rsi
addq $0x5e14, %rsi           # imm = 0x5E14
callq 0x67ae
leaq 0x70b8(%rbx), %rdi
movl $0xfa0, %edx            # imm = 0xFA0
movl $0xff, %esi
callq 0x3160
xorl %eax, %eax
movslq 0x5e0c(%rbx), %rcx
cmpq %rcx, %rax
jge 0x576d
movslq 0x5e14(%rbx,%rax,4), %rcx
movl %eax, 0x70b8(%rbx,%rcx,4)
incq %rax
jmp 0x574d
leaq 0x108(%rsp), %rdi
movq %rbx, (%rdi)
movq %rdi, 0x8(%rdi)
leaq 0x1049(%rip), %rax      # 0x67cc
movq %rax, 0x18(%rdi)
leaq 0x1044(%rip), %rax      # 0x67d2
movq %rax, 0x10(%rdi)
movl 0x5e10(%rbx), %esi
callq 0x5f0e
leaq 0xe8(%rsp), %rdi
movq %rbx, (%rdi)
movq %rdi, 0x8(%rdi)
leaq 0x10e3(%rip), %rax      # 0x6896
movq %rax, 0x18(%rdi)
leaq 0x10de(%rip), %rax      # 0x689c
movq %rax, 0x10(%rdi)
movl 0x5e10(%rbx), %esi
pushq $-0x1
popq %rcx
xorl %edx, %edx
callq 0x5f2a
leaq 0xe8(%rsp), %rdi
callq 0x5f5e
leaq 0x108(%rsp), %rdi
callq 0x5f5e
leaq 0x18(%rsp), %rdi
callq 0x5f5e
leaq 0x88(%rsp), %rdi
callq 0x3100
leaq 0xa8(%rsp), %rdi
callq 0x3100
leaq 0x60(%rsp), %rdi
callq 0x3100
leaq 0x48(%rsp), %rdi
callq 0x65ec
leaq 0xc8(%rsp), %rdi
callq 0x3100
leaq 0x128(%rsp), %rdi
callq 0x3090
leaq 0x330(%rsp), %rdi
callq 0x3090
addq $0x538, %rsp            # imm = 0x538
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
leaq 0x4857(%rip), %rdi      # 0xa0bb
leaq 0x4819(%rip), %rsi      # 0xa084
leaq 0x484f(%rip), %rcx      # 0xa0c1
movl $0x93, %edx
callq 0x3190
leaq 0x4838(%rip), %rdi      # 0xa0bb
leaq 0x47fa(%rip), %rsi      # 0xa084
leaq 0x4830(%rip), %rcx      # 0xa0c1
movl $0xa7, %edx
callq 0x3190
leaq 0x4819(%rip), %rdi      # 0xa0bb
leaq 0x47db(%rip), %rsi      # 0xa084
leaq 0x4811(%rip), %rcx      # 0xa0c1
pushq $0x7e
popq %rdx
callq 0x3190
leaq 0x47fc(%rip), %rdi      # 0xa0bb
leaq 0x47be(%rip), %rsi      # 0xa084
leaq 0x47f4(%rip), %rcx      # 0xa0c1
movl $0x9d, %edx
callq 0x3190
leaq 0x47dd(%rip), %rdi      # 0xa0bb
leaq 0x479f(%rip), %rsi      # 0xa084
leaq 0x47d5(%rip), %rcx      # 0xa0c1
movl $0xaf, %edx
callq 0x3190
leaq 0x47be(%rip), %rdi      # 0xa0bb
leaq 0x4780(%rip), %rsi      # 0xa084
leaq 0x47b6(%rip), %rcx      # 0xa0c1
movl $0xc4, %edx
callq 0x3190
movq %rax, %r15
leaq 0xe8(%rsp), %rdi
callq 0x5f5e
jmp 0x592a
movq %rax, %r15
leaq 0x108(%rsp), %rdi
callq 0x5f5e
jmp 0x5950
jmp 0x5974
jmp 0x595e
movq %rax, %r15
jmp 0x59ce
movq %rax, %r15
jmp 0x59db
movq %rax, %r15
leaq 0x18(%rsp), %rdi
callq 0x5f5e
jmp 0x5981
jmp 0x597e
movq %rax, %r15
jmp 0x59b4
movq %rax, %r15
leaq 0x60(%rsp), %rdi
callq 0x3100
jmp 0x59b4
jmp 0x597e
movq %rax, %r15
movq 0x8(%rsp), %r12
jmp 0x59b4
movq %rax, %r15
movq 0x8(%rsp), %r12
leaq 0x88(%rsp), %rdi
callq 0x3100
leaq 0xa8(%rsp), %rdi
callq 0x3100
leaq 0x60(%rsp), %rdi
callq 0x3100
leaq 0x48(%rsp), %rdi
callq 0x65ec
leaq 0xc8(%rsp), %rdi
callq 0x3100
leaq 0x128(%rsp), %rdi
callq 0x3090
leaq 0x330(%rsp), %rdi
callq 0x3090
movl $0x5df0, %r14d          # imm = 0x5DF0
leaq (%rbx,%r14), %rdi
callq 0x65ec
addq $-0x18, %r14
cmpq $0x30, %r14
jne 0x59e1
movq %r12, %rdi
callq 0x5f7a
movq %rbx, %rdi
callq 0x6984
movq %r15, %rdi
callq 0x33e0