// File: /workspace/github_cpp_makefile_star2_O2/jswaff[P]prophet3/test/hash__test.cpp
// Function: test_hash_keys2()
void test_hash_keys2() {
    position pos;
    reset_pos(&pos);

    position pos2;
    reset_pos(&pos2);

    uint64 keys[20]; int nkeys=0;
    uint64 keys2[20]; int nkeys2=0;

    assert(build_hash_key(&pos)==build_hash_key(&pos2));

    // step through French Defense with pos1
    apply_move(&pos,to_move(PAWN,E2,E4),gundos);
    keys[nkeys++] = build_hash_key(&pos);
    apply_move(&pos,to_move(PAWN,E7,E6),gundos);
    keys[nkeys++] = build_hash_key(&pos);
    apply_move(&pos,to_move(PAWN,D2,D4),gundos);
    keys[nkeys++] = build_hash_key(&pos);
    apply_move(&pos,to_move(PAWN,D7,D5),gundos);
    keys[nkeys++] = build_hash_key(&pos);
    apply_move(&pos,to_capture(PAWN,E4,D5,PAWN),gundos);
    keys[nkeys++] = build_hash_key(&pos);
    apply_move(&pos,to_capture(PAWN,E6,D5,PAWN),gundos);
    keys[nkeys++] = build_hash_key(&pos);
    apply_move(&pos,to_move(KNIGHT,G1,F3),gundos);
    keys[nkeys++] = build_hash_key(&pos);
    apply_move(&pos,to_move(KNIGHT,G8,F6),gundos);
    keys[nkeys++] = build_hash_key(&pos);

    // step through the Petrov Defense with pos2
    apply_move(&pos2,to_move(PAWN,E2,E4),gundos);
    keys2[nkeys2++] = build_hash_key(&pos2);
    apply_move(&pos2,to_move(PAWN,E7,E5),gundos);
    keys2[nkeys2++] = build_hash_key(&pos2);
    apply_move(&pos2,to_move(KNIGHT,G1,F3),gundos);
    keys2[nkeys2++] = build_hash_key(&pos2);
    apply_move(&pos2,to_move(KNIGHT,G8,F6),gundos);
    keys2[nkeys2++] = build_hash_key(&pos2);
    apply_move(&pos2,to_capture(KNIGHT,F3,E5,PAWN),gundos);
    keys2[nkeys2++] = build_hash_key(&pos2);
    apply_move(&pos2,to_move(PAWN,D7,D6),gundos);
    keys2[nkeys2++] = build_hash_key(&pos2);
    apply_move(&pos2,to_move(KNIGHT,E5,F3),gundos);
    keys2[nkeys2++] = build_hash_key(&pos2);
    apply_move(&pos2,to_capture(KNIGHT,F6,E4,PAWN),gundos);
    keys2[nkeys2++] = build_hash_key(&pos2);
    apply_move(&pos2,to_move(PAWN,D2,D3),gundos);
    keys2[nkeys2++] = build_hash_key(&pos2);
    apply_move(&pos2,to_move(KNIGHT,E4,F6),gundos);
    keys2[nkeys2++] = build_hash_key(&pos2);
    apply_move(&pos2,to_move(PAWN,D3,D4),gundos);
    keys2[nkeys2++] = build_hash_key(&pos2);
    apply_move(&pos2,to_move(PAWN,D6,D5),gundos);
    keys2[nkeys2++] = build_hash_key(&pos2);

    // Positions would be equal at this point, except for move history and fifty counter
    assert(!equal_pos(&pos,&pos2,true));
    assert(build_hash_key(&pos)==build_hash_key(&pos2));

    // by adding a pawn move we should be equal except move history and number of moves
    apply_move(&pos,to_move(PAWN,G2,G3),gundos);
    apply_move(&pos2,to_move(PAWN,G2,G3),gundos);

    assert(!equal_pos(&pos,&pos2,true));
    assert(build_hash_key(&pos)==build_hash_key(&pos2));

    // hash codes should be equal at beginning, move 1, move 7 and end only.
    for (int i=0;i<nkeys;i++) {
        if (i==0) {
            assert(keys2[i]==keys[i]);
            assert(!contains_key(keys[i],keys2,nkeys2,1));
        } else if (i==7) {
            assert(keys2[11]==keys[i]);
            assert(!contains_key(keys[i],keys2,nkeys2-1,0));
        } else {
            assert(!contains_key(keys[i],keys2,nkeys2));
        }
    }

}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x4e8, %rsp            # imm = 0x4E8
leaq 0x158(%rsp), %rbx
movq %rbx, %rdi
callq 0xa187
leaq 0x320(%rsp), %r14
movq %r14, %rdi
callq 0xa187
movq %rbx, %rdi
callq 0x5a50
movq %rax, %rbx
movq %r14, %rdi
callq 0x5a50
cmpq %rax, %rbx
jne 0x1530d
pushq $0x1
popq %rbx
pushq $0x34
popq %rsi
pushq $0x24
popq %r13
movl %ebx, %edi
movl %r13d, %edx
callq 0x7284
leaq 0xb6d6f(%rip), %r12     # 0xcbaf0
leaq 0x158(%rsp), %r15
movq %r15, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %r15, %rdi
callq 0x5a50
movq %rax, (%rsp)
movq %rax, 0xb0(%rsp)
pushq $0xc
popq %rsi
pushq $0x14
popq %r14
movl %ebx, %edi
movl %r14d, %edx
callq 0x7284
movq %r15, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %r15, %rdi
callq 0x5a50
movq %rax, 0xb8(%rsp)
pushq $0x33
popq %rsi
pushq $0x23
popq %rdx
movl %ebx, %edi
callq 0x7284
movq %r15, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %r15, %rdi
callq 0x5a50
movq %rax, 0xc0(%rsp)
pushq $0xb
popq %rsi
pushq $0x1b
popq %rbp
movl %ebx, %edi
movl %ebp, %edx
callq 0x7284
movq %r15, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %r15, %rdi
callq 0x5a50
movq %rax, 0xc8(%rsp)
movl %ebx, %edi
movl %r13d, %esi
movl %ebp, %edx
movl %ebx, %ecx
callq 0x72a3
movq %r15, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %r15, %rdi
callq 0x5a50
movq %rax, 0xd0(%rsp)
movl %ebx, %edi
movl %r14d, %esi
movl %ebp, %edx
movl %ebx, %ecx
movl %ebx, %ebp
callq 0x72a3
movq %r15, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %r15, %rdi
callq 0x5a50
movq %rax, 0xd8(%rsp)
pushq $0x2
popq %r14
pushq $0x3e
popq %rsi
pushq $0x2d
popq %rdx
movl %r14d, %edi
callq 0x7284
movq %r15, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %r15, %rdi
callq 0x5a50
movq %rax, 0xe0(%rsp)
pushq $0x6
popq %rsi
pushq $0x15
popq %rdx
movl %r14d, %edi
callq 0x7284
movq %r15, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %r15, %rdi
callq 0x5a50
movq %rax, %rbx
movq %rax, 0xe8(%rsp)
movl %ebp, %r15d
movl %ebp, %edi
pushq $0x34
popq %rsi
movl %r13d, %edx
callq 0x7284
leaq 0x320(%rsp), %rbp
movq %rbp, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %rbp, %rdi
callq 0x5a50
movq %rax, 0x8(%rsp)
movq %rax, 0x10(%rsp)
pushq $0x1c
popq %r13
movl %r15d, %edi
pushq $0xc
popq %rsi
movl %r13d, %edx
callq 0x7284
movq %rbp, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %rbp, %rdi
callq 0x5a50
movq %rax, 0x18(%rsp)
movl %r14d, %edi
pushq $0x3e
popq %rsi
pushq $0x2d
popq %r15
movl %r15d, %edx
callq 0x7284
movq %rbp, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %rbp, %rdi
callq 0x5a50
movq %rax, 0x20(%rsp)
movl %r14d, %edi
pushq $0x6
popq %rsi
pushq $0x15
popq %rdx
callq 0x7284
movq %rbp, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %rbp, %rdi
callq 0x5a50
movq %rax, 0x28(%rsp)
movl %r14d, %edi
movl %r15d, %esi
movl %r13d, %edx
movl %r13d, %r15d
pushq $0x1
popq %r14
movl %r14d, %ecx
callq 0x72a3
movq %rbp, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %rbp, %rdi
callq 0x5a50
movq %rax, 0x30(%rsp)
pushq $0x13
popq %rdx
movl %r14d, %edi
pushq $0xb
popq %rsi
callq 0x7284
movq %rbp, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %rbp, %rdi
callq 0x5a50
movq %rax, 0x38(%rsp)
pushq $0x2
popq %r13
movl %r13d, %edi
movl %r15d, %esi
pushq $0x2d
popq %rdx
callq 0x7284
movq %rbp, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %rbp, %rdi
callq 0x5a50
movq %rax, 0x40(%rsp)
movl %r13d, %edi
pushq $0x15
popq %rsi
pushq $0x24
popq %r13
movl %r13d, %edx
movl %r14d, %r15d
movl %r14d, %ecx
callq 0x72a3
movq %rbp, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %rbp, %rdi
callq 0x5a50
movq %rax, 0x48(%rsp)
pushq $0x2b
popq %r14
movl %r15d, %edi
pushq $0x33
popq %rsi
movl %r14d, %edx
callq 0x7284
movq %rbp, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %rbp, %rdi
callq 0x5a50
movq %rax, 0x50(%rsp)
pushq $0x2
popq %rdi
movl %r13d, %esi
pushq $0x15
popq %rdx
callq 0x7284
movq %rbp, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %rbp, %rdi
callq 0x5a50
movq %rax, 0x58(%rsp)
movl %r15d, %edi
movl %r14d, %esi
pushq $0x23
popq %rdx
callq 0x7284
movq %rbp, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %rbp, %rdi
callq 0x5a50
movq %rax, 0x60(%rsp)
movl %r15d, %edi
pushq $0x13
popq %rsi
pushq $0x1b
popq %rdx
callq 0x7284
movq %rbp, %rdi
movq %rax, %rsi
movq %r12, %rdx
callq 0x2fa5
movq %rbp, %rdi
callq 0x5a50
movq %rax, %r12
movq %rax, 0x68(%rsp)
leaq 0x158(%rsp), %rdi
movq %rbp, %rsi
movl %r15d, %edx
callq 0x98c8
testb %al, %al
jne 0x1532c
movq (%rsp), %rbp
leaq 0x158(%rsp), %rdi
callq 0x5a50
movq %rax, %r14
leaq 0x320(%rsp), %rdi
callq 0x5a50
cmpq %rax, %r14
jne 0x1534b
pushq $0x1
popq %r14
pushq $0x36
popq %rsi
pushq $0x2e
popq %r15
movl %r14d, %edi
movl %r15d, %edx
callq 0x7284
leaq 0xb6981(%rip), %r13     # 0xcbaf0
leaq 0x158(%rsp), %rdi
movq %rax, %rsi
movq %r13, %rdx
callq 0x2fa5
movl %r14d, %edi
pushq $0x36
popq %rsi
movl %r15d, %edx
callq 0x7284
leaq 0x320(%rsp), %r15
movq %r15, %rdi
movq %rax, %rsi
movq %r13, %rdx
callq 0x2fa5
leaq 0x158(%rsp), %rdi
movq %r15, %rsi
movl %r14d, %edx
callq 0x98c8
testb %al, %al
jne 0x1536a
leaq 0x158(%rsp), %rdi
callq 0x5a50
movq %rax, %r14
leaq 0x320(%rsp), %rdi
callq 0x5a50
cmpq %rax, %r14
jne 0x15389
xorl %r14d, %r14d
leaq 0x10(%rsp), %r15
pushq $0xc
popq %r13
movq %rbx, %rdi
cmpq $0x8, %r14
je 0x15260
cmpl $0x7, %r14d
je 0x1522c
testl %r14d, %r14d
jne 0x15244
cmpq %rbp, 0x8(%rsp)
jne 0x152cf
movq %rbp, %rdi
movq %r15, %rsi
movl %r13d, %edx
pushq $0x1
popq %rcx
callq 0x141cc
testb %al, %al
je 0x1525b
jmp 0x152ee
cmpq %rdi, %r12
jne 0x15272
movq %r15, %rsi
pushq $0xb
popq %rdx
xorl %ecx, %ecx
callq 0x141cc
testb %al, %al
je 0x1525b
jmp 0x15291
movq 0xb0(%rsp,%r14,8), %rdi
movq %r15, %rsi
movl %r13d, %edx
callq 0x141eb
testb %al, %al
jne 0x152b0
incq %r14
jmp 0x151f3
addq $0x4e8, %rsp            # imm = 0x4E8
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
leaq 0x1a9bc(%rip), %rdi     # 0x2fc35
leaq 0x1a8d5(%rip), %rsi     # 0x2fb55
leaq 0x1a943(%rip), %rcx     # 0x2fbca
movl $0xe2, %edx
callq 0x20c0
leaq 0x1a9b0(%rip), %rdi     # 0x2fc48
leaq 0x1a8b6(%rip), %rsi     # 0x2fb55
leaq 0x1a924(%rip), %rcx     # 0x2fbca
movl $0xe3, %edx
callq 0x20c0
leaq 0x1a9b9(%rip), %rdi     # 0x2fc70
leaq 0x1a897(%rip), %rsi     # 0x2fb55
leaq 0x1a905(%rip), %rcx     # 0x2fbca
movl $0xe5, %edx
callq 0x20c0
leaq 0x1a927(%rip), %rdi     # 0x2fbfd
leaq 0x1a878(%rip), %rsi     # 0x2fb55
leaq 0x1a8e6(%rip), %rcx     # 0x2fbca
movl $0xdf, %edx
callq 0x20c0
leaq 0x1a91a(%rip), %rdi     # 0x2fc0f
leaq 0x1a859(%rip), %rsi     # 0x2fb55
leaq 0x1a8c7(%rip), %rcx     # 0x2fbca
movl $0xe0, %edx
callq 0x20c0
leaq 0x1a88a(%rip), %rdi     # 0x2fb9e
leaq 0x1a83a(%rip), %rsi     # 0x2fb55
leaq 0x1a8a8(%rip), %rcx     # 0x2fbca
movl $0xa3, %edx
callq 0x20c0
leaq 0x1a8ae(%rip), %rdi     # 0x2fbe1
leaq 0x1a81b(%rip), %rsi     # 0x2fb55
leaq 0x1a889(%rip), %rcx     # 0x2fbca
movl $0xd2, %edx
callq 0x20c0
leaq 0x1a84c(%rip), %rdi     # 0x2fb9e
leaq 0x1a7fc(%rip), %rsi     # 0x2fb55
leaq 0x1a86a(%rip), %rcx     # 0x2fbca
movl $0xd3, %edx
callq 0x20c0
leaq 0x1a870(%rip), %rdi     # 0x2fbe1
leaq 0x1a7dd(%rip), %rsi     # 0x2fb55
leaq 0x1a84b(%rip), %rcx     # 0x2fbca
movl $0xd9, %edx
callq 0x20c0
leaq 0x1a80e(%rip), %rdi     # 0x2fb9e
leaq 0x1a7be(%rip), %rsi     # 0x2fb55
leaq 0x1a82c(%rip), %rcx     # 0x2fbca
movl $0xda, %edx
callq 0x20c0