// File: /workspace/github_cpp_makefile_star2_O2/jswaff[P]prophet3/src/think.cpp
// Function: think_helper(void*)
void* think_helper(void *ptr) {

    move_line pv = iterate(&search_pos,false);

    // sanity check - the global position shouldn't have changed
    assert(equal_pos(&search_pos,&gpos,true));
    assert(undo_stacks_equal(search_undos,gundos,gpos.move_counter));

    apply_move(&gpos,pv.mv[0],gundos);
    print_move(pv.mv[0]);
    game_status gs = get_game_status();


    // pondering loop.  as long as we guess correctly we'll loop back around.
    // if we don't predict correctly this thread is terminated.
    bool ponder_failure = false;
    char move_buffer[8];
    while (gs==INPROGRESS && pondering_enabled && pv.n > 1 && !ponder_failure && !abort_iterator) {

        pthread_mutex_lock(&ponder_mutex);
        printd("# think_helper acquired lock #1 on ponder_mutex\n");

        if (!abort_iterator) {
            ponder_move = pv.mv[1];
            move_to_str(ponder_move,move_buffer);
            apply_move(&search_pos,pv.mv[0],search_undos); // apply the move just made so we're in sync
            apply_move(&search_pos,ponder_move,search_undos); // apply the predicted move

            printd("### START PONDERING: %s\n",move_buffer);

            set_ponder_mode(true);
            set_abort_search(false);

            pthread_mutex_unlock(&ponder_mutex);
            printd("# think_helper released lock #1 on ponder_mutex\n");

            pv = iterate(&search_pos,false);
            printd("# ponder search terminated\n");

            pthread_mutex_lock(&ponder_mutex);
            printd("# think_helper acquired lock #2 on ponder_mutex\n");

            ponder_move = 0;

            // if we're not in ponder mode, it's because the usermove was correctly predicted and the main
            // thread transitioned the search into "normal mode."
            if (!pondering) {
                assert(equal_pos(&search_pos,&gpos,true));
                assert(undo_stacks_equal(search_undos,gundos,gpos.move_counter));
                apply_move(&gpos,pv.mv[0],gundos);
                print_move(pv.mv[0]);
                gs = get_game_status();
            } else {
                // we're still in ponder mode.  this means the search terminated on its own.
                // in this case just bail out.
                ponder_failure = true;
            }

            set_ponder_mode(false);
        }

        pthread_mutex_unlock(&ponder_mutex);
        printd("# think_helper released lock #2 on ponder_mutex\n");

    }

    // If game is over by rule then print the result
    printd("# exiting search thread\n");

    if (gs != INPROGRESS) {
        print_result(gs);
    }

    return 0;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x658, %rsp            # imm = 0x658
leaq 0x872f93(%rip), %rbx    # 0x87f978
leaq 0x8(%rsp), %rdi
movq %rbx, %rsi
xorl %edx, %edx
callq 0xcd14
leaq 0xbef25(%rip), %r14     # 0xcb920
pushq $0x1
popq %rdx
movq %rbx, %rdi
movq %r14, %rsi
callq 0x98c8
testb %al, %al
je 0xccde
movl 0x144(%r14), %edx
leaq 0x87cd91(%rip), %rdi    # 0x8897b0
leaq 0xbf0ca(%rip), %rsi     # 0xcbaf0
callq 0xdcec
testb %al, %al
je 0xccf7
leaq 0x8(%rsp), %rbx
movq 0x8(%rbx), %rsi
leaq 0xbf0ad(%rip), %rdx     # 0xcbaf0
movq %r14, %rdi
callq 0x2fa5
movq 0x8(%rbx), %rdi
callq 0xdc25
callq 0xdbb8
movl %eax, %ebp
xorl %r15d, %r15d
leaq 0x8730db(%rip), %r12    # 0x87fb40
leaq 0x1de26(%rip), %r13     # 0x2a892
leaq 0x1dee7(%rip), %rbx     # 0x2a95a
movq %rsp, %r14
testl %ebp, %ebp
jne 0xcc77
movb 0x872ee0(%rip), %al     # 0x87f964
cmpl $0x2, 0x8(%rsp)
setl %cl
notb %al
orb %r15b, %al
orb %cl, %al
testb $0x1, %al
jne 0xcc67
cmpb $0x0, 0x872ece(%rip)    # 0x87f970
jne 0xcc67
movq %r12, %rdi
callq 0x2290
xorl %ebp, %ebp
movq %r13, %rdi
xorl %eax, %eax
callq 0x60fd
cmpb $0x0, 0x872ead(%rip)    # 0x87f970
movl $0x0, %r15d
jne 0xcc50
movq 0x18(%rsp), %rax
movq %rax, 0x872e8d(%rip)    # 0x87f968
movq 0x872e86(%rip), %rdi    # 0x87f968
movq %r14, %rsi
callq 0xd5f6
movq 0x10(%rsp), %rsi
leaq 0x872e82(%rip), %r15    # 0x87f978
movq %r15, %rdi
leaq 0x87ccb0(%rip), %rbp    # 0x8897b0
movq %rbp, %rdx
callq 0x2fa5
movq 0x872e59(%rip), %rsi    # 0x87f968
movq %r15, %rdi
movq %rbp, %rdx
callq 0x2fa5
xorl %ebp, %ebp
leaq 0x1dda0(%rip), %rdi     # 0x2a8c3
movq %r14, %rsi
xorl %eax, %eax
callq 0x60fd
pushq $0x1
popq %rdi
callq 0xc923
xorl %edi, %edi
callq 0xa94e
movq %r12, %rdi
callq 0x20d0
leaq 0x1dd91(%rip), %rdi     # 0x2a8dc
xorl %eax, %eax
callq 0x60fd
movq %r14, %r15
movq %rbx, %r14
movq %r13, %rbx
leaq 0x330(%rsp), %r13
movq %r13, %rdi
leaq 0x872e0b(%rip), %rsi    # 0x87f978
xorl %edx, %edx
callq 0xcd14
movl $0x328, %edx            # imm = 0x328
leaq 0x8(%rsp), %rdi
movq %r13, %rsi
movq %rbx, %r13
movq %r14, %rbx
movq %r15, %r14
callq 0x20f0
leaq 0x1dd77(%rip), %rdi     # 0x2a90d
xorl %eax, %eax
callq 0x60fd
movq %r12, %rdi
callq 0x2290
leaq 0x1dd7d(%rip), %rdi     # 0x2a929
xorl %eax, %eax
callq 0x60fd
movq $0x0, 0x872daa(%rip) # 0x87f968
movb 0x872da0(%rip), %r15b   # 0x87f965
testb %r15b, %r15b
jne 0xcc49
movq %r14, %r12
movq %rbx, %r14
movq %r13, %rbx
leaq 0x872d9e(%rip), %rdi    # 0x87f978
leaq 0xbed3f(%rip), %rbp     # 0xcb920
movq %rbp, %rsi
pushq $0x1
popq %rdx
callq 0x98c8
testb %al, %al
je 0xcca0
movl 0x144(%rbp), %edx
leaq 0x87cbaf(%rip), %rdi    # 0x8897b0
leaq 0xbeee8(%rip), %r13     # 0xcbaf0
movq %r13, %rsi
callq 0xdcec
testb %al, %al
je 0xccbf
movq 0x10(%rsp), %rsi
movq %rbp, %rdi
movq %r13, %rdx
callq 0x2fa5
movq 0x10(%rsp), %rdi
callq 0xdc25
callq 0xdbb8
movl %eax, %ebp
movq %rbx, %r13
movq %r14, %rbx
movq %r12, %r14
leaq 0x872ef7(%rip), %r12    # 0x87fb40
xorl %edi, %edi
callq 0xc923
movq %r12, %rdi
callq 0x20d0
movq %rbx, %rdi
xorl %eax, %eax
callq 0x60fd
jmp 0xca76
leaq 0x1dd1d(%rip), %rdi     # 0x2a98b
xorl %eax, %eax
callq 0x60fd
jmp 0xcc8c
leaq 0x1dd0d(%rip), %rdi     # 0x2a98b
xorl %eax, %eax
callq 0x60fd
movl %ebp, %edi
callq 0xdeec
xorl %eax, %eax
addq $0x658, %rsp            # imm = 0x658
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
leaq 0x1db67(%rip), %rdi     # 0x2a80e
leaq 0x1db82(%rip), %rsi     # 0x2a830
leaq 0x1db89(%rip), %rcx     # 0x2a83e
movl $0x81, %edx
callq 0x20c0
leaq 0x1db93(%rip), %rdi     # 0x2a859
leaq 0x1db63(%rip), %rsi     # 0x2a830
leaq 0x1db6a(%rip), %rcx     # 0x2a83e
movl $0x82, %edx
callq 0x20c0
leaq 0x1db29(%rip), %rdi     # 0x2a80e
leaq 0x1db44(%rip), %rsi     # 0x2a830
leaq 0x1db4b(%rip), %rcx     # 0x2a83e
pushq $0x57
jmp 0xcd0e
leaq 0x1db5b(%rip), %rdi     # 0x2a859
leaq 0x1db2b(%rip), %rsi     # 0x2a830
leaq 0x1db32(%rip), %rcx     # 0x2a83e
pushq $0x58
popq %rdx
callq 0x20c0