magic_generate.c (2007B)
1 #include "internal.h" 2 #include "random.h" 3 4 #include <inttypes.h> 5 #include <stdio.h> 6 #include <stdlib.h> 7 #include <string.h> 8 #include <time.h> 9 10 const char *FORMAT = "C64(0x%llx),\n"; 11 12 U64 generate_magic_number() { 13 return random_get_U64() & random_get_U64() & random_get_U64(); 14 } 15 16 U64 find_magic_number(Square square, int relevant_bits, int bishop) { 17 U64 occupancies[4096], attacks[4096], used_attacks[4096]; 18 U64 attack_mask = bishop ? bishop_mask(square) : rook_mask(square); 19 int occupancy_indicies = 1 << relevant_bits; 20 21 for (int index = 0; index < occupancy_indicies; index++) { 22 occupancies[index] = set_occupancy(index, relevant_bits, attack_mask); 23 attacks[index] = bishop ? bishop_on_the_fly(square, occupancies[index]) 24 : rook_on_the_fly(square, occupancies[index]); 25 } 26 27 for (int random_count = 0; random_count < 100000000; random_count++) { 28 U64 magic_number = generate_magic_number(); 29 if (bit_count((attack_mask * magic_number) & C64(0xFF00000000000000)) < 30 6) 31 continue; 32 33 memset(used_attacks, C64(0), sizeof(used_attacks)); 34 int index, fail; 35 36 for (index = 0, fail = 0; !fail && index < occupancy_indicies; 37 index++) { 38 int magic_index = 39 hash(occupancies[index], magic_number, relevant_bits); 40 41 if (used_attacks[magic_index] == C64(0)) 42 used_attacks[magic_index] = attacks[index]; 43 else if (used_attacks[magic_index] != attacks[index]) 44 fail = 1; 45 } 46 47 if (!fail) return magic_number; 48 } 49 50 return C64(0); 51 } 52 53 int main(void) { 54 random_state_reset(); 55 56 printf("Bishup Magic Numbers:\n"); 57 for (int i = 0; i < 64; i++) 58 printf(FORMAT, find_magic_number(i, bishop_relevant_bits[i], 1)); 59 60 printf("Rook Magic Numbers:\n"); 61 for (int i = 0; i < 64; i++) 62 printf(FORMAT, find_magic_number(i, rook_relevant_bits[i], 0)); 63 return 0; 64 }