From 98c54553d06ff79ee8720b1e0a81f4477f38f3d9 Mon Sep 17 00:00:00 2001 From: Bruno Raoult Date: Mon, 22 Jul 2024 18:16:14 +0200 Subject: [PATCH] Combo changes - move eval_material to eval-simple.c - move phase_t to eval.h - init.c: add eval init - piece.h: add piece_midval/piece_endval - fen.c: add phase calculation - eval-simple: fix calc_phase --- Makefile | 2 +- src/alloc.c | 2 +- src/chessdefs.h | 8 ----- src/eval-simple.c | 84 +++++++++++++++++++++++++++++++---------------- src/eval-simple.h | 18 ++++++++-- src/eval.c | 28 +++------------- src/eval.h | 12 +++++-- src/fen.c | 2 ++ src/init.c | 4 +-- src/piece.h | 7 +++- 10 files changed, 98 insertions(+), 69 deletions(-) diff --git a/Makefile b/Makefile index 797be0f..03ba8b4 100644 --- a/Makefile +++ b/Makefile @@ -130,7 +130,7 @@ else # ifeq ($(build),dev) #CPPFLAGS += -DDEBUG_ATTACK_ATTACKERS # sq_attackers #CPPFLAGS += -DDEBUG_ATTACK_PINNERS # sq_pinners details # eval.c eval-simple.c - CPPFLAGS += -DEVAL # eval + CPPFLAGS += -DDEBUG_EVAL # eval # old unused flags #CPPFLAGS += -DDEBUG_POS # position.c diff --git a/src/alloc.c b/src/alloc.c index bb90e3d..7128267 100644 --- a/src/alloc.c +++ b/src/alloc.c @@ -88,7 +88,7 @@ void *alloc_aligned_hugepage(size_t size) /* round size (up) to alignment */ size_t rounded = (size + PAGE_SIZE - 1) & -PAGE_SIZE; void *mem = alloc_aligned(PAGE_SIZE, rounded); - printf("size=%zu rounded=%zu\n", size, rounded); + //printf("size=%zu rounded=%zu\n", size, rounded); //void *mem = aligned_alloc(HUGE_PAGE_SIZE, size); if (mem) { if (madvise(mem, rounded, MADV_HUGEPAGE | MADV_RANDOM)) diff --git a/src/chessdefs.h b/src/chessdefs.h index ca6abc8..ecd4805 100644 --- a/src/chessdefs.h +++ b/src/chessdefs.h @@ -79,14 +79,6 @@ typedef enum { #define clr_ooo(f, c) ((f) & ~(CASTLE_Q << (2 * (c)))) #define clr_castle(f, c) ((f) & ~(CASTLE_KQ << (2 * (c)) )) -/* game phases - */ -typedef enum { - MIDGAME, - ENDGAME, - PHASE_NB -} phase_t; - /* forward defs */ typedef struct __pos_s pos_t; typedef struct __movelist_s movelist_t; diff --git a/src/eval-simple.c b/src/eval-simple.c index 54c49b3..116705d 100644 --- a/src/eval-simple.c +++ b/src/eval-simple.c @@ -12,11 +12,13 @@ */ #include +#include #include "chessdefs.h" #include "piece.h" #include "position.h" #include "eval-simple.h" +#include "eval.h" /* * Piece-square tables. For easier reading, they are defined for black side: @@ -463,29 +465,31 @@ int pc_sq_eg[COLOR_NB][PT_NB][SQUARE_NB]; /* phase calculation from Fruit: * https://github.com/Warpten/Fruit-2.1 */ -int phase; -static u16 piece_phase[] = { 0, 1, 1, 2, 4, 0 }; -static const int p_phase = 0; -static const int n_phase = 1; -static const int b_phase = 1; -static const int r_phase = 2; -static const int q_phase = 4; - -static const int total_phase = p_phase * 16 + n_phase * 4 + - b_phase * 4 + r_phase * 4 + q_phase * 2; - -int calc_phase(pos_t *pos) +/** + * calc_phase - calculate position phase + * @pos: &position + * + * This function should be calculated when a new position is setup, or as + * a verification of an incremental one. + * phase is clamped between 0 (opening) and 24 (ending). + * + * @return: + */ +s16 calc_phase(pos_t *pos) { - phase = total_phase; - phase -= p_phase * popcount64(pos->bb[WHITE][PAWN] | pos->bb[BLACK][PAWN]); - phase -= n_phase * popcount64(pos->bb[WHITE][KNIGHT] | pos->bb[BLACK][KNIGHT]); - phase -= b_phase * popcount64(pos->bb[WHITE][BISHOP] | pos->bb[BLACK][BISHOP]); - phase -= r_phase * popcount64(pos->bb[WHITE][ROOK] | pos->bb[BLACK][ROOK]); - phase -= q_phase * popcount64(pos->bb[WHITE][QUEEN] | pos->bb[BLACK][QUEEN]); + int phase = ALL_PHASE; + phase -= P_PHASE * popcount64(pos->bb[WHITE][PAWN] | pos->bb[BLACK][PAWN]); + phase -= N_PHASE * popcount64(pos->bb[WHITE][KNIGHT] | pos->bb[BLACK][KNIGHT]); + phase -= B_PHASE * popcount64(pos->bb[WHITE][BISHOP] | pos->bb[BLACK][BISHOP]); + phase -= R_PHASE * popcount64(pos->bb[WHITE][ROOK] | pos->bb[BLACK][ROOK]); + phase -= Q_PHASE * popcount64(pos->bb[WHITE][QUEEN] | pos->bb[BLACK][QUEEN]); - phase = max(phase, 0); - return (phase * 256 + (total_phase / 2)) / total_phase; + phase = clamp(phase, 0, ALL_PHASE); +# ifdef DEBUG_EVAL + printf("calc phase:%d\n", phase); +# endif + return phase; } int eval_simple_find(char *str) @@ -514,14 +518,42 @@ void eval_simple_set(int set) } } -void eval_simple_init(void) +void eval_simple_init(char *set) { + int n = eval_simple_find(set); # ifdef DEBUG_EVAL - printf("initializing eval_simple\n"); + printf("initializing eval_simple with set=%s: found=%d\n", set, n); # endif + + if (n >= 0) + pc_sq_current = n; eval_simple_set(pc_sq_current); } +/** + * eval_material() - eval position material + * @pos: &position to evaluate + * + * Basic material evaluation. Only midgame value is used. + * + * @return: the @pos material evaluation in centipawns + */ +eval_t eval_material(pos_t *pos) +{ + eval_t val[COLOR_NB] = { 0 }; + + for (piece_type_t pt = PAWN; pt < KING; ++pt) { + eval_t pval = piece_midval(pt); + val[WHITE] += popcount64(pos->bb[WHITE][pt]) * pval; + val[BLACK] += popcount64(pos->bb[BLACK][pt]) * pval; + } +# ifdef DEBUG_EVAL + printf("material: w:%d b:%d\n", val[WHITE], val[BLACK]); +# endif + + return val[WHITE] - val[BLACK]; +} + /** * eval_simple() - simple and fast position evaluation * @pos: &position to evaluate @@ -539,9 +571,6 @@ eval_t eval_simple(pos_t *pos) //struct pc_sq = sq_ int (*gg)[6 + 2][64] = eg? pc_sq_eg: pc_sq_mg; //pos->eval_simple_phase = ENDGAME; -# ifdef DEBUG_EVAL - log_f(5, "phase = %d\n", eg? "endgame": "midgame"); -# endif for (color_t color = WHITE; color < COLOR_NB; ++color) { mg_eval[color] = 0; @@ -555,8 +584,7 @@ eval_t eval_simple(pos_t *pos) } # ifdef DEBUG_EVAL - printf("c=%d p=%d mg=%ld eg=%ld\n", color, pt, - popcount64(pos->bb[color][pt]), + printf("c=%d pt=%d mg=%d eg=%d\n", color, pt, mg_eval[color], eg_eval[color]); # endif @@ -564,7 +592,7 @@ eval_t eval_simple(pos_t *pos) } # ifdef DEBUG_EVAL printf("phase:%d mg[WHITE]:%d mg[BLACK]:%d eg[WHITE]:%d eg[BLACK]:%d\n", - mg_eval[WHITE], mg_eval[BLACK], eg_eval[WHITE], eg_eval[BLACK]); + pos->phase, mg_eval[WHITE], mg_eval[BLACK], eg_eval[WHITE], eg_eval[BLACK]); # endif return eval[WHITE] - eval[BLACK]; diff --git a/src/eval-simple.h b/src/eval-simple.h index ecb1ad2..a833605 100644 --- a/src/eval-simple.h +++ b/src/eval-simple.h @@ -17,12 +17,24 @@ #include "chessdefs.h" #include "piece.h" +#include "eval.h" struct pc_sq { char *name; /* one word only, no spaces */ int val[PIECE_TYPE_NB][PHASE_NB][SQUARE_NB]; /* MG then EG */ }; +/* pieces weight in phase calculation. + */ +enum { + P_PHASE = 0, + N_PHASE = 1, + B_PHASE = 1, + R_PHASE = 2, + Q_PHASE = 4, + ALL_PHASE = P_PHASE*16 + N_PHASE*4 + B_PHASE*4 + R_PHASE*4 + Q_PHASE*2 +}; + /** * pc_sq - pre-defined piece-square tables. */ @@ -57,10 +69,12 @@ extern int pc_sq_eg[COLOR_NB][PT_NB][SQUARE_NB]; simple_no_rook(p, BLACK) && \ simple_one_minor_piece(p, BLACK))) ) -int calc_phase(pos_t *pos); +s16 calc_phase(pos_t *pos); int eval_simple_find(char *str); void eval_simple_set(int set); -void eval_simple_init(void); +void eval_simple_init(char *set); + +eval_t eval_material(pos_t *pos); eval_t eval_simple(pos_t *pos); #endif /* EVAL_SIMPLE_H */ diff --git a/src/eval.c b/src/eval.c index 3a47ae0..832d79d 100644 --- a/src/eval.c +++ b/src/eval.c @@ -20,26 +20,6 @@ #include "eval.h" #include "eval-simple.h" -inline eval_t eval_material(pos_t *pos, bool color) -{ - eval_t res = 0; - - /* I need to do something about the king, if it can be potentially taken - * if pseudo-moves include a pinned piece on King. - */ - for (piece_type_t pt = PAWN; pt < KING; ++pt) { -# ifdef DEBUG_EVAL - log_f(2, "color=%u piece=%u bb=%u=%c count=%ul val=%ld\n", - color, piece, bb, P_LETTER(piece), popcount64(pos->bb[color][bb]), - P_VALUE(piece)); -# endif - res += popcount64(pos->bb[color][pt]) * piece_val(pt); - } - return res; -} - - - /* * inline eval_t eval_mobility(pos_t *pos, bool color) * { @@ -66,7 +46,7 @@ eval_t eval(pos_t *pos) //material[BLACK] = eval_material(pos, BLACK); simple = eval_simple(pos); -# ifdef DEBUG_EVAL +# ifdef DEBUG_EVAL2 log_f(2, "eval_simple=%d\n", simple); # endif @@ -74,7 +54,7 @@ eval_t eval(pos_t *pos) //control[WHITE] = eval_square_control(pos, WHITE); //control[BLACK] = eval_square_control(pos, BLACK); -# ifdef DEBUG_EVAL +# ifdef DEBUG_EVAL2 log_f(2, "square control: W:%d B:%d diff=%d\n", control[WHITE], control[BLACK], (control[WHITE] - control[BLACK]) * 10); @@ -82,7 +62,7 @@ eval_t eval(pos_t *pos) /* 3) mobility: 10 mobility diff = 1 pawn */ -# ifdef DEBUG_EVAL +# ifdef DEBUG_EVAL2 log_f(2, "mobility: W:%u B:%u diff=%d\n", pos->mobility[WHITE], pos->mobility[BLACK], (pos->mobility[WHITE] - pos->mobility[BLACK]) * 10); @@ -91,7 +71,7 @@ eval_t eval(pos_t *pos) //eval_t res = simple + // (control[WHITE] - control[BLACK]) * 10 + // (pos->mobility[WHITE] - pos->mobility[BLACK]) * 10; -# ifdef DEBUG_EVAL +# ifdef DEBUG_EVAL2 log_f(2, "eval: %d\n", res); # endif pos->eval = simple; diff --git a/src/eval.h b/src/eval.h index 77f6f79..e6b45ee 100644 --- a/src/eval.h +++ b/src/eval.h @@ -18,8 +18,17 @@ #include "chessdefs.h" +/* game phases + */ +enum { + MIDGAME, + ENDGAME, + PHASE_NB +}; +typedef s16 phase_t; + /* max pieces eval is 9*QUEEN_VALUE + 2*ROOK_VALUE + 2*BISHOP_VALUE - * + 2*KNIGHT_VALUE which is (for a pawn valued at 100) well less than 10,000. + * + 2*KNIGHT_VALUE which is (for a pawn valued at 100) well less than 15,000. */ #define EVAL_MAX (SHRT_MAX) /* 32767 */ #define EVAL_MIN (-EVAL_MAX) @@ -28,7 +37,6 @@ #define EVAL_MATE 30000 -eval_t eval_material(pos_t *pos, bool color); eval_t eval_mobility(pos_t *pos, bool color); eval_t eval_square_control(pos_t *pos, bool color); diff --git a/src/fen.c b/src/fen.c index ef4ae6b..403e6c2 100644 --- a/src/fen.c +++ b/src/fen.c @@ -23,6 +23,7 @@ #include "chessdefs.h" #include "alloc.h" #include "position.h" +#include "eval-simple.h" #include "fen.h" /* FEN description: @@ -258,6 +259,7 @@ end: return NULL; /* invalid position: ignored */ tmppos.key = zobrist_calc(&tmppos); + tmppos.phase = calc_phase(&tmppos); if (!pos) pos = pos_new(); pos_copy(&tmppos, pos); diff --git a/src/init.c b/src/init.c index adb0411..4c06d81 100644 --- a/src/init.c +++ b/src/init.c @@ -49,12 +49,12 @@ void init_all(void) printff("zobrist tables... "); zobrist_init(); - printff("transposition tables... "); + printff("hash tables... "); tt_create(HASH_SIZE_DEFAULT); /* eval tables */ printf("eval data... "); - eval_simple_init(); + eval_simple_init("cpw"); printf("done.\n"); } diff --git a/src/piece.h b/src/piece.h index ec0c76c..2765853 100644 --- a/src/piece.h +++ b/src/piece.h @@ -103,10 +103,15 @@ extern const char pieces_str[6+6+1]; /* to search from fen/user inp #define SET_BLACK(p) (piece_t)((p) |= MASK_COLOR) #define SET_COLOR(p, c) (piece_t)(!(c)? SET_WHITE(p): SET_BLACK(p)) -static __inline s16 piece_val(piece_type_t pt) +static __inline s16 piece_midval(piece_type_t pt) { return piece_details[pt].mid_value; } +static __inline s16 piece_endval(piece_type_t pt) +{ + return piece_details[pt].mid_value; +} +#define piece_val(pt) piece_midval(pt) bool piece_ok(piece_t p);