Rev 96 | Rev 169 | Go to most recent revision | Show entire file | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 96 | Rev 154 | ||
---|---|---|---|
Line 19... | Line 19... | ||
19 | */ |
19 | */ |
20 | 20 | ||
21 | #include <algorithm> |
21 | #include <algorithm> |
22 | 22 | ||
23 | #include "bitboard.h" |
23 | #include "bitboard.h" |
24 | #include "bitcount.h" |
- | |
25 | #include "misc.h" |
24 | #include "misc.h" |
26 | 25 | ||
- | 26 | uint8_t PopCnt16[1 << 16]; |
|
27 | int SquareDistance[SQUARE_NB][SQUARE_NB]; |
27 | int SquareDistance[SQUARE_NB][SQUARE_NB]; |
28 | 28 | ||
29 | Bitboard RookMasks [SQUARE_NB]; |
29 | Bitboard RookMasks [SQUARE_NB]; |
30 | Bitboard RookMagics [SQUARE_NB]; |
30 | Bitboard RookMagics [SQUARE_NB]; |
31 | Bitboard* RookAttacks[SQUARE_NB]; |
31 | Bitboard* RookAttacks[SQUARE_NB]; |
Line 71... | Line 71... | ||
71 | 71 | ||
72 | unsigned bsf_index(Bitboard b) { |
72 | unsigned bsf_index(Bitboard b) { |
73 | b ^= b - 1; |
73 | b ^= b - 1; |
74 | return Is64Bit ? (b * DeBruijn64) >> 58 |
74 | return Is64Bit ? (b * DeBruijn64) >> 58 |
75 | : ((unsigned(b) ^ unsigned(b >> 32)) * DeBruijn32) >> 26; |
75 | : ((unsigned(b) ^ unsigned(b >> 32)) * DeBruijn32) >> 26; |
- | 76 | } |
|
- | 77 | ||
- | 78 | ||
- | 79 | // popcount16() counts the non-zero bits using SWAR-Popcount algorithm |
|
- | 80 | ||
- | 81 | unsigned popcount16(unsigned u) { |
|
- | 82 | u -= (u >> 1) & 0x5555U; |
|
- | 83 | u = ((u >> 2) & 0x3333U) + (u & 0x3333U); |
|
- | 84 | u = ((u >> 4) + u) & 0x0F0FU; |
|
- | 85 | return (u * 0x0101U) >> 8; |
|
76 | } |
86 | } |
77 | } |
87 | } |
78 | 88 | ||
79 |
|
89 | #ifdef NO_BSF |
80 | 90 | ||
81 | /// Software fall-back of lsb() and msb() for CPU lacking hardware support |
91 | /// Software fall-back of lsb() and msb() for CPU lacking hardware support |
82 | 92 | ||
83 | Square lsb(Bitboard b) { |
93 | Square lsb(Bitboard b) { |
- | 94 | assert(b); |
|
84 | return BSFTable[bsf_index(b)]; |
95 | return BSFTable[bsf_index(b)]; |
85 | } |
96 | } |
86 | 97 | ||
87 | Square msb(Bitboard b) { |
98 | Square msb(Bitboard b) { |
88 | 99 | ||
- | 100 | assert(b); |
|
89 | unsigned b32; |
101 | unsigned b32; |
90 | int result = 0; |
102 | int result = 0; |
91 | 103 | ||
92 | if (b > 0xFFFFFFFF) |
104 | if (b > 0xFFFFFFFF) |
93 | { |
105 | { |
Line 110... | Line 122... | ||
110 | } |
122 | } |
111 | 123 | ||
112 | return Square(result + MSBTable[b32]); |
124 | return Square(result + MSBTable[b32]); |
113 | } |
125 | } |
114 | 126 | ||
115 | #endif // |
127 | #endif // ifdef NO_BSF |
116 | 128 | ||
117 | 129 | ||
118 | /// Bitboards::pretty() returns an ASCII representation of a bitboard suitable |
130 | /// Bitboards::pretty() returns an ASCII representation of a bitboard suitable |
119 | /// to be printed to standard output. Useful for debugging. |
131 | /// to be printed to standard output. Useful for debugging. |
120 | 132 | ||
Line 136... | Line 148... | ||
136 | 148 | ||
137 | /// Bitboards::init() initializes various bitboard tables. It is called at |
149 | /// Bitboards::init() initializes various bitboard tables. It is called at |
138 | /// startup and relies on global objects to be already zero-initialized. |
150 | /// startup and relies on global objects to be already zero-initialized. |
139 | 151 | ||
140 | void Bitboards::init() { |
152 | void Bitboards::init() { |
- | 153 | ||
- | 154 | for (unsigned i = 0; i < (1 << 16); ++i) |
|
- | 155 | PopCnt16[i] = (uint8_t) popcount16(i); |
|
141 | 156 | ||
142 | for (Square s = SQ_A1; s <= SQ_H8; ++s) |
157 | for (Square s = SQ_A1; s <= SQ_H8; ++s) |
143 | { |
158 | { |
144 | SquareBB[s] = 1ULL << s; |
159 | SquareBB[s] = 1ULL << s; |
145 | BSFTable[bsf_index(SquareBB[s])] = s; |
160 | BSFTable[bsf_index(SquareBB[s])] = s; |
Line 188... | Line 203... | ||
188 | 203 | ||
189 | if (is_ok(to) && distance(s, to) < 3) |
204 | if (is_ok(to) && distance(s, to) < 3) |
190 | StepAttacksBB[make_piece(c, pt)][s] |= to; |
205 | StepAttacksBB[make_piece(c, pt)][s] |= to; |
191 | } |
206 | } |
192 | 207 | ||
193 | Square RookDeltas[] = { |
208 | Square RookDeltas[] = { NORTH, EAST, SOUTH, WEST }; |
194 | Square BishopDeltas[] = { |
209 | Square BishopDeltas[] = { NORTH_EAST, SOUTH_EAST, SOUTH_WEST, NORTH_WEST }; |
195 | 210 | ||
196 | init_magics(RookTable, RookAttacks, RookMagics, RookMasks, RookShifts, RookDeltas, magic_index<ROOK>); |
211 | init_magics(RookTable, RookAttacks, RookMagics, RookMasks, RookShifts, RookDeltas, magic_index<ROOK>); |
197 | init_magics(BishopTable, BishopAttacks, BishopMagics, BishopMasks, BishopShifts, BishopDeltas, magic_index<BISHOP>); |
212 | init_magics(BishopTable, BishopAttacks, BishopMagics, BishopMasks, BishopShifts, BishopDeltas, magic_index<BISHOP>); |
198 | 213 | ||
199 | for (Square s1 = SQ_A1; s1 <= SQ_H8; ++s1) |
214 | for (Square s1 = SQ_A1; s1 <= SQ_H8; ++s1) |
Line 261... | Line 276... | ||
261 | // 's' computed on an empty board. The index must be big enough to contain |
276 | // 's' computed on an empty board. The index must be big enough to contain |
262 | // all the attacks for each possible subset of the mask and so is 2 power |
277 | // all the attacks for each possible subset of the mask and so is 2 power |
263 | // the number of 1s of the mask. Hence we deduce the size of the shift to |
278 | // the number of 1s of the mask. Hence we deduce the size of the shift to |
264 | // apply to the 64 or 32 bits word to get the index. |
279 | // apply to the 64 or 32 bits word to get the index. |
265 | masks[s] = sliding_attack(deltas, s, 0) & ~edges; |
280 | masks[s] = sliding_attack(deltas, s, 0) & ~edges; |
266 | shifts[s] = (Is64Bit ? 64 : 32) - popcount |
281 | shifts[s] = (Is64Bit ? 64 : 32) - popcount(masks[s]); |
267 | 282 | ||
268 | // Use Carry-Rippler trick to enumerate all subsets of masks[s] and |
283 | // Use Carry-Rippler trick to enumerate all subsets of masks[s] and |
269 | // store the corresponding sliding attack bitboard in reference[]. |
284 | // store the corresponding sliding attack bitboard in reference[]. |
270 | b = size = 0; |
285 | b = size = 0; |
271 | do { |
286 | do { |
Line 292... | Line 307... | ||
292 | // Find a magic for square 's' picking up an (almost) random number |
307 | // Find a magic for square 's' picking up an (almost) random number |
293 | // until we find the one that passes the verification test. |
308 | // until we find the one that passes the verification test. |
294 | do { |
309 | do { |
295 | do |
310 | do |
296 | magics[s] = rng.sparse_rand<Bitboard>(); |
311 | magics[s] = rng.sparse_rand<Bitboard>(); |
297 | while (popcount |
312 | while (popcount((magics[s] * masks[s]) >> 56) < 6); |
298 | 313 | ||
299 | // A good magic must map every possible occupancy to an index that |
314 | // A good magic must map every possible occupancy to an index that |
300 | // looks up the correct sliding attack in the attacks[s] database. |
315 | // looks up the correct sliding attack in the attacks[s] database. |
301 | // Note that we build up the database for square 's' as a side |
316 | // Note that we build up the database for square 's' as a side |
302 | // effect of verifying the magic. |
317 | // effect of verifying the magic. |