// File: /workspace/github_cpp_makefile_star2_O1/iPapatsoris[P]Maximum-Independent-Set/src/Alg.cpp
// Function: Alg::run()
void Alg::run() {
    uint32_t searchNodes = 1;
    uint32_t minCompletedSearchNode = NONE;
    bool down = true;
    uint32_t i = 0;
    while(true) {
        if (down) {
            if (searchTree[i]->theta == 5 && !searchTree[i]->hasCut && searchTree[i]->handleCuts()) {
                ;
            } else {
                searchTree[i]->reductions->run(searchTree[i]->theta);
                //cout << "search node " << searchNodes ;
                searchTree[i]->branchingRule.choose(searchTree[i]->graph, *(searchTree[i]->reductions), searchTree[i]->theta, searchTree[i]);
            }
        } else if (searchTree[i]->rightChild == NONE) {
            down = true;
            assert(searchTree[i]->branchingRule.type != BranchingRule::Type::DONE);
        }
        if (down && searchTree[i]->branchingRule.type == BranchingRule::Type::DONE) {
            searchTree[i]->id = searchNodeID++;
            searchTree[i]->finalMis = new vector<uint32_t>();
            searchTree[i]->mis.unfoldHypernodes(searchTree[i]->graph.zeroDegreeNodes, *searchTree[i]->finalMis);
            i = searchTree[i]->parent;
            if (i == NONE) {
                break;
            }
            down = false;
            continue;
        }
        uint32_t *nextChild;
        if (searchTree[i]->leftChild == NONE) {
            nextChild = &searchTree[i]->leftChild;
        } else if (searchTree[i]->rightChild == NONE) {
            nextChild = &searchTree[i]->rightChild;
        } else if (searchTree[i]->hasCut && !searchTree[i]->cutIsDone) {
            chooseCutBranch(searchTree[i]);
            nextChild = &searchTree[i]->rightChild;
            down = true;
        } else {
            if (i < minCompletedSearchNode) {
                minCompletedSearchNode = i;
                cout << i << endl;
            }
            SearchNode *parent = searchTree[i];
            if (parent->hasCut) {
                assert(parent->cutIsDone);
                concatMis(parent);
                //cout << "concating mis" << endl;
            } else {
                chooseMaxMis(parent);
            }
            i = parent->parent;
            if (searchTree.size() == 1) {
                break;
            }
            continue;
        }
        SearchNode *searchNode = new SearchNode(*searchTree[i], i);
        searchNodes++;
        searchTree.push_back(searchNode);
        *nextChild = searchTree.size() - 1;
        if (nextChild == &searchTree[i]->leftChild) {
            branchLeft(searchTree[i]->branchingRule, searchNode, searchTree[i]->mis);
        }
        else if (nextChild == &searchTree[i]->rightChild) {
            branchRight(searchTree[i]->branchingRule, searchNode, searchTree[i]->mis);
        }
        else {
            assert(false);
        }
        i = *nextChild;
    }
    cout << searchNodes << " search nodes\n";
    searchTree[0]->graph.collectZeroDegreeNodes();
    //cout << "Final id " << searchTree[0]->id;
    Mis::print(*searchTree[0]->finalMis);
    delete searchTree[0]->finalMis;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x18, %rsp
movq %rdi, %rbx
leaq 0x4(%rsp), %rax
movl $0x0, (%rax)
movl $0x1, 0xc(%rsp)
movl $0xffffffff, 0x8(%rsp)  # imm = 0xFFFFFFFF
movb $0x1, %r14b
xorl %r15d, %r15d
movl %r15d, %r13d
movq (%rbx), %rax
movq (%rax,%r13,8), %rdi
testb $0x1, %r14b
je 0x142f4
cmpl $0x5, 0x4(%rdi)
jne 0x142bc
cmpb $0x0, 0x128(%rdi)
jne 0x142bc
callq 0x1464a
testb %al, %al
jne 0x1430a
movq (%rbx), %rax
movq (%rax,%r13,8), %rsi
movq 0x108(%rsi), %rdi
addq $0x4, %rsi
callq 0xfcd0
movq (%rbx), %rax
movq (%rax,%r13,8), %r8
leaq 0x8(%r8), %rdi
leaq 0x30(%r8), %rsi
movq 0x108(%r8), %rdx
leaq 0x4(%r8), %rcx
callq 0x14cd0
jmp 0x1430a
cmpl $-0x1, 0x118(%rdi)
jne 0x1430a
movb $0x1, %r14b
cmpl $0xb, 0x8(%rdi)
je 0x145d4
testb $0x1, %r14b
je 0x1438c
movq (%rbx), %r12
movq (%r12,%r13,8), %rax
cmpl $0xb, 0x8(%rax)
jne 0x1438c
movl 0xeead(%rip), %ecx      # 0x231d0
leal 0x1(%rcx), %edx
movl %edx, 0xeea4(%rip)      # 0x231d0
movl %ecx, (%rax)
movl $0x18, %edi
callq 0x21e0
xorps %xmm0, %xmm0
movups %xmm0, (%rax)
movq $0x0, 0x10(%rax)
movq (%r12,%r13,8), %rcx
movq %rax, 0x120(%rcx)
movq (%r12,%r13,8), %rsi
leaq 0x80(%rsi), %rdi
movq 0x120(%rsi), %rdx
addq $0x50, %rsi
callq 0x1787a
movq (%rbx), %rax
movq (%rax,%r13,8), %rax
movl 0x110(%rax), %r15d
xorl %r14d, %r14d
cmpl $-0x1, %r15d
jne 0x14294
jmp 0x14554
movl %r15d, 0x4(%rsp)
movq (%rbx), %rax
movq (%rax,%r13,8), %rbp
cmpl $-0x1, 0x114(%rbp)
je 0x1443b
cmpl $-0x1, 0x118(%rbp)
je 0x14444
cmpb $0x1, 0x128(%rbp)
jne 0x143c8
cmpb $0x0, 0x199(%rbp)
je 0x14478
cmpl 0x8(%rsp), %r15d
jae 0x1440d
movq 0xebfa(%rip), %rdi      # 0x22fd0
movq %r13, %rsi
callq 0x2120
movq %rax, %r12
movq (%rax), %rax
movq -0x18(%rax), %rdi
addq %r12, %rdi
movl $0xa, %esi
callq 0x21b0
movsbl %al, %esi
movq %r12, %rdi
callq 0x2030
movq %rax, %rdi
callq 0x2130
movl %r15d, 0x8(%rsp)
movq (%rbx), %rax
movq (%rax,%r13,8), %r12
cmpb $0x1, 0x128(%r12)
jne 0x1444d
cmpb $0x0, 0x199(%r12)
je 0x14617
movq %rbx, %rdi
movq %r12, %rsi
callq 0x1515c
jmp 0x14458
addq $0x114, %rbp            # imm = 0x114
jmp 0x14495
addq $0x118, %rbp            # imm = 0x118
jmp 0x14495
movq %rbx, %rdi
movq %r12, %rsi
callq 0x152d8
movl 0x110(%r12), %r15d
movl %r15d, 0x4(%rsp)
movq 0x8(%rbx), %rax
subq (%rbx), %rax
cmpq $0x8, %rax
sete %al
jmp 0x1454a
movq %rbx, %rdi
movq %rbp, %rsi
callq 0x1508c
movq (%rbx), %rax
movq (%rax,%r13,8), %rbp
movl $0x118, %eax            # imm = 0x118
addq %rax, %rbp
movb $0x1, %r14b
movl $0x1a0, %edi            # imm = 0x1A0
callq 0x21e0
movq %rax, %r12
movq (%rbx), %rax
movq (%rax,%r13,8), %rsi
movq %r12, %rdi
leaq 0x4(%rsp), %rdx
callq 0x13f06
movq %r12, 0x10(%rsp)
movq 0x8(%rbx), %rsi
cmpq 0x10(%rbx), %rsi
je 0x144cf
movq %r12, (%rsi)
addq $0x8, 0x8(%rbx)
jmp 0x144dc
movq %rbx, %rdi
leaq 0x10(%rsp), %rdx
callq 0x174fc
movq (%rbx), %rax
movq 0x8(%rbx), %rcx
subq %rax, %rcx
shrq $0x3, %rcx
decl %ecx
movl %ecx, (%rbp)
movq (%rax,%r13,8), %rcx
leaq 0x114(%rcx), %rax
cmpq %rax, %rbp
je 0x14526
leaq 0x118(%rcx), %rax
cmpq %rax, %rbp
jne 0x145f8
leaq 0x8(%rcx), %rsi
movq 0x10(%rsp), %rdx
subq $-0x80, %rcx
movq %rbx, %rdi
callq 0x15802
jmp 0x1453b
leaq 0x8(%rcx), %rsi
movq 0x10(%rsp), %rdx
subq $-0x80, %rcx
movq %rbx, %rdi
callq 0x153e2
incl 0xc(%rsp)
movl (%rbp), %r15d
movl %r15d, 0x4(%rsp)
xorl %eax, %eax
testb %al, %al
je 0x14294
jmp 0x14559
movl %r15d, 0x4(%rsp)
movl 0xc(%rsp), %esi
movq 0xea6c(%rip), %rdi      # 0x22fd0
callq 0x2120
leaq 0x651a(%rip), %rsi      # 0x1aa8a
movl $0xe, %edx
movq %rax, %rdi
callq 0x2200
movq (%rbx), %rax
movq (%rax), %rdi
addq $0x30, %rdi
callq 0x6fca
movq (%rbx), %rax
movq (%rax), %rax
movq 0x120(%rax), %rdi
callq 0x17ad4
movq (%rbx), %rax
movq (%rax), %rax
movq 0x120(%rax), %rbx
testq %rbx, %rbx
je 0x145c5
movq (%rbx), %rdi
testq %rdi, %rdi
je 0x145bd
callq 0x21a0
movq %rbx, %rdi
callq 0x21a0
addq $0x18, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
movl %r15d, 0x4(%rsp)
leaq 0x643d(%rip), %rdi      # 0x1aa1d
leaq 0x6475(%rip), %rsi      # 0x1aa5c
leaq 0x647a(%rip), %rcx      # 0x1aa68
movl $0x3b, %edx
callq 0x2110
leaq 0x62cc(%rip), %rdi      # 0x1a8cb
leaq 0x6456(%rip), %rsi      # 0x1aa5c
leaq 0x645b(%rip), %rcx      # 0x1aa68
movl $0x6f, %edx
callq 0x2110
leaq 0x645a(%rip), %rdi      # 0x1aa78
leaq 0x6437(%rip), %rsi      # 0x1aa5c
leaq 0x643c(%rip), %rcx      # 0x1aa68
movl $0x58, %edx
callq 0x2110
movq %rax, %rbx
movq %r12, %rdi
callq 0x21a0
movq %rbx, %rdi
callq 0x2320
nop