From 6112d4cfc20918891335e4ebbe21efd7c76fec25 Mon Sep 17 00:00:00 2001 From: Rui Coelho Date: Tue, 25 Oct 2022 15:18:20 +0100 Subject: [PATCH 1/2] Introduce trained PSQ tables depending on king position Bench: 2169197 --- psqt-769d9df255ea.dat | Bin 0 -> 40960 bytes src/Evaluation.cpp | 24 +++++++++----- src/PieceSquareTables.cpp | 67 ++++++++++++++++++++++++++++++++++++++ src/PieceSquareTables.hpp | 28 ++++++++++++++++ src/Position.cpp | 47 ++++++++++++++++++++++---- src/Position.hpp | 18 +++++++--- src/Types.hpp | 9 ++++- src/UCI.cpp | 2 ++ src/UCI.hpp | 1 + src/main.cpp | 2 ++ 10 files changed, 177 insertions(+), 21 deletions(-) create mode 100644 psqt-769d9df255ea.dat create mode 100644 src/PieceSquareTables.cpp diff --git a/psqt-769d9df255ea.dat b/psqt-769d9df255ea.dat new file mode 100644 index 0000000000000000000000000000000000000000..da4d732a41adefd65e252c5696ec436b5954dd78 GIT binary patch literal 40960 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 B-LC)u literal 0 HcmV?d00001 diff --git a/src/Evaluation.cpp b/src/Evaluation.cpp index e600a6c..0af102f 100644 --- a/src/Evaluation.cpp +++ b/src/Evaluation.cpp @@ -74,15 +74,21 @@ MixedScore piece_square_value(Board board, EvalData& eval) { eval.fields[WHITE].placement = MixedScore(0, 0); eval.fields[BLACK].placement = MixedScore(0, 0); - Bitboard bb; - for (auto piece : { PAWN, KNIGHT, BISHOP, ROOK, QUEEN, KING }) + Square king_sq[] = { board.get_pieces().bitscan_forward(), + board.get_pieces().bitscan_forward() }; + + for (PieceType p : { PAWN, KNIGHT, BISHOP, ROOK, QUEEN }) { - for (auto turn : { WHITE, BLACK }) + for (Turn t : { WHITE, BLACK }) { - bb = board.get_pieces(turn, piece); - while (bb) - eval.fields[turn].placement += piece_square(piece, bb.bitscan_forward_reset(), turn); + Bitboard b = board.get_pieces(t, p); + while (b) + { + Square s = b.bitscan_forward_reset(); + eval.fields[t].placement += piece_square(p, s, t, king_sq[WHITE], WHITE) + + piece_square(p, s, t, king_sq[BLACK], BLACK); + } } } @@ -490,8 +496,8 @@ Score evaluation(const Board& board, EvalData& data, Thread& thread) MaterialEntry* me = probe_material(board, thread.m_material_table); mixed_result += me->imbalance(); - // Material and PSQT: incrementally updated in the position - mixed_result += board.material() + board.psq(); + // Material incrementally updated in the position + mixed_result += board.material(); // Pawn structure mixed_result += pawns(board, data); @@ -512,7 +518,7 @@ Score evaluation(const Board& board, EvalData& data, Thread& thread) mixed_result += passed(board, data) - passed(board, data); // Tapered eval - Score result = scale(board, data, mixed_result); + Score result = scale(board, data, mixed_result) + board.psq(); // We don't return exact draw scores -> add one unit to the moving side if (result == SCORE_DRAW) diff --git a/src/PieceSquareTables.cpp b/src/PieceSquareTables.cpp new file mode 100644 index 0000000..a76ece6 --- /dev/null +++ b/src/PieceSquareTables.cpp @@ -0,0 +1,67 @@ +#include "Types.hpp" +#include "PieceSquareTables.hpp" +#include +#include +#include + +namespace PSQT +{ + PSQT* psqt_data; + + + PSQT::PSQT(std::string file) + { + std::ifstream input(file, std::ios_base::binary); + assert(input.is_open() && "Failed to open PSQ input file!"); + assert(input.read(reinterpret_cast(m_weights), sizeof(m_weights)) && "Failed to read PSQ data!"); + } + + + Score PSQT::get(PieceType piece, Square square, Turn turn, Square king_sq, Turn king_turn) const + { + // No PSQ data for the king + if (piece == KING) + return 0; + + // Vertical mirror for black + if (turn == BLACK) + { + king_turn = ~king_turn; + square = vertical_mirror(square); + king_sq = vertical_mirror(king_sq); + } + + // Horiziontal mirror if king on the files E to H + if (file(king_sq) >= 4) + { + square = horizontal_mirror(square); + king_sq = horizontal_mirror(king_sq); + } + + // Compute corrected king index (since we are mirrored there are only 4 files) + int king_index = 4 * rank(king_sq) + file(king_sq); + + // Compute PSQ table index + int index = square + + piece * NUM_SQUARES + + king_index * (NUM_SQUARES * (NUM_PIECE_TYPES - 1)) + + king_turn * (NUM_SQUARES * (NUM_PIECE_TYPES - 1) * NUM_SQUARES / 2); + + return m_weights[index]; + } + + + void init() + { + load(PSQT_Default_File); + } + + + void load(std::string file) + { + if (psqt_data) + delete psqt_data; + + psqt_data = new PSQT(file); + } +} diff --git a/src/PieceSquareTables.hpp b/src/PieceSquareTables.hpp index f21d83d..c5dd78b 100644 --- a/src/PieceSquareTables.hpp +++ b/src/PieceSquareTables.hpp @@ -1,6 +1,8 @@ #pragma once #include "Types.hpp" +#define PSQT_Default_File "psqt-769d9df255ea.dat" + using S = MixedScore; constexpr S PawnValue( 125, 200); @@ -122,3 +124,29 @@ constexpr MixedScore piece_square(PieceType piece, Square square, Turn turn) else return psq_table[piece - 1][sq_rank][horizontal_distance(square)] / 2; } + +namespace PSQT +{ + + class PSQT + { + static constexpr std::size_t NUM_FEATURES = 20480; + int16_t m_weights[NUM_FEATURES]; + + public: + PSQT(std::string file); + Score get(PieceType piece, Square square, Turn turn, Square king_sq, Turn king_turn) const; + }; + + extern PSQT* psqt_data; + + void init(); + + void load(std::string file); +} + + +inline Score piece_square(PieceType piece, Square square, Turn turn, Square king_sq, Turn king_turn) +{ + return PSQT::psqt_data->get(piece, square, turn, king_sq, king_turn); +} \ No newline at end of file diff --git a/src/Position.cpp b/src/Position.cpp index 3e33d82..d20267c 100644 --- a/src/Position.cpp +++ b/src/Position.cpp @@ -62,7 +62,6 @@ Board::Board() Board::Board(std::string fen) : m_hash(0), m_material_hash(Zobrist::get_initial_material_hash()), - m_psq(0, 0), m_phase(Phases::Total) { auto c = fen.cbegin(); @@ -70,6 +69,8 @@ Board::Board(std::string fen) // Default initialisation for board pieces std::memset(m_board_pieces, PIECE_NONE, sizeof(m_board_pieces)); std::memset(m_piece_count, 0, sizeof(m_piece_count)); + std::memset(m_psq, 0, sizeof(m_psq)); + std::memset(m_king_sq, 0, sizeof(m_king_sq)); // Read position Square square = SQUARE_A8; @@ -120,6 +121,11 @@ Board::Board(std::string fen) m_hash ^= Zobrist::get_ep_file(file(m_enpassant_square)); update_checkers(); + + m_king_sq[WHITE] = m_pieces[KING][WHITE].bitscan_forward(); + m_king_sq[BLACK] = m_pieces[KING][BLACK].bitscan_forward(); + regen_psqt(WHITE); + regen_psqt(BLACK); } @@ -213,6 +219,24 @@ void Board::update_checkers() } +void Board::regen_psqt(Turn turn) +{ + m_psq[turn] = 0; + for (PieceType p : { PAWN, KNIGHT, BISHOP, ROOK, QUEEN }) + { + for (Turn t : { WHITE, BLACK }) + { + Bitboard b = get_pieces(t, p); + while (b) + { + Square s = b.bitscan_forward_reset(); + m_psq[turn] += piece_square(p, s, t, m_king_sq[turn], turn) * turn_to_color(t); + } + } + } +} + + void Board::generate_moves(MoveList& list, MoveGenType type) const { if (m_turn == WHITE) @@ -294,6 +318,13 @@ Board Board::make_move(Move move) const result.move_piece(piece, m_turn, move.from(), move.to()); } + // After a king move, update PSQ tables + if (piece == KING) + { + result.m_king_sq[m_turn] = result.m_pieces[KING][m_turn].bitscan_forward(); + result.regen_psqt(m_turn); + } + // Swap turns result.m_turn = ~m_turn; result.m_hash ^= Zobrist::get_black_move(); @@ -343,7 +374,7 @@ bool Board::is_valid() const // Material and phase evaluation uint8_t phase = Phases::Total; MixedScore material(0, 0); - MixedScore psq(0, 0); + Score psq_sides[2] = { Score(0), Score(0) }; Hash material_hash = 0; for (PieceType piece : { PAWN, KNIGHT, BISHOP, ROOK, QUEEN, KING }) for (Turn turn : { WHITE, BLACK }) @@ -355,14 +386,18 @@ bool Board::is_valid() const phase -= bb.count() * Phases::Pieces[piece]; material_hash ^= Zobrist::get_piece_turn_square(piece, turn, bb.count()); while (bb) - psq += piece_square(piece, bb.bitscan_forward_reset(), turn) * turn_to_color(turn); + { + Square s = bb.bitscan_forward_reset(); + psq_sides[WHITE] += piece_square(piece, s, turn, m_king_sq[WHITE], WHITE) * turn_to_color(turn); + psq_sides[BLACK] += piece_square(piece, s, turn, m_king_sq[BLACK], BLACK) * turn_to_color(turn); + } } MixedScore total_material = m_material[WHITE] - m_material[BLACK]; if (phase != m_phase) return false; if (material.middlegame() != total_material.middlegame() || material.endgame() != total_material.endgame()) return false; - if (psq.middlegame() != m_psq.middlegame() || psq.endgame() != m_psq.endgame()) + if (psq_sides[WHITE] != m_psq[WHITE] || psq_sides[BLACK] != m_psq[BLACK]) return false; if (material_hash != m_material_hash) return false; @@ -527,9 +562,9 @@ MixedScore Board::material(Turn turn) const } -MixedScore Board::psq() const +Score Board::psq() const { - return m_psq; + return m_psq[WHITE] + m_psq[BLACK]; } diff --git a/src/Position.hpp b/src/Position.hpp index 52d708e..37b3e68 100644 --- a/src/Position.hpp +++ b/src/Position.hpp @@ -26,11 +26,12 @@ class Board int m_full_move_clock; // Updated fields + Square m_king_sq[NUM_COLORS]; Hash m_hash; Hash m_material_hash; Bitboard m_checkers; MixedScore m_material[NUM_COLORS]; - MixedScore m_psq; + Score m_psq[NUM_COLORS]; uint8_t m_phase; Piece m_board_pieces[NUM_SQUARES]; uint8_t m_piece_count[NUM_PIECE_TYPES][NUM_COLORS]; @@ -262,7 +263,8 @@ class Board m_pieces[piece][turn].set(square); m_hash ^= Zobrist::get_piece_turn_square(piece, turn, square); m_board_pieces[square] = get_piece(piece, turn); - m_psq += piece_square(piece, square, turn) * turn_to_color(turn); + m_psq[WHITE] += piece_square(piece, square, turn, m_king_sq[WHITE], WHITE) * turn_to_color(turn); + m_psq[BLACK] += piece_square(piece, square, turn, m_king_sq[BLACK], BLACK) * turn_to_color(turn); m_material[turn] += piece_value[piece]; m_phase -= Phases::Pieces[piece]; m_piece_count[piece][turn]++; @@ -276,7 +278,8 @@ class Board m_pieces[piece][turn].reset(square); m_hash ^= Zobrist::get_piece_turn_square(piece, turn, square); m_board_pieces[square] = NO_PIECE; - m_psq -= piece_square(piece, square, turn) * turn_to_color(turn); + m_psq[WHITE] -= piece_square(piece, square, turn, m_king_sq[WHITE], WHITE) * turn_to_color(turn); + m_psq[BLACK] -= piece_square(piece, square, turn, m_king_sq[BLACK], BLACK) * turn_to_color(turn); m_material[turn] -= piece_value[piece]; m_phase += Phases::Pieces[piece]; m_piece_count[piece][turn]--; @@ -293,7 +296,10 @@ class Board m_hash ^= Zobrist::get_piece_turn_square(piece, turn, to); m_board_pieces[from] = NO_PIECE; m_board_pieces[to] = get_piece(piece, turn); - m_psq += (piece_square(piece, to, turn) - piece_square(piece, from, turn)) * turn_to_color(turn); + m_psq[WHITE] -= piece_square(piece, from, turn, m_king_sq[WHITE], WHITE) * turn_to_color(turn); + m_psq[BLACK] -= piece_square(piece, from, turn, m_king_sq[BLACK], BLACK) * turn_to_color(turn); + m_psq[WHITE] += piece_square(piece, to, turn, m_king_sq[WHITE], WHITE) * turn_to_color(turn); + m_psq[BLACK] += piece_square(piece, to, turn, m_king_sq[BLACK], BLACK) * turn_to_color(turn); } @@ -462,6 +468,8 @@ class Board return legal(move, occupancy); } + void regen_psqt(Turn turn); + public: Board(); @@ -630,7 +638,7 @@ class Board MixedScore material(Turn turn) const; - MixedScore psq() const; + Score psq() const; uint8_t phase() const; diff --git a/src/Types.hpp b/src/Types.hpp index 8551fd7..e42ab71 100644 --- a/src/Types.hpp +++ b/src/Types.hpp @@ -33,6 +33,7 @@ enum Turn : int8_t enum Color : int8_t { WHITE_COLOR = 1, + NO_COLOR = 0, BLACK_COLOR = -1 }; @@ -256,7 +257,13 @@ inline constexpr Square horizontal_distance(Square square) inline constexpr Square vertical_mirror(Square square) { - return file(square) + (7 - rank(square)); + return make_square(7 - rank(square), file(square)); +} + + +inline constexpr Square horizontal_mirror(Square square) +{ + return make_square(rank(square), 7 - file(square)); } template diff --git a/src/UCI.cpp b/src/UCI.cpp index 321f3ca..0e0f7a4 100644 --- a/src/UCI.cpp +++ b/src/UCI.cpp @@ -25,6 +25,7 @@ namespace UCI bool Ponder; int Threads; int MoveOverhead; + std::string PSQT_File; } @@ -104,6 +105,7 @@ namespace UCI [](int v) { pool->resize(v); })); OptionsMap.emplace("Move Overhead", Option(&Options::MoveOverhead, 0, 0, 5000)); OptionsMap.emplace("Ponder", Option(&Options::Ponder, false)); + OptionsMap.emplace("PSQT_File", Option(&Options::PSQT_File, PSQT_Default_File, PSQT::load)); } diff --git a/src/UCI.hpp b/src/UCI.hpp index 22534b8..0815d1a 100644 --- a/src/UCI.hpp +++ b/src/UCI.hpp @@ -86,6 +86,7 @@ namespace UCI extern bool Ponder; extern int Threads; extern int MoveOverhead; + extern std::string PSQT_File; } diff --git a/src/main.cpp b/src/main.cpp index a6e0bf6..ffcae92 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -1,5 +1,6 @@ #include "Types.hpp" #include "Position.hpp" +#include "PieceSquareTables.hpp" #include "Tests.hpp" #include "Zobrist.hpp" #include "Search.hpp" @@ -12,6 +13,7 @@ int main(int argc, char** argv) { Bitboards::init_bitboards(); Zobrist::build_rnd_hashes(); + PSQT::init(); UCI::init_options(); ttable = HashTable(16); pool = new ThreadPool(); From fe0faec36ac2872f46709aaa885813dc121e6f85 Mon Sep 17 00:00:00 2001 From: Rui Coelho Date: Sat, 5 Nov 2022 02:26:16 +0000 Subject: [PATCH 2/2] Embed default PSQ table in the binary with incbin Bench: 2169197 --- src/PieceSquareTables.cpp | 102 ++++---- src/PieceSquareTables.hpp | 107 +-------- src/UCI.cpp | 2 +- src/incbin/UNLICENSE | 24 ++ src/incbin/incbin.h | 476 ++++++++++++++++++++++++++++++++++++++ src/main.cpp | 1 + 6 files changed, 577 insertions(+), 135 deletions(-) create mode 100644 src/incbin/UNLICENSE create mode 100644 src/incbin/incbin.h diff --git a/src/PieceSquareTables.cpp b/src/PieceSquareTables.cpp index a76ece6..28a8d90 100644 --- a/src/PieceSquareTables.cpp +++ b/src/PieceSquareTables.cpp @@ -1,67 +1,91 @@ #include "Types.hpp" #include "PieceSquareTables.hpp" -#include +#include #include #include namespace PSQT { - PSQT* psqt_data; + const FeatureType* psqt_data; - PSQT::PSQT(std::string file) + INCBIN(FeatureType, EmbeddedPSQT, PSQT_Default_File); + + + void init() { - std::ifstream input(file, std::ios_base::binary); - assert(input.is_open() && "Failed to open PSQ input file!"); - assert(input.read(reinterpret_cast(m_weights), sizeof(m_weights)) && "Failed to read PSQ data!"); + psqt_data = nullptr; + load(PSQT_Default_File); } - - Score PSQT::get(PieceType piece, Square square, Turn turn, Square king_sq, Turn king_turn) const + + void load(std::string file) { - // No PSQ data for the king - if (piece == KING) - return 0; + if (psqt_data) + clean(); - // Vertical mirror for black - if (turn == BLACK) + if (file == "" || file == PSQT_Default_File) { - king_turn = ~king_turn; - square = vertical_mirror(square); - king_sq = vertical_mirror(king_sq); + psqt_data = gEmbeddedPSQTData; } - - // Horiziontal mirror if king on the files E to H - if (file(king_sq) >= 4) + else { - square = horizontal_mirror(square); - king_sq = horizontal_mirror(king_sq); - } + std::ifstream input(file, std::ios_base::binary); + if (!input.is_open()) + { + std::cerr << "Failed to open PSQ input file!" << std::endl; + std::abort(); + } - // Compute corrected king index (since we are mirrored there are only 4 files) - int king_index = 4 * rank(king_sq) + file(king_sq); + psqt_data = new FeatureType[NUM_FEATURES]; + + if(!input.read(const_cast(reinterpret_cast(psqt_data)), NUM_FEATURES * sizeof(FeatureType))) + { + std::cerr << "Failed to read PSQ data!" << std::endl; + std::abort(); + } + } + } - // Compute PSQ table index - int index = square - + piece * NUM_SQUARES - + king_index * (NUM_SQUARES * (NUM_PIECE_TYPES - 1)) - + king_turn * (NUM_SQUARES * (NUM_PIECE_TYPES - 1) * NUM_SQUARES / 2); - return m_weights[index]; + void clean() + { + if (psqt_data != gEmbeddedPSQTData) + delete[] psqt_data; + psqt_data = nullptr; } +} - void init() +Score piece_square(PieceType piece, Square square, Turn turn, Square king_sq, Turn king_turn) +{ + // No PSQ data for the king + if (piece == KING) + return 0; + + // Vertical mirror for black + if (turn == BLACK) { - load(PSQT_Default_File); + king_turn = ~king_turn; + square = vertical_mirror(square); + king_sq = vertical_mirror(king_sq); } - - void load(std::string file) + // Horiziontal mirror if king on the files E to H + if (file(king_sq) >= 4) { - if (psqt_data) - delete psqt_data; - - psqt_data = new PSQT(file); + square = horizontal_mirror(square); + king_sq = horizontal_mirror(king_sq); } -} + + // Compute corrected king index (since we are mirrored there are only 4 files) + int king_index = 4 * rank(king_sq) + file(king_sq); + + // Compute PSQ table index + int index = square + + piece * NUM_SQUARES + + king_index * (NUM_SQUARES * (NUM_PIECE_TYPES - 1)) + + king_turn * (NUM_SQUARES * (NUM_PIECE_TYPES - 1) * NUM_SQUARES / 2); + + return PSQT::psqt_data[index]; +} \ No newline at end of file diff --git a/src/PieceSquareTables.hpp b/src/PieceSquareTables.hpp index c5dd78b..efb8641 100644 --- a/src/PieceSquareTables.hpp +++ b/src/PieceSquareTables.hpp @@ -1,4 +1,5 @@ #pragma once +#include "incbin/incbin.h" #include "Types.hpp" #define PSQT_Default_File "psqt-769d9df255ea.dat" @@ -39,114 +40,30 @@ constexpr Score piece_value_eg[] = { PawnValue.endgame(), 0, // Empty 0 }; // PIECE_NONE -// Tables stolen from Stockfish using the implicitly mirrored convention -constexpr S psq_table[][8][4] = { - { // Knight - { S(-175, -96), S(-92, -65), S(-74, -49), S(-73, -21) }, - { S( -77, -67), S(-41, -54), S(-27, -18), S(-15, 8) }, - { S( -61, -40), S(-17, -27), S( 6, -8), S( 12, 29) }, - { S( -35, -35), S( 8, -2), S( 40, 13), S( 49, 28) }, - { S( -34, -45), S( 13, -16), S( 44, 9), S( 51, 39) }, - { S( -9, -51), S( 22, -44), S( 58, -16), S( 53, 17) }, - { S( -67, -69), S(-27, -50), S( 4, -51), S( 37, 12) }, - { S(-201, -100), S(-83, -88), S(-56, -56), S(-26, -17) } - }, - { // Bishop - { S(-37, -40), S( -4, -21), S( -6, -26), S(-16, -8) }, - { S(-11, -26), S( 6, -9), S( 13, -12), S( 3, 1) }, - { S( -5, -11), S( 15, -1), S( -4, -1), S( 12, 7) }, - { S( -4, -14), S( 8, -4), S( 18, 0), S( 27, 12) }, - { S( -8, -12), S( 20, -1), S( 15, -10), S( 22, 11) }, - { S(-11, -21), S( 4, 4), S( 1, 3), S( 8, 4) }, - { S(-12, -22), S(-10, -14), S( 4, -1), S( 0, 1) }, - { S(-34, -32), S( 1, -29), S(-10, -26), S(-16, -17) } - }, - { // Rook - { S(-31, -9), S(-20, -13), S(-14, -10), S(-5, -9) }, - { S(-21, -12), S(-13, -9), S( -8, -1), S( 6, -2) }, - { S(-25, 6), S(-11, -8), S( -1, -2), S( 3, -6) }, - { S(-13, -6), S( -5, 1), S( -4, -9), S(-6, 7) }, - { S(-27, -5), S(-15, 8), S( -4, 7), S( 3, -6) }, - { S(-22, 6), S( -2, 1), S( 6, -7), S(12, 10) }, - { S( -2, 4), S( 12, 5), S( 16, 20), S(18, -5) }, - { S(-17, 18), S(-19, 0), S( -1, 19), S( 9, 13) } - }, - { // Queen - { S( 3, -69), S(-5, -57), S(-5, -47), S( 4, -26) }, - { S(-3, -54), S( 5, -31), S( 8, -22), S(12, -4) }, - { S(-3, -39), S( 6, -18), S(13, -9), S( 7, 3) }, - { S( 4, -23), S( 5, -3), S( 9, 13), S( 8, 24) }, - { S( 0, -29), S(14, -6), S(12, 9), S( 5, 21) }, - { S(-4, -38), S(10, -18), S( 6, -11), S( 8, 1) }, - { S(-5, -50), S( 6, -27), S(10, -24), S( 8, -8) }, - { S(-2, -74), S(-2, -52), S( 1, -43), S(-2, -34) } - }, - { // King - { S(271, 1), S(327, 45), S(271, 85), S(198, 76) }, - { S(278, 53), S(303, 100), S(234, 133), S(179, 135) }, - { S(195, 88), S(258, 130), S(169, 169), S(120, 175) }, - { S(164, 103), S(190, 156), S(138, 172), S( 98, 172) }, - { S(154, 96), S(179, 166), S(105, 199), S( 70, 199) }, - { S(123, 92), S(145, 172), S( 81, 184), S( 31, 191) }, - { S( 88, 47), S(120, 121), S( 65, 116), S( 33, 131) }, - { S( 59, 11), S( 89, 59), S( 45, 73), S( -1, 78) } - } -}; - - -constexpr S psq_table_pawns[6][8] = -{ // Pawn (asymmetric distribution) - { S( 2, -8), S( 4, -6), S( 11, 9), S( 18, 5), S(16, 16), S( 21, 6), S( 9, -6), S( -3, -18) }, - { S(-9, -9), S(-15, -7), S( 11, -10), S( 15, 5), S(31, 2), S( 23, 3), S( 6, -8), S(-20, -5) }, - { S(-3, 7), S(-20, 1), S( 8, -8), S( 19, -2), S(39, -14), S( 17, -13), S( 2, -11), S( -5, -6) }, - { S(11, 12), S( -4, 6), S(-11, 2), S( 2, -6), S(11, -5), S( 0, -4), S(-12, 14), S( 5, 9) }, - { S( 3, 27), S(-11, 18), S( -6, 19), S( 22, 29), S(-8, 30), S( -5, 9), S(-14, 8), S(-11, 14) }, - { S(-7, -1), S( 6, -14), S( -2, 13), S(-11, 22), S( 4, 24), S(-14, 17), S( 10, 7), S( -9, 7) } -}; - constexpr S imbalance_terms[][NUM_PIECE_TYPES] = { // Pawn Knight Bishop Rook Queen - { S( 0, 0) }, // Pawn - { S(14, 10), S(-5, -6) }, // Knight - { S( 6, 7), S( 1, 2), S( 0, 0) }, // Bishop - { S( 0, 0), S( 7, 4), S( 9, 8), S(-12, -11) }, // Rook - { S( 0, 0), S( 9, 9), S(10, 7), S(-11, -13), S(0, 0) } // Queen + { S( 0, 0) }, // Pawn + { S(14, 10), S(-5, -6) }, // Knight + { S( 6, 7), S( 1, 2), S( 0, 0) }, // Bishop + { S( 0, 0), S( 7, 4), S( 9, 8), S(-12, -11) }, // Rook + { S( 0, 0), S( 9, 9), S(10, 7), S(-11, -13), S(0, 0) } // Queen }; -constexpr MixedScore piece_square(PieceType piece, Square square, Turn turn) -{ - // Correct piece position for table lookup - int sq_rank = (turn == WHITE) ? rank(square) : (7 - rank(square)); - if (piece == PAWN) - return psq_table_pawns[sq_rank - 1][file(square)]; - else - return psq_table[piece - 1][sq_rank][horizontal_distance(square)] / 2; -} - namespace PSQT { + using FeatureType = int16_t; + static constexpr std::size_t NUM_FEATURES = 20480; - class PSQT - { - static constexpr std::size_t NUM_FEATURES = 20480; - int16_t m_weights[NUM_FEATURES]; - - public: - PSQT(std::string file); - Score get(PieceType piece, Square square, Turn turn, Square king_sq, Turn king_turn) const; - }; - - extern PSQT* psqt_data; + extern const FeatureType* psqt_data; void init(); void load(std::string file); + + void clean(); } -inline Score piece_square(PieceType piece, Square square, Turn turn, Square king_sq, Turn king_turn) -{ - return PSQT::psqt_data->get(piece, square, turn, king_sq, king_turn); -} \ No newline at end of file +Score piece_square(PieceType piece, Square square, Turn turn, Square king_sq, Turn king_turn); \ No newline at end of file diff --git a/src/UCI.cpp b/src/UCI.cpp index 0e0f7a4..dda29a6 100644 --- a/src/UCI.cpp +++ b/src/UCI.cpp @@ -105,7 +105,7 @@ namespace UCI [](int v) { pool->resize(v); })); OptionsMap.emplace("Move Overhead", Option(&Options::MoveOverhead, 0, 0, 5000)); OptionsMap.emplace("Ponder", Option(&Options::Ponder, false)); - OptionsMap.emplace("PSQT_File", Option(&Options::PSQT_File, PSQT_Default_File, PSQT::load)); + OptionsMap.emplace("PSQT_File", Option(&Options::PSQT_File, "", PSQT::load)); } diff --git a/src/incbin/UNLICENSE b/src/incbin/UNLICENSE new file mode 100644 index 0000000..68a49da --- /dev/null +++ b/src/incbin/UNLICENSE @@ -0,0 +1,24 @@ +This is free and unencumbered software released into the public domain. + +Anyone is free to copy, modify, publish, use, compile, sell, or +distribute this software, either in source code form or as a compiled +binary, for any purpose, commercial or non-commercial, and by any +means. + +In jurisdictions that recognize copyright laws, the author or authors +of this software dedicate any and all copyright interest in the +software to the public domain. We make this dedication for the benefit +of the public at large and to the detriment of our heirs and +successors. We intend this dedication to be an overt act of +relinquishment in perpetuity of all present and future rights to this +software under copyright law. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR +OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, +ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +OTHER DEALINGS IN THE SOFTWARE. + +For more information, please refer to diff --git a/src/incbin/incbin.h b/src/incbin/incbin.h new file mode 100644 index 0000000..8542825 --- /dev/null +++ b/src/incbin/incbin.h @@ -0,0 +1,476 @@ +/** + * @file incbin.h + * @author Dale Weiler + * @brief Utility for including binary files + * + * Facilities for including binary files into the current translation unit and + * making use from them externally in other translation units. + */ +#ifndef INCBIN_HDR +#define INCBIN_HDR +#include +#if defined(__AVX512BW__) || \ + defined(__AVX512CD__) || \ + defined(__AVX512DQ__) || \ + defined(__AVX512ER__) || \ + defined(__AVX512PF__) || \ + defined(__AVX512VL__) || \ + defined(__AVX512F__) +# define INCBIN_ALIGNMENT_INDEX 6 +#elif defined(__AVX__) || \ + defined(__AVX2__) +# define INCBIN_ALIGNMENT_INDEX 5 +#elif defined(__SSE__) || \ + defined(__SSE2__) || \ + defined(__SSE3__) || \ + defined(__SSSE3__) || \ + defined(__SSE4_1__) || \ + defined(__SSE4_2__) || \ + defined(__neon__) || \ + defined(__ARM_NEON) || \ + defined(__ALTIVEC__) +# define INCBIN_ALIGNMENT_INDEX 4 +#elif ULONG_MAX != 0xffffffffu +# define INCBIN_ALIGNMENT_INDEX 3 +# else +# define INCBIN_ALIGNMENT_INDEX 2 +#endif + +/* Lookup table of (1 << n) where `n' is `INCBIN_ALIGNMENT_INDEX' */ +#define INCBIN_ALIGN_SHIFT_0 1 +#define INCBIN_ALIGN_SHIFT_1 2 +#define INCBIN_ALIGN_SHIFT_2 4 +#define INCBIN_ALIGN_SHIFT_3 8 +#define INCBIN_ALIGN_SHIFT_4 16 +#define INCBIN_ALIGN_SHIFT_5 32 +#define INCBIN_ALIGN_SHIFT_6 64 + +/* Actual alignment value */ +#define INCBIN_ALIGNMENT \ + INCBIN_CONCATENATE( \ + INCBIN_CONCATENATE(INCBIN_ALIGN_SHIFT, _), \ + INCBIN_ALIGNMENT_INDEX) + +/* Stringize */ +#define INCBIN_STR(X) \ + #X +#define INCBIN_STRINGIZE(X) \ + INCBIN_STR(X) +/* Concatenate */ +#define INCBIN_CAT(X, Y) \ + X ## Y +#define INCBIN_CONCATENATE(X, Y) \ + INCBIN_CAT(X, Y) +/* Deferred macro expansion */ +#define INCBIN_EVAL(X) \ + X +#define INCBIN_INVOKE(N, ...) \ + INCBIN_EVAL(N(__VA_ARGS__)) +/* Variable argument count for overloading by arity */ +#define INCBIN_VA_ARG_COUNTER(_1, _2, _3, N, ...) N +#define INCBIN_VA_ARGC(...) INCBIN_VA_ARG_COUNTER(__VA_ARGS__, 3, 2, 1, 0) + +/* Green Hills uses a different directive for including binary data */ +#if defined(__ghs__) +# if (__ghs_asm == 2) +# define INCBIN_MACRO ".file" +/* Or consider the ".myrawdata" entry in the ld file */ +# else +# define INCBIN_MACRO "\tINCBIN" +# endif +#else +# define INCBIN_MACRO ".incbin" +#endif + +#ifndef _MSC_VER +# define INCBIN_ALIGN \ + __attribute__((aligned(INCBIN_ALIGNMENT))) +#else +# define INCBIN_ALIGN __declspec(align(INCBIN_ALIGNMENT)) +#endif + +#if defined(__arm__) || /* GNU C and RealView */ \ + defined(__arm) || /* Diab */ \ + defined(_ARM) /* ImageCraft */ +# define INCBIN_ARM +#endif + +#ifdef __GNUC__ +/* Utilize .balign where supported */ +# define INCBIN_ALIGN_HOST ".balign " INCBIN_STRINGIZE(INCBIN_ALIGNMENT) "\n" +# define INCBIN_ALIGN_BYTE ".balign 1\n" +#elif defined(INCBIN_ARM) +/* + * On arm assemblers, the alignment value is calculated as (1 << n) where `n' is + * the shift count. This is the value passed to `.align' + */ +# define INCBIN_ALIGN_HOST ".align " INCBIN_STRINGIZE(INCBIN_ALIGNMENT_INDEX) "\n" +# define INCBIN_ALIGN_BYTE ".align 0\n" +#else +/* We assume other inline assembler's treat `.align' as `.balign' */ +# define INCBIN_ALIGN_HOST ".align " INCBIN_STRINGIZE(INCBIN_ALIGNMENT) "\n" +# define INCBIN_ALIGN_BYTE ".align 1\n" +#endif + +/* INCBIN_CONST is used by incbin.c generated files */ +#if defined(__cplusplus) +# define INCBIN_EXTERNAL extern "C" +# define INCBIN_CONST extern const +#else +# define INCBIN_EXTERNAL extern +# define INCBIN_CONST const +#endif + +/** + * @brief Optionally override the linker section into which size and data is + * emitted. + * + * @warning If you use this facility, you might have to deal with + * platform-specific linker output section naming on your own. + */ +#if !defined(INCBIN_OUTPUT_SECTION) +# if defined(__APPLE__) +# define INCBIN_OUTPUT_SECTION ".const_data" +# else +# define INCBIN_OUTPUT_SECTION ".rodata" +# endif +#endif + +/** + * @brief Optionally override the linker section into which data is emitted. + * + * @warning If you use this facility, you might have to deal with + * platform-specific linker output section naming on your own. + */ +#if !defined(INCBIN_OUTPUT_DATA_SECTION) +# define INCBIN_OUTPUT_DATA_SECTION INCBIN_OUTPUT_SECTION +#endif + +/** + * @brief Optionally override the linker section into which size is emitted. + * + * @warning If you use this facility, you might have to deal with + * platform-specific linker output section naming on your own. + * + * @note This is useful for Harvard architectures where program memory cannot + * be directly read from the program without special instructions. With this you + * can chose to put the size variable in RAM rather than ROM. + */ +#if !defined(INCBIN_OUTPUT_SIZE_SECTION) +# define INCBIN_OUTPUT_SIZE_SECTION INCBIN_OUTPUT_SECTION +#endif + +#if defined(__APPLE__) +# include "TargetConditionals.h" +# if defined(TARGET_OS_IPHONE) && !defined(INCBIN_SILENCE_BITCODE_WARNING) +# warning "incbin is incompatible with bitcode. Using the library will break upload to App Store if you have bitcode enabled. Add `#define INCBIN_SILENCE_BITCODE_WARNING` before including this header to silence this warning." +# endif +/* The directives are different for Apple branded compilers */ +# define INCBIN_SECTION INCBIN_OUTPUT_SECTION "\n" +# define INCBIN_GLOBAL(NAME) ".globl " INCBIN_MANGLE INCBIN_STRINGIZE(INCBIN_PREFIX) #NAME "\n" +# define INCBIN_INT ".long " +# define INCBIN_MANGLE "_" +# define INCBIN_BYTE ".byte " +# define INCBIN_TYPE(...) +#else +# define INCBIN_SECTION ".section " INCBIN_OUTPUT_SECTION "\n" +# define INCBIN_GLOBAL(NAME) ".global " INCBIN_STRINGIZE(INCBIN_PREFIX) #NAME "\n" +# if defined(__ghs__) +# define INCBIN_INT ".word " +# else +# define INCBIN_INT ".int " +# endif +# if defined(__USER_LABEL_PREFIX__) +# define INCBIN_MANGLE INCBIN_STRINGIZE(__USER_LABEL_PREFIX__) +# else +# define INCBIN_MANGLE "" +# endif +# if defined(INCBIN_ARM) +/* On arm assemblers, `@' is used as a line comment token */ +# define INCBIN_TYPE(NAME) ".type " INCBIN_STRINGIZE(INCBIN_PREFIX) #NAME ", %object\n" +# elif defined(__MINGW32__) || defined(__MINGW64__) +/* Mingw doesn't support this directive either */ +# define INCBIN_TYPE(NAME) +# else +/* It's safe to use `@' on other architectures */ +# define INCBIN_TYPE(NAME) ".type " INCBIN_STRINGIZE(INCBIN_PREFIX) #NAME ", @object\n" +# endif +# define INCBIN_BYTE ".byte " +#endif + +/* List of style types used for symbol names */ +#define INCBIN_STYLE_CAMEL 0 +#define INCBIN_STYLE_SNAKE 1 + +/** + * @brief Specify the prefix to use for symbol names. + * + * @note By default this is "g". + * + * @code + * #define INCBIN_PREFIX incbin + * #include "incbin.h" + * INCBIN(Foo, "foo.txt"); + * + * // Now you have the following symbols instead: + * // const unsigned char incbinFoo[]; + * // const unsigned char *const incbinFoo; + * // const unsigned int incbinFoo; + * @endcode + */ +#if !defined(INCBIN_PREFIX) +# define INCBIN_PREFIX g +#endif + +/** + * @brief Specify the style used for symbol names. + * + * Possible options are + * - INCBIN_STYLE_CAMEL "CamelCase" + * - INCBIN_STYLE_SNAKE "snake_case" + * + * @note By default this is INCBIN_STYLE_CAMEL + * + * @code + * #define INCBIN_STYLE INCBIN_STYLE_SNAKE + * #include "incbin.h" + * INCBIN(foo, "foo.txt"); + * + * // Now you have the following symbols: + * // const unsigned char foo_data[]; + * // const unsigned char *const foo_end; + * // const unsigned int foo_size; + * @endcode + */ +#if !defined(INCBIN_STYLE) +# define INCBIN_STYLE INCBIN_STYLE_CAMEL +#endif + +/* Style lookup tables */ +#define INCBIN_STYLE_0_DATA Data +#define INCBIN_STYLE_0_END End +#define INCBIN_STYLE_0_SIZE Size +#define INCBIN_STYLE_1_DATA _data +#define INCBIN_STYLE_1_END _end +#define INCBIN_STYLE_1_SIZE _size + +/* Style lookup: returning identifier */ +#define INCBIN_STYLE_IDENT(TYPE) \ + INCBIN_CONCATENATE( \ + INCBIN_STYLE_, \ + INCBIN_CONCATENATE( \ + INCBIN_EVAL(INCBIN_STYLE), \ + INCBIN_CONCATENATE(_, TYPE))) + +/* Style lookup: returning string literal */ +#define INCBIN_STYLE_STRING(TYPE) \ + INCBIN_STRINGIZE( \ + INCBIN_STYLE_IDENT(TYPE)) \ + +/* Generate the global labels by indirectly invoking the macro with our style + * type and concatenating the name against them. */ +#define INCBIN_GLOBAL_LABELS(NAME, TYPE) \ + INCBIN_INVOKE( \ + INCBIN_GLOBAL, \ + INCBIN_CONCATENATE( \ + NAME, \ + INCBIN_INVOKE( \ + INCBIN_STYLE_IDENT, \ + TYPE))) \ + INCBIN_INVOKE( \ + INCBIN_TYPE, \ + INCBIN_CONCATENATE( \ + NAME, \ + INCBIN_INVOKE( \ + INCBIN_STYLE_IDENT, \ + TYPE))) + +/** + * @brief Externally reference binary data included in another translation unit. + * + * Produces three external symbols that reference the binary data included in + * another translation unit. + * + * The symbol names are a concatenation of `INCBIN_PREFIX' before *NAME*; with + * "Data", as well as "End" and "Size" after. An example is provided below. + * + * @param TYPE Optional array type. Omitting this picks a default of `unsigned char`. + * @param NAME The name given for the binary data + * + * @code + * INCBIN_EXTERN(Foo); + * + * // Now you have the following symbols: + * // extern const unsigned char Foo[]; + * // extern const unsigned char *const Foo; + * // extern const unsigned int Foo; + * @endcode + * + * You may specify a custom optional data type as well as the first argument. + * @code + * INCBIN_EXTERN(custom_type, Foo); + * + * // Now you have the following symbols: + * // extern const custom_type Foo[]; + * // extern const custom_type *const Foo; + * // extern const unsigned int Foo; + * @endcode + */ +#define INCBIN_EXTERN(...) \ + INCBIN_CONCATENATE(INCBIN_EXTERN_, INCBIN_VA_ARGC(__VA_ARGS__))(__VA_ARGS__) +#define INCBIN_EXTERN_1(NAME, ...) \ + INCBIN_EXTERN_2(unsigned char, NAME) +#define INCBIN_EXTERN_2(TYPE, NAME) \ + INCBIN_EXTERNAL const INCBIN_ALIGN TYPE \ + INCBIN_CONCATENATE( \ + INCBIN_CONCATENATE(INCBIN_PREFIX, NAME), \ + INCBIN_STYLE_IDENT(DATA))[]; \ + INCBIN_EXTERNAL const INCBIN_ALIGN TYPE *const \ + INCBIN_CONCATENATE( \ + INCBIN_CONCATENATE(INCBIN_PREFIX, NAME), \ + INCBIN_STYLE_IDENT(END)); \ + INCBIN_EXTERNAL const unsigned int \ + INCBIN_CONCATENATE( \ + INCBIN_CONCATENATE(INCBIN_PREFIX, NAME), \ + INCBIN_STYLE_IDENT(SIZE)) + +/** + * @brief Externally reference textual data included in another translation unit. + * + * Produces three external symbols that reference the textual data included in + * another translation unit. + * + * The symbol names are a concatenation of `INCBIN_PREFIX' before *NAME*; with + * "Data", as well as "End" and "Size" after. An example is provided below. + * + * @param NAME The name given for the textual data + * + * @code + * INCBIN_EXTERN(Foo); + * + * // Now you have the following symbols: + * // extern const char Foo[]; + * // extern const char *const Foo; + * // extern const unsigned int Foo; + * @endcode + */ +#define INCTXT_EXTERN(NAME) \ + INCBIN_EXTERN_2(char, NAME) + +/** + * @brief Include a binary file into the current translation unit. + * + * Includes a binary file into the current translation unit, producing three symbols + * for objects that encode the data and size respectively. + * + * The symbol names are a concatenation of `INCBIN_PREFIX' before *NAME*; with + * "Data", as well as "End" and "Size" after. An example is provided below. + * + * @param TYPE Optional array type. Omitting this picks a default of `unsigned char`. + * @param NAME The name to associate with this binary data (as an identifier.) + * @param FILENAME The file to include (as a string literal.) + * + * @code + * INCBIN(Icon, "icon.png"); + * + * // Now you have the following symbols: + * // const unsigned char Icon[]; + * // const unsigned char *const Icon; + * // const unsigned int Icon; + * @endcode + * + * You may specify a custom optional data type as well as the first argument. + * These macros are specialized by arity. + * @code + * INCBIN(custom_type, Icon, "icon.png"); + * + * // Now you have the following symbols: + * // const custom_type Icon[]; + * // const custom_type *const Icon; + * // const unsigned int Icon; + * @endcode + * + * @warning This must be used in global scope + * @warning The identifiers may be different if INCBIN_STYLE is not default + * + * To externally reference the data included by this in another translation unit + * please @see INCBIN_EXTERN. + */ +#ifdef _MSC_VER +# define INCBIN(NAME, FILENAME) \ + INCBIN_EXTERN(NAME) +#else +# define INCBIN(...) \ + INCBIN_CONCATENATE(INCBIN_, INCBIN_VA_ARGC(__VA_ARGS__))(__VA_ARGS__) +# if defined(__GNUC__) +# define INCBIN_1(...) _Pragma("GCC error \"Single argument INCBIN not allowed\"") +# elif defined(__clang__) +# define INCBIN_1(...) _Pragma("clang error \"Single argument INCBIN not allowed\"") +# else +# define INCBIN_1(...) /* Cannot do anything here */ +# endif +# define INCBIN_2(NAME, FILENAME) \ + INCBIN_3(unsigned char, NAME, FILENAME) +# define INCBIN_3(TYPE, NAME, FILENAME) INCBIN_COMMON(TYPE, NAME, FILENAME, /* No terminator for binary data */) +# define INCBIN_COMMON(TYPE, NAME, FILENAME, TERMINATOR) \ + __asm__(INCBIN_SECTION \ + INCBIN_GLOBAL_LABELS(NAME, DATA) \ + INCBIN_ALIGN_HOST \ + INCBIN_MANGLE INCBIN_STRINGIZE(INCBIN_PREFIX) #NAME INCBIN_STYLE_STRING(DATA) ":\n" \ + INCBIN_MACRO " \"" FILENAME "\"\n" \ + TERMINATOR \ + INCBIN_GLOBAL_LABELS(NAME, END) \ + INCBIN_ALIGN_BYTE \ + INCBIN_MANGLE INCBIN_STRINGIZE(INCBIN_PREFIX) #NAME INCBIN_STYLE_STRING(END) ":\n" \ + INCBIN_BYTE "1\n" \ + INCBIN_GLOBAL_LABELS(NAME, SIZE) \ + INCBIN_ALIGN_HOST \ + INCBIN_MANGLE INCBIN_STRINGIZE(INCBIN_PREFIX) #NAME INCBIN_STYLE_STRING(SIZE) ":\n" \ + INCBIN_INT INCBIN_MANGLE INCBIN_STRINGIZE(INCBIN_PREFIX) #NAME INCBIN_STYLE_STRING(END) " - " \ + INCBIN_MANGLE INCBIN_STRINGIZE(INCBIN_PREFIX) #NAME INCBIN_STYLE_STRING(DATA) "\n" \ + INCBIN_ALIGN_HOST \ + ".text\n" \ + ); \ + INCBIN_EXTERN(TYPE, NAME) +#endif + +/** + * @brief Include a textual file into the current translation unit. + * + * This behaves the same as INCBIN except it produces char compatible arrays + * and implicitly adds a null-terminator byte, thus the size of data included + * by this is one byte larger than that of INCBIN. + * + * Includes a textual file into the current translation unit, producing three + * symbols for objects that encode the data and size respectively. + * + * The symbol names are a concatenation of `INCBIN_PREFIX' before *NAME*; with + * "Data", as well as "End" and "Size" after. An example is provided below. + * + * @param NAME The name to associate with this binary data (as an identifier.) + * @param FILENAME The file to include (as a string literal.) + * + * @code + * INCTXT(Readme, "readme.txt"); + * + * // Now you have the following symbols: + * // const char Readme[]; + * // const char *const Readme; + * // const unsigned int Readme; + * @endcode + * + * @warning This must be used in global scope + * @warning The identifiers may be different if INCBIN_STYLE is not default + * + * To externally reference the data included by this in another translation unit + * please @see INCBIN_EXTERN. + */ +#if defined(_MSC_VER) +# define INCTXT(NAME, FILENAME) \ + INCBIN_EXTERN(NAME) +#else +# define INCTXT(NAME, FILENAME) \ + INCBIN_COMMON(char, NAME, FILENAME, INCBIN_BYTE "0\n") +#endif + +#endif diff --git a/src/main.cpp b/src/main.cpp index ffcae92..951e89b 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -27,4 +27,5 @@ int main(int argc, char** argv) UCI::main_loop(ss.str()); pool->kill_threads(); + PSQT::clean(); }