// File: /workspace/github_cpp_makefile_star2_O1/jswaff[P]prophet3/src/apply.cpp
// Function: undo_last_move(position*, undo*)
void undo_last_move(position *p,undo *undo_stack) {
    assert(p);
    assert(p->move_counter > 0);
    assert(undo_stack);

    undo *u = undo_stack + p->move_counter - 1;

    p->player = opposite_player(p->player);
    p->ep_sq = u->ep_sq;
    p->castling_rights = u->castling_rights;
    p->fifty_counter = u->fifty_counter;
    p->move_counter--;

    move mv = u->mv;
    assert(abs(u->captured)==get_captured_piece(mv));

    // remove the moving piece from to_sq
    square_t to_sq = get_to_sq(mv);
    square_t from_sq = get_from_sq(mv);
    piece_t piece = get_piece(mv);

    if (p->piece[to_sq] != NO_PIECE) {
        remove_piece(p,to_sq);
    }

    // place the moving piece on from_sq
    add_piece(p,piece * (p->player==WHITE ? 1 : -1),from_sq);
    if (piece==KING) {
        if (p->player==WHITE) {
            p->white_king = from_sq;
        } else {
            p->black_king = from_sq;
        }
    }

    // restore the captured piece
    if (is_capture(mv)) {
        if (is_epcapture(mv)) {
            if (p->player==BLACK) {
                add_piece(p,PAWN,(square_t)(p->ep_sq-8));
            } else {
                add_piece(p,-PAWN,(square_t)(p->ep_sq+8));
            }
        } else {
            add_piece(p,u->captured,to_sq);
        }
    } else if (is_castle(mv)) {
        if (from_sq==E1) {
            if (to_sq==G1) {
                remove_piece(p,F1);
                add_piece(p,ROOK,H1);
            } else {
                remove_piece(p,D1);
                add_piece(p,ROOK,A1);
            }
        } else {
            if (to_sq==G8) {
                remove_piece(p,F8);
                add_piece(p,-ROOK,H8);
            } else {
                remove_piece(p,D8);
                add_piece(p,-ROOK,A8);
            }
        }
    }

    p->hash_key = u->hash_key;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
pushq %rax
testq %rdi, %rdi
je 0x3542
movq %rdi, %rbx
movl 0x144(%rdi), %ebp
testq %rbp, %rbp
je 0x3561
movq %rsi, %r14
testq %rsi, %rsi
je 0x3580
shlq $0x5, %rbp
movl 0x138(%rbx), %edi
callq 0xdfc4
movl %eax, 0x138(%rbx)
movl -0xc(%r14,%rbp), %eax
movl %eax, 0x13c(%rbx)
movl -0x4(%r14,%rbp), %eax
movl %eax, 0x140(%rbx)
movl -0x8(%r14,%rbp), %eax
movl %eax, 0x148(%rbx)
decl 0x144(%rbx)
movq -0x20(%r14,%rbp), %r15
movl -0x10(%r14,%rbp), %eax
movl %eax, %r12d
negl %r12d
cmovsl %eax, %r12d
movq %r15, %rdi
callq 0x77d5
cmpl %eax, %r12d
jne 0x359f
movq %r15, %rdi
callq 0x77b7
movl %eax, %r12d
movq %r15, %rdi
callq 0x77b0
movl %eax, 0x4(%rsp)
movq %r15, %rdi
callq 0x77c1
movl %eax, %r13d
movl %r12d, %eax
cmpl $0x0, (%rbx,%rax,4)
je 0x340a
movq %rbx, %rdi
movl %r12d, %esi
callq 0xa7d2
movl %r13d, %esi
negl %esi
cmpl $0x1, 0x138(%rbx)
cmovel %r13d, %esi
movq %rbx, %rdi
movl 0x4(%rsp), %edx
callq 0xa63d
cmpl $0x6, %r13d
jne 0x344b
cmpl $0x1, 0x138(%rbx)
jne 0x3441
movl 0x4(%rsp), %eax
movl %eax, 0x14c(%rbx)
jmp 0x344b
movl 0x4(%rsp), %eax
movl %eax, 0x150(%rbx)
addq %rbp, %r14
movq %r15, %rdi
callq 0x77df
movq %r15, %rdi
testb %al, %al
je 0x3485
callq 0x77e9
testb %al, %al
je 0x34bb
cmpl $0x0, 0x138(%rbx)
movl 0x13c(%rbx), %edx
je 0x34e9
addl $0x8, %edx
movq %rbx, %rdi
movl $0xffffffff, %esi       # imm = 0xFFFFFFFF
jmp 0x3523
callq 0x77f3
testb %al, %al
je 0x3528
cmpl $0x3c, 0x4(%rsp)
jne 0x34c7
movq %rbx, %rdi
cmpl $0x3e, %r12d
jne 0x34f6
movl $0x3d, %esi
callq 0xa7d2
movq %rbx, %rdi
movl $0x4, %esi
movl $0x3f, %edx
jmp 0x3523
movl -0x10(%r14), %esi
movq %rbx, %rdi
movl %r12d, %edx
jmp 0x3523
movq %rbx, %rdi
cmpl $0x6, %r12d
jne 0x350f
movl $0x5, %esi
callq 0xa7d2
movq %rbx, %rdi
movl $0xfffffffc, %esi       # imm = 0xFFFFFFFC
movl $0x7, %edx
jmp 0x3523
addl $-0x8, %edx
movq %rbx, %rdi
movl $0x1, %esi
jmp 0x3523
movl $0x3b, %esi
callq 0xa7d2
movq %rbx, %rdi
movl $0x4, %esi
movl $0x38, %edx
jmp 0x3523
movl $0x3, %esi
callq 0xa7d2
movq %rbx, %rdi
movl $0xfffffffc, %esi       # imm = 0xFFFFFFFC
xorl %edx, %edx
callq 0xa63d
movq -0x18(%r14), %rax
movq %rax, 0x1b8(%rbx)
addq $0x8, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
leaq 0x31d33(%rip), %rdi     # 0x3527c
leaq 0x25ac2(%rip), %rsi     # 0x29012
leaq 0x25c0c(%rip), %rcx     # 0x29163
movl $0x95, %edx
callq 0x20d0
leaq 0x25c23(%rip), %rdi     # 0x2918b
leaq 0x25aa3(%rip), %rsi     # 0x29012
leaq 0x25bed(%rip), %rcx     # 0x29163
movl $0x96, %edx
callq 0x20d0
leaq 0x25ba9(%rip), %rdi     # 0x29130
leaq 0x25a84(%rip), %rsi     # 0x29012
leaq 0x25bce(%rip), %rcx     # 0x29163
movl $0x97, %edx
callq 0x20d0
leaq 0x25bf9(%rip), %rdi     # 0x2919f
leaq 0x25a65(%rip), %rsi     # 0x29012
leaq 0x25baf(%rip), %rcx     # 0x29163
movl $0xa2, %edx
callq 0x20d0