home /
fornax /
fornax-v4-0 /
src /
tt /
zobrist.cpp
zobrist.cpp
//
// zobrist.cpp
// fornax3
//
// Created by Anders on 25/12/2020.
//
#include <random>
#include "zobrist.hpp"
#include "board.h"
#include <stdarg.h>
ttkey* hashes;
#define SEED 0xAC20201003
void zobrist_init() {
std::mt19937_64 eng(SEED); // 64-bit Mersenne Twister 19937
std::uniform_int_distribution<ttkey> dist;
hashes = (ttkey*) calloc(64 * 13, sizeof(ttkey));
// pieces numbers
for (int i = 0; i < 12 * 64; ++i) hashes[i] = dist(eng);
// castling numbers
hashes[12 * 64] = dist(eng);
hashes[12 * 64 + 7] = dist(eng);
hashes[12 * 64 + 56] = dist(eng);
hashes[12 * 64 + 63] = dist(eng);
// en passant numbers
for (int i = 12 * 64 + 16; i < 12 * 64 + 24; ++i) hashes[i] = dist(eng);
for (int i = 12 * 64 + 40; i < 12 * 64 + 48; ++i) hashes[i] = dist(eng);
// "whose turn is it" number
hashes[12 * 64 + 49] = dist(eng);
}
void zobrist_destroy() {
free(hashes);
}
ttkey zobrist_compute_hash(const Board* b) {
ttkey hash = 0;
for (int i = 0; i < 6; i++) {
ttkey bb = b->side[WHITE].pieces[i];
while (bb) {
square sq = bits_pop_trailing(&bb);
hash ^= zobrist_get_piece<WHITE>((piecetype) i, sq);
}
bb = b->side[BLACK].pieces[i];
while (bb) {
square sq = bits_pop_trailing(&bb);
hash ^= zobrist_get_piece<BLACK>((piecetype) i, sq);
}
}
if (b->active == BLACK) hash ^= zobrist_get_switchmove();
const Plyinfo* info = &b->plyinfo[b->ply];
if (info->castlingrights & BB_RIGHTS_WCK) hash ^= zobrist_get_castle(7);
if (info->castlingrights & BB_RIGHTS_WCQ) hash ^= zobrist_get_castle(0);
if (info->castlingrights & BB_RIGHTS_BCK) hash ^= zobrist_get_castle(63);
if (info->castlingrights & BB_RIGHTS_BCQ) hash ^= zobrist_get_castle(56);
if (info->enpassant) hash ^= zobrist_get_enpassant(info->enpassant);
return hash;
}