Rev 169 | Show entire file | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed
| Rev 169 | Rev 185 | ||
|---|---|---|---|
| Line 4... | Line 4... | ||
| 4 | Copyright (C) 2008-2015 Marco Costalba, Joona Kiiski, Tord Romstad |
4 | Copyright (C) 2008-2015 Marco Costalba, Joona Kiiski, Tord Romstad |
| 5 | Copyright (C) 2015- |
5 | Copyright (C) 2015-2019 Marco Costalba, Joona Kiiski, Gary Linscott, Tord Romstad |
| 6 | 6 | ||
| 7 | Stockfish is free software: you can redistribute it and/or modify |
7 | Stockfish is free software: you can redistribute it and/or modify |
| 8 | it under the terms of the GNU General Public License as published by |
8 | it under the terms of the GNU General Public License as published by |
| 9 | the Free Software Foundation, either version 3 of the License, or |
9 | the Free Software Foundation, either version 3 of the License, or |
| 10 | (at your option) any later version. |
10 | (at your option) any later version. |
| Line 78... | Line 78... | ||
| 78 | #else |
78 | #else |
| 79 | # define pext(b, m) 0 |
79 | # define pext(b, m) 0 |
| 80 | #endif |
80 | #endif |
| 81 | 81 | ||
| 82 | #ifdef USE_POPCNT |
82 | #ifdef USE_POPCNT |
| 83 |
|
83 | constexpr bool HasPopCnt = true; |
| 84 | #else |
84 | #else |
| 85 |
|
85 | constexpr bool HasPopCnt = false; |
| 86 | #endif |
86 | #endif |
| 87 | 87 | ||
| 88 | #ifdef USE_PEXT |
88 | #ifdef USE_PEXT |
| 89 |
|
89 | constexpr bool HasPext = true; |
| 90 | #else |
90 | #else |
| 91 |
|
91 | constexpr bool HasPext = false; |
| 92 | #endif |
92 | #endif |
| 93 | 93 | ||
| 94 | #ifdef IS_64BIT |
94 | #ifdef IS_64BIT |
| 95 |
|
95 | constexpr bool Is64Bit = true; |
| 96 | #else |
96 | #else |
| 97 |
|
97 | constexpr bool Is64Bit = false; |
| 98 | #endif |
98 | #endif |
| 99 | 99 | ||
| 100 | typedef uint64_t Key; |
100 | typedef uint64_t Key; |
| 101 | typedef uint64_t Bitboard; |
101 | typedef uint64_t Bitboard; |
| 102 | 102 | ||
| 103 |
|
103 | constexpr int MAX_MOVES = 256; |
| 104 |
|
104 | constexpr int MAX_PLY = 128; |
| 105 | 105 | ||
| 106 | /// A move needs 16 bits to be stored |
106 | /// A move needs 16 bits to be stored |
| 107 | /// |
107 | /// |
| 108 | /// bit 0- 5: destination square (from 0 to 63) |
108 | /// bit 0- 5: destination square (from 0 to 63) |
| 109 | /// bit 6-11: origin square (from 0 to 63) |
109 | /// bit 6-11: origin square (from 0 to 63) |
| Line 141... | Line 141... | ||
| 141 | WHITE_OOO = WHITE_OO << 1, |
141 | WHITE_OOO = WHITE_OO << 1, |
| 142 | BLACK_OO = WHITE_OO << 2, |
142 | BLACK_OO = WHITE_OO << 2, |
| 143 | BLACK_OOO = WHITE_OO << 3, |
143 | BLACK_OOO = WHITE_OO << 3, |
| 144 | ANY_CASTLING = WHITE_OO | WHITE_OOO | BLACK_OO | BLACK_OOO, |
144 | ANY_CASTLING = WHITE_OO | WHITE_OOO | BLACK_OO | BLACK_OOO, |
| 145 | CASTLING_RIGHT_NB = 16 |
145 | CASTLING_RIGHT_NB = 16 |
| 146 | }; |
- | |
| 147 | - | ||
| 148 | template<Color C, CastlingSide S> struct MakeCastling { |
- | |
| 149 | static constexpr CastlingRight |
- | |
| 150 | right = C == WHITE ? S == QUEEN_SIDE ? WHITE_OOO : WHITE_OO |
- | |
| 151 | : S == QUEEN_SIDE ? BLACK_OOO : BLACK_OO; |
- | |
| 152 | }; |
146 | }; |
| 153 | 147 | ||
| 154 | enum Phase { |
148 | enum Phase { |
| 155 | PHASE_ENDGAME, |
149 | PHASE_ENDGAME, |
| 156 | PHASE_MIDGAME = 128, |
150 | PHASE_MIDGAME = 128, |
| 157 | MG = 0, EG = 1, PHASE_NB = 2 |
151 | MG = 0, EG = 1, PHASE_NB = 2 |
| 158 | }; |
152 | }; |
| 159 | 153 | ||
| 160 | enum ScaleFactor { |
154 | enum ScaleFactor { |
| 161 | SCALE_FACTOR_DRAW = 0, |
155 | SCALE_FACTOR_DRAW = 0, |
| 162 | SCALE_FACTOR_ONEPAWN = 48, |
- | |
| 163 | SCALE_FACTOR_NORMAL = 64, |
156 | SCALE_FACTOR_NORMAL = 64, |
| 164 | SCALE_FACTOR_MAX = 128, |
157 | SCALE_FACTOR_MAX = 128, |
| 165 | SCALE_FACTOR_NONE = 255 |
158 | SCALE_FACTOR_NONE = 255 |
| 166 | }; |
159 | }; |
| 167 | 160 | ||
| Line 181... | Line 174... | ||
| 181 | VALUE_NONE = 32002, |
174 | VALUE_NONE = 32002, |
| 182 | 175 | ||
| 183 | VALUE_MATE_IN_MAX_PLY = VALUE_MATE - 2 * MAX_PLY, |
176 | VALUE_MATE_IN_MAX_PLY = VALUE_MATE - 2 * MAX_PLY, |
| 184 | VALUE_MATED_IN_MAX_PLY = -VALUE_MATE + 2 * MAX_PLY, |
177 | VALUE_MATED_IN_MAX_PLY = -VALUE_MATE + 2 * MAX_PLY, |
| 185 | 178 | ||
| 186 | PawnValueMg = |
179 | PawnValueMg = 136, PawnValueEg = 208, |
| 187 | KnightValueMg = |
180 | KnightValueMg = 782, KnightValueEg = 865, |
| 188 | BishopValueMg = |
181 | BishopValueMg = 830, BishopValueEg = 918, |
| 189 | RookValueMg = |
182 | RookValueMg = 1289, RookValueEg = 1378, |
| 190 | QueenValueMg = |
183 | QueenValueMg = 2529, QueenValueEg = 2687, |
| 191 | 184 | ||
| 192 | MidgameLimit = 15258, EndgameLimit = 3915 |
185 | MidgameLimit = 15258, EndgameLimit = 3915 |
| 193 | }; |
186 | }; |
| 194 | 187 | ||
| 195 | enum PieceType { |
188 | enum PieceType { |
| 196 | NO_PIECE_TYPE, PAWN, KNIGHT, BISHOP, ROOK, QUEEN, KING, |
189 | NO_PIECE_TYPE, PAWN, KNIGHT, BISHOP, ROOK, QUEEN, KING, |
| 197 | ALL_PIECES = 0, |
190 | ALL_PIECES = 0, |
| 198 | QUEEN_DIAGONAL = 7, |
- | |
| 199 | PIECE_TYPE_NB = 8 |
191 | PIECE_TYPE_NB = 8 |
| 200 | }; |
192 | }; |
| 201 | 193 | ||
| 202 | enum Piece { |
194 | enum Piece { |
| 203 | NO_PIECE, |
195 | NO_PIECE, |
| Line 256... | Line 248... | ||
| 256 | enum Rank : int { |
248 | enum Rank : int { |
| 257 | RANK_1, RANK_2, RANK_3, RANK_4, RANK_5, RANK_6, RANK_7, RANK_8, RANK_NB |
249 | RANK_1, RANK_2, RANK_3, RANK_4, RANK_5, RANK_6, RANK_7, RANK_8, RANK_NB |
| 258 | }; |
250 | }; |
| 259 | 251 | ||
| 260 | 252 | ||
| 261 | /// Score enum stores a middlegame and an endgame value in a single integer |
253 | /// Score enum stores a middlegame and an endgame value in a single integer (enum). |
| 262 | /// |
254 | /// The least significant 16 bits are used to store the middlegame value and the |
| 263 | /// |
255 | /// upper 16 bits are used to store the endgame value. We have to take care to |
| 264 | /// |
256 | /// avoid left-shifting a signed int to avoid undefined behavior. |
| 265 | enum Score : int { SCORE_ZERO }; |
257 | enum Score : int { SCORE_ZERO }; |
| 266 | 258 | ||
| 267 | constexpr Score make_score(int mg, int eg) { |
259 | constexpr Score make_score(int mg, int eg) { |
| 268 | return Score((int)((unsigned int)eg << 16) + mg); |
260 | return Score((int)((unsigned int)eg << 16) + mg); |
| 269 | } |
261 | } |
| Line 324... | Line 316... | ||
| 324 | constexpr Value operator-(Value v, int i) { return Value(int(v) - i); } |
316 | constexpr Value operator-(Value v, int i) { return Value(int(v) - i); } |
| 325 | inline Value& operator+=(Value& v, int i) { return v = v + i; } |
317 | inline Value& operator+=(Value& v, int i) { return v = v + i; } |
| 326 | inline Value& operator-=(Value& v, int i) { return v = v - i; } |
318 | inline Value& operator-=(Value& v, int i) { return v = v - i; } |
| 327 | 319 | ||
| 328 | /// Additional operators to add a Direction to a Square |
320 | /// Additional operators to add a Direction to a Square |
| 329 |
|
321 | constexpr Square operator+(Square s, Direction d) { return Square(int(s) + int(d)); } |
| 330 |
|
322 | constexpr Square operator-(Square s, Direction d) { return Square(int(s) - int(d)); } |
| 331 | inline Square& operator+=(Square |
323 | inline Square& operator+=(Square& s, Direction d) { return s = s + d; } |
| 332 | inline Square& operator-=(Square |
324 | inline Square& operator-=(Square& s, Direction d) { return s = s - d; } |
| 333 | 325 | ||
| 334 | /// Only declared but not defined. We don't want to multiply two scores due to |
326 | /// Only declared but not defined. We don't want to multiply two scores due to |
| 335 | /// a very high risk of overflow. So user should explicitly convert to integer. |
327 | /// a very high risk of overflow. So user should explicitly convert to integer. |
| 336 | Score operator*(Score, Score) = delete; |
328 | Score operator*(Score, Score) = delete; |
| 337 | 329 | ||
| Line 345... | Line 337... | ||
| 345 | 337 | ||
| 346 | Score result = Score(int(s) * i); |
338 | Score result = Score(int(s) * i); |
| 347 | 339 | ||
| 348 | assert(eg_value(result) == (i * eg_value(s))); |
340 | assert(eg_value(result) == (i * eg_value(s))); |
| 349 | assert(mg_value(result) == (i * mg_value(s))); |
341 | assert(mg_value(result) == (i * mg_value(s))); |
| 350 | assert((i == 0) || (result / i) == s |
342 | assert((i == 0) || (result / i) == s); |
| 351 | 343 | ||
| 352 | return result; |
344 | return result; |
| 353 | } |
345 | } |
| 354 | 346 | ||
| 355 | constexpr Color operator~(Color c) { |
347 | constexpr Color operator~(Color c) { |
| Line 448... | Line 440... | ||
| 448 | 440 | ||
| 449 | constexpr PieceType promotion_type(Move m) { |
441 | constexpr PieceType promotion_type(Move m) { |
| 450 | return PieceType(((m >> 12) & 3) + KNIGHT); |
442 | return PieceType(((m >> 12) & 3) + KNIGHT); |
| 451 | } |
443 | } |
| 452 | 444 | ||
| 453 |
|
445 | constexpr Move make_move(Square from, Square to) { |
| 454 | return Move((from << 6) + to); |
446 | return Move((from << 6) + to); |
| 455 | } |
447 | } |
| 456 | 448 | ||
| 457 | template<MoveType T> |
449 | template<MoveType T> |
| 458 | constexpr Move make(Square from, Square to, PieceType pt = KNIGHT) { |
450 | constexpr Move make(Square from, Square to, PieceType pt = KNIGHT) { |