1 /* 2 * tbprobe.h 3 * (C) 2015 basil, all rights reserved, 4 * 5 * Permission is hereby granted, free of charge, to any person obtaining a 6 * copy of this software and associated documentation files (the "Software"), 7 * to deal in the Software without restriction, including without limitation 8 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 9 * and/or sell copies of the Software, and to permit persons to whom the 10 * Software is furnished to do so, subject to the following conditions: 11 * 12 * The above copyright notice and this permission notice shall be included in 13 * all copies or substantial portions of the Software. 14 * 15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 21 * DEALINGS IN THE SOFTWARE. 22 */ 23 24 #ifndef TBPROBE_H 25 # define TBPROBE_H 26 27 # include "tbconfig.h" 28 29 # ifdef __cplusplus 30 extern "C" { 31 # endif 32 33 # ifndef TB_NO_STDINT 34 # include <stdint.h> 35 # else 36 typedef unsigned char uint8_t; 37 typedef unsigned short uint16_t; 38 typedef unsigned uint32_t; 39 typedef long long unsigned uint64_t; 40 typedef char int8_t; 41 typedef short int16_t; 42 typedef int int32_t; 43 typedef long long int64_t; 44 # endif 45 46 # ifndef TB_NO_STDBOOL 47 # include <stdbool.h> 48 # else 49 # ifndef __cplusplus 50 typedef uint8_t bool; 51 # define true 1 52 # define false 0 53 # endif 54 # endif 55 56 /* 57 * Internal definitions. Do not call these functions directly. 58 */ 59 extern bool tb_init_impl(const char *_path); 60 extern unsigned tb_probe_wdl_impl(uint64_t _white, uint64_t _black, 61 uint64_t _kings, uint64_t _queens, uint64_t _rooks, uint64_t _bishops, 62 uint64_t _knights, uint64_t _pawns, unsigned _ep, bool _turn, 63 uint64_t _hash); 64 extern unsigned tb_probe_root_impl(uint64_t _white, uint64_t _black, 65 uint64_t _kings, uint64_t _queens, uint64_t _rooks, uint64_t _bishops, 66 uint64_t _knights, uint64_t _pawns, unsigned _rule50, unsigned _ep, 67 bool _turn, unsigned *_results); 68 69 /****************************************************************************/ 70 /* MAIN API */ 71 /****************************************************************************/ 72 73 # define TB_MAX_MOVES (192+1) 74 75 # define TB_CASTLING_K 0x1 76 /* White king-side. */ 77 # define TB_CASTLING_Q 0x2 78 /* White queen-side. */ 79 # define TB_CASTLING_k 0x4 80 /* Black king-side. */ 81 # define TB_CASTLING_q 0x8 82 /* Black queen-side. */ 83 84 # define TB_LOSS 0 85 /* LOSS */ 86 # define TB_BLESSED_LOSS 1 87 /* LOSS but 50-move draw */ 88 # define TB_DRAW 2 89 /* DRAW */ 90 # define TB_CURSED_WIN 3 91 /* WIN but 50-move draw */ 92 # define TB_WIN 4 93 /* WIN */ 94 95 # define TB_PROMOTES_NONE 0 96 # define TB_PROMOTES_QUEEN 1 97 # define TB_PROMOTES_ROOK 2 98 # define TB_PROMOTES_BISHOP 3 99 # define TB_PROMOTES_KNIGHT 4 100 101 # define TB_RESULT_WDL_MASK 0x0000000F 102 # define TB_RESULT_TO_MASK 0x000003F0 103 # define TB_RESULT_FROM_MASK 0x0000FC00 104 # define TB_RESULT_PROMOTES_MASK 0x00070000 105 # define TB_RESULT_EP_MASK 0x00080000 106 # define TB_RESULT_DTZ_MASK 0xFFF00000 107 # define TB_RESULT_WDL_SHIFT 0 108 # define TB_RESULT_TO_SHIFT 4 109 # define TB_RESULT_FROM_SHIFT 10 110 # define TB_RESULT_PROMOTES_SHIFT 16 111 # define TB_RESULT_EP_SHIFT 19 112 # define TB_RESULT_DTZ_SHIFT 20 113 114 # define TB_GET_WDL(_res) \ 115 (((_res) & TB_RESULT_WDL_MASK) >> TB_RESULT_WDL_SHIFT) 116 # define TB_GET_TO(_res) \ 117 (((_res) & TB_RESULT_TO_MASK) >> TB_RESULT_TO_SHIFT) 118 # define TB_GET_FROM(_res) \ 119 (((_res) & TB_RESULT_FROM_MASK) >> TB_RESULT_FROM_SHIFT) 120 # define TB_GET_PROMOTES(_res) \ 121 (((_res) & TB_RESULT_PROMOTES_MASK) >> TB_RESULT_PROMOTES_SHIFT) 122 # define TB_GET_EP(_res) \ 123 (((_res) & TB_RESULT_EP_MASK) >> TB_RESULT_EP_SHIFT) 124 # define TB_GET_DTZ(_res) \ 125 (((_res) & TB_RESULT_DTZ_MASK) >> TB_RESULT_DTZ_SHIFT) 126 127 # define TB_SET_WDL(_res, _wdl) \ 128 (((_res) & ~TB_RESULT_WDL_MASK) | \ 129 (((_wdl) << TB_RESULT_WDL_SHIFT) & TB_RESULT_WDL_MASK)) 130 # define TB_SET_TO(_res, _to) \ 131 (((_res) & ~TB_RESULT_TO_MASK) | \ 132 (((_to) << TB_RESULT_TO_SHIFT) & TB_RESULT_TO_MASK)) 133 # define TB_SET_FROM(_res, _from) \ 134 (((_res) & ~TB_RESULT_FROM_MASK) | \ 135 (((_from) << TB_RESULT_FROM_SHIFT) & TB_RESULT_FROM_MASK)) 136 # define TB_SET_PROMOTES(_res, _promotes) \ 137 (((_res) & ~TB_RESULT_PROMOTES_MASK) | \ 138 (((_promotes) << TB_RESULT_PROMOTES_SHIFT) & TB_RESULT_PROMOTES_MASK)) 139 # define TB_SET_EP(_res, _ep) \ 140 (((_res) & ~TB_RESULT_EP_MASK) | \ 141 (((_ep) << TB_RESULT_EP_SHIFT) & TB_RESULT_EP_MASK)) 142 # define TB_SET_DTZ(_res, _dtz) \ 143 (((_res) & ~TB_RESULT_DTZ_MASK) | \ 144 (((_dtz) << TB_RESULT_DTZ_SHIFT) & TB_RESULT_DTZ_MASK)) 145 146 # define TB_RESULT_CHECKMATE TB_SET_WDL(0, TB_WIN) 147 # define TB_RESULT_STALEMATE TB_SET_WDL(0, TB_DRAW) 148 # define TB_RESULT_FAILED 0xFFFFFFFF 149 150 /* 151 * The tablebase can be probed for any position where #pieces <= TB_LARGEST. 152 */ 153 extern unsigned TB_LARGEST; 154 155 /* 156 * Initialize the tablebase. 157 * 158 * PARAMETERS: 159 * - path: 160 * The tablebase PATH string. 161 * 162 * RETURN: 163 * - true=succes, false=failed. The TB_LARGEST global will also be 164 * initialized. If no tablebase files are found, then `true' is returned 165 * and TB_LARGEST is set to zero. 166 */ tb_init(const char * _path)167 static inline bool tb_init(const char *_path) { 168 return tb_init_impl(_path); 169 } 170 /* 171 * Probe the Win-Draw-Loss (WDL) table. 172 * 173 * PARAMETERS: 174 * - white, black, kings, queens, rooks, bishops, knights, pawns: 175 * The current position (bitboards). 176 * - rule50: 177 * The 50-move half-move clock. 178 * - castling: 179 * Castling rights. Set to zero if no castling is possible. 180 * - ep: 181 * The en passant square (if exists). Set to zero if there is no en passant 182 * square. 183 * - turn: 184 * true=white, false=black 185 * 186 * RETURN: 187 * - One of {TB_LOSS, TB_BLESSED_LOSS, TB_DRAW, TB_CURSED_WIN, TB_WIN}. 188 * Otherwise returns TB_RESULT_FAILED if the probe failed. 189 * 190 * NOTES: 191 * - Engines should use this function during search. 192 * - This function is thread safe assuming TB_NO_THREADS is disabled. tb_probe_wdl(uint64_t _white,uint64_t _black,uint64_t _kings,uint64_t _queens,uint64_t _rooks,uint64_t _bishops,uint64_t _knights,uint64_t _pawns,unsigned _rule50,unsigned _castling,unsigned _ep,bool _turn,uint64_t _hash)193 */ static inline unsigned tb_probe_wdl( 194 uint64_t _white, uint64_t _black, uint64_t _kings, uint64_t _queens, 195 uint64_t _rooks, uint64_t _bishops, uint64_t _knights, uint64_t _pawns, 196 unsigned _rule50, unsigned _castling, unsigned _ep, bool _turn, 197 uint64_t _hash) { 198 if (_castling != 0) 199 return TB_RESULT_FAILED; 200 if (_rule50 != 0) 201 return TB_RESULT_FAILED; 202 return tb_probe_wdl_impl(_white, _black, _kings, _queens, _rooks, 203 _bishops, _knights, _pawns, _ep, _turn, _hash); 204 } 205 206 /* 207 * Probe the Distance-To-Zero (DTZ) table. 208 * 209 * PARAMETERS: 210 * - white, black, kings, queens, rooks, bishops, knights, pawns: 211 * The current position (bitboards). 212 * - rule50: 213 * The 50-move half-move clock. 214 * - castling: 215 * Castling rights. Set to zero if no castling is possible. 216 * - ep: 217 * The en passant square (if exists). Set to zero if there is no en passant 218 * square. 219 * - turn: 220 * true=white, false=black 221 * - results (OPTIONAL): 222 * Alternative results, one for each possible legal move. The passed array 223 * must be TB_MAX_MOVES in size. 224 * If alternative results are not desired then set results=NULL. 225 * 226 * RETURN: 227 * - A TB_RESULT value comprising: 228 * 1) The WDL value (TB_GET_WDL) 229 * 2) The suggested move (TB_GET_FROM, TB_GET_TO, TB_GET_PROMOTES, TB_GET_EP) 230 * 3) The DTZ value (TB_GET_DTZ) 231 * The suggested move is guaranteed to preserved the WDL value. 232 * 233 * Otherwise: 234 * 1) TB_RESULT_STALEMATE is returned if the position is in stalemate. 235 * 2) TB_RESULT_CHECKMATE is returned if the position is in checkmate. 236 * 3) TB_RESULT_FAILED is returned if the probe failed. 237 * 238 * If results!=NULL, then a TB_RESULT for each legal move will be generated 239 * and stored in the results array. The results array will be terminated 240 * by TB_RESULT_FAILED. 241 * 242 * NOTES: 243 * - Engines can use this function to probe at the root. This function should 244 * not be used during search. 245 * - DTZ tablebases can suggest unnatural moves, especially for losing 246 * positions. Engines may prefer to traditional search combined with WDL 247 * move filtering using the alternative results array. 248 * - This function is NOT thread safe. For engines this function should only 249 * be called once at the root per search. 250 */ tb_probe_root(uint64_t _white,uint64_t _black,uint64_t _kings,uint64_t _queens,uint64_t _rooks,uint64_t _bishops,uint64_t _knights,uint64_t _pawns,unsigned _rule50,unsigned _castling,unsigned _ep,bool _turn,unsigned * _results)251 static inline unsigned tb_probe_root(uint64_t _white, uint64_t _black, 252 uint64_t _kings, uint64_t _queens, uint64_t _rooks, uint64_t _bishops, 253 uint64_t _knights, uint64_t _pawns, unsigned _rule50, 254 unsigned _castling, unsigned _ep, bool _turn, unsigned *_results) { 255 if (_castling != 0) 256 return TB_RESULT_FAILED; 257 return tb_probe_root_impl(_white, _black, _kings, _queens, _rooks, 258 _bishops, _knights, _pawns, _rule50, _ep, _turn, _results); 259 } 260 261 /****************************************************************************/ 262 /* HELPER API */ 263 /****************************************************************************/ 264 265 /* 266 * The HELPER API provides some useful additional functions. It is optional 267 * and can be disabled by defining TB_NO_HELPER_API. Engines should disable 268 * the HELPER API. 269 */ 270 271 # ifndef TB_NO_HELPER_API 272 273 extern unsigned tb_pop_count(uint64_t _bb); 274 extern unsigned tb_lsb(uint64_t _bb); 275 extern uint64_t tb_pop_lsb(uint64_t _bb); 276 extern uint64_t tb_king_attacks(unsigned _square); 277 extern uint64_t tb_queen_attacks(unsigned _square, uint64_t _occ); 278 extern uint64_t tb_rook_attacks(unsigned _square, uint64_t _occ); 279 extern uint64_t tb_bishop_attacks(unsigned _square, uint64_t _occ); 280 extern uint64_t tb_knight_attacks(unsigned _square); 281 extern uint64_t tb_pawn_attacks(unsigned _square, bool _color); 282 283 # endif 284 285 # ifdef __cplusplus 286 } 287 # endif 288 289 #endif 290