Remove white/black_pawn_attacks()
[stockfish] / src / position.cpp
1 /*
2   Glaurung, a UCI chess playing engine.
3   Copyright (C) 2004-2008 Tord Romstad
4
5   Glaurung is free software: you can redistribute it and/or modify
6   it under the terms of the GNU General Public License as published by
7   the Free Software Foundation, either version 3 of the License, or
8   (at your option) any later version.
9
10   Glaurung is distributed in the hope that it will be useful,
11   but WITHOUT ANY WARRANTY; without even the implied warranty of
12   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13   GNU General Public License for more details.
14
15   You should have received a copy of the GNU General Public License
16   along with this program.  If not, see <http://www.gnu.org/licenses/>.
17 */
18
19
20 ////
21 //// Includes
22 ////
23
24 #include <cassert>
25 #include <iostream>
26 #include <fstream>
27
28 #include "mersenne.h"
29 #include "movegen.h"
30 #include "movepick.h"
31 #include "position.h"
32 #include "psqtab.h"
33 #include "ucioption.h"
34
35
36 ////
37 //// Variables
38 ////
39
40 int Position::castleRightsMask[64];
41
42 Key Position::zobrist[2][8][64];
43 Key Position::zobEp[64];
44 Key Position::zobCastle[16];
45 Key Position::zobMaterial[2][8][16];
46 Key Position::zobSideToMove;
47
48 Value Position::MgPieceSquareTable[16][64];
49 Value Position::EgPieceSquareTable[16][64];
50
51
52 ////
53 //// Functions
54 ////
55
56 /// Constructors
57
58 Position::Position(const Position &pos) {
59   copy(pos);
60 }
61
62 Position::Position(const std::string &fen) {
63   from_fen(fen);
64 }
65
66
67 /// Position::from_fen() initializes the position object with the given FEN
68 /// string. This function is not very robust - make sure that input FENs are
69 /// correct (this is assumed to be the responsibility of the GUI).
70
71 void Position::from_fen(const std::string &fen) {
72
73   static const std::string pieceLetters = "KQRBNPkqrbnp";
74   static const Piece pieces[] = { WK, WQ, WR, WB, WN, WP, BK, BQ, BR, BB, BN, BP };
75
76   clear();
77
78   // Board
79   Rank rank = RANK_8;
80   File file = FILE_A;
81   size_t i = 0;
82   for ( ; fen[i] != ' '; i++)
83   {
84       if (isdigit(fen[i]))
85       {
86           // Skip the given number of files
87           file += (fen[i] - '1' + 1);
88           continue;
89       }
90       else if (fen[i] == '/')
91       {
92           file = FILE_A;
93           rank--;
94           continue;
95       }
96       size_t idx = pieceLetters.find(fen[i]);
97       if (idx == std::string::npos)
98       {
99            std::cout << "Error in FEN at character " << i << std::endl;
100            return;
101       }
102       Square square = make_square(file, rank);
103       put_piece(pieces[idx], square);
104       file++;
105   }
106
107   // Side to move
108   i++;
109   if (fen[i] != 'w' && fen[i] != 'b')
110   {
111       std::cout << "Error in FEN at character " << i << std::endl;
112       return;
113   }
114   sideToMove = (fen[i] == 'w' ? WHITE : BLACK);
115
116   // Castling rights:
117   i++;
118   if (fen[i] != ' ')
119   {
120       std::cout << "Error in FEN at character " << i << std::endl;
121       return;
122   }
123
124   i++;
125   while(strchr("KQkqabcdefghABCDEFGH-", fen[i])) {
126     if(fen[i] == '-') {
127       i++; break;
128     }
129     else if(fen[i] == 'K') allow_oo(WHITE);
130     else if(fen[i] == 'Q') allow_ooo(WHITE);
131     else if(fen[i] == 'k') allow_oo(BLACK);
132     else if(fen[i] == 'q') allow_ooo(BLACK);
133     else if(fen[i] >= 'A' && fen[i] <= 'H') {
134       File rookFile, kingFile = FILE_NONE;
135       for(Square square = SQ_B1; square <= SQ_G1; square++)
136         if(piece_on(square) == WK)
137           kingFile = square_file(square);
138       if(kingFile == FILE_NONE) {
139         std::cout << "Error in FEN at character " << i << std::endl;
140         return;
141       }
142       initialKFile = kingFile;
143       rookFile = File(fen[i] - 'A') + FILE_A;
144       if(rookFile < initialKFile) {
145         allow_ooo(WHITE);
146         initialQRFile = rookFile;
147       }
148       else {
149         allow_oo(WHITE);
150         initialKRFile = rookFile;
151       }
152     }
153     else if(fen[i] >= 'a' && fen[i] <= 'h') {
154       File rookFile, kingFile = FILE_NONE;
155       for(Square square = SQ_B8; square <= SQ_G8; square++)
156         if(piece_on(square) == BK)
157           kingFile = square_file(square);
158       if(kingFile == FILE_NONE) {
159         std::cout << "Error in FEN at character " << i << std::endl;
160         return;
161       }
162       initialKFile = kingFile;
163       rookFile = File(fen[i] - 'a') + FILE_A;
164       if(rookFile < initialKFile) {
165         allow_ooo(BLACK);
166         initialQRFile = rookFile;
167       }
168       else {
169         allow_oo(BLACK);
170         initialKRFile = rookFile;
171       }
172     }
173     else {
174       std::cout << "Error in FEN at character " << i << std::endl;
175       return;
176     }
177     i++;
178   }
179
180   // Skip blanks
181   while (fen[i] == ' ')
182       i++;
183
184   // En passant square
185   if (    i < fen.length() - 2
186       && (fen[i] >= 'a' && fen[i] <= 'h')
187       && (fen[i+1] == '3' || fen[i+1] == '6'))
188       epSquare = square_from_string(fen.substr(i, 2));
189
190   // Various initialisation
191   for (Square sq = SQ_A1; sq <= SQ_H8; sq++)
192       castleRightsMask[sq] = ALL_CASTLES;
193
194   castleRightsMask[make_square(initialKFile,  RANK_1)] ^= (WHITE_OO|WHITE_OOO);
195   castleRightsMask[make_square(initialKFile,  RANK_8)] ^= (BLACK_OO|BLACK_OOO);
196   castleRightsMask[make_square(initialKRFile, RANK_1)] ^= WHITE_OO;
197   castleRightsMask[make_square(initialKRFile, RANK_8)] ^= BLACK_OO;
198   castleRightsMask[make_square(initialQRFile, RANK_1)] ^= WHITE_OOO;
199   castleRightsMask[make_square(initialQRFile, RANK_8)] ^= BLACK_OOO;
200
201   find_checkers();
202
203   key = compute_key();
204   pawnKey = compute_pawn_key();
205   materialKey = compute_material_key();
206   mgValue = compute_mg_value();
207   egValue = compute_eg_value();
208   npMaterial[WHITE] = compute_non_pawn_material(WHITE);
209   npMaterial[BLACK] = compute_non_pawn_material(BLACK);
210 }
211
212
213 /// Position::to_fen() converts the position object to a FEN string. This is
214 /// probably only useful for debugging.
215
216 const std::string Position::to_fen() const {
217
218   static const std::string pieceLetters = " PNBRQK  pnbrqk";
219   std::string fen;
220   int skip;
221
222   for (Rank rank = RANK_8; rank >= RANK_1; rank--)
223   {
224       skip = 0;
225       for (File file = FILE_A; file <= FILE_H; file++)
226       {
227           Square sq = make_square(file, rank);
228           if (!square_is_occupied(sq))
229           {   skip++;
230               continue;
231           }
232           if (skip > 0)
233           {
234               fen += (char)skip + '0';
235               skip = 0;
236           }
237           fen += pieceLetters[piece_on(sq)];         
238       }
239       if (skip > 0)
240           fen += (char)skip + '0';
241
242       fen += (rank > RANK_1 ? '/' : ' ');
243   }
244   fen += (sideToMove == WHITE ? 'w' : 'b') + ' ';
245   if (castleRights != NO_CASTLES)
246   {
247     if (can_castle_kingside(WHITE))  fen += 'K';
248     if (can_castle_queenside(WHITE)) fen += 'Q';
249     if (can_castle_kingside(BLACK))  fen += 'k';
250     if (can_castle_queenside(BLACK)) fen += 'q';
251   } else
252       fen += '-';
253
254   fen += ' ';
255   if (ep_square() != SQ_NONE)
256       fen += square_to_string(ep_square());
257   else
258       fen += '-';
259
260   return fen;
261 }
262
263
264 /// Position::print() prints an ASCII representation of the position to
265 /// the standard output.
266
267 void Position::print() const {
268   char pieceStrings[][8] =
269     {"| ? ", "| P ", "| N ", "| B ", "| R ", "| Q ", "| K ", "| ? ",
270      "| ? ", "|=P=", "|=N=", "|=B=", "|=R=", "|=Q=", "|=K="
271     };
272
273   for(Rank rank = RANK_8; rank >= RANK_1; rank--) {
274     std::cout << "+---+---+---+---+---+---+---+---+\n";
275     for(File file = FILE_A; file <= FILE_H; file++) {
276       Square sq = make_square(file, rank);
277       Piece piece = piece_on(sq);
278       if(piece == EMPTY)
279         std::cout << ((square_color(sq) == WHITE)? "|   " : "| . ");
280       else
281         std::cout << pieceStrings[piece];
282     }
283     std::cout << "|\n";
284   }
285   std::cout << "+---+---+---+---+---+---+---+---+\n";
286   std::cout << to_fen() << std::endl;
287   std::cout << key << std::endl;
288 }
289
290
291 /// Position::copy() creates a copy of the input position.
292
293 void Position::copy(const Position &pos) {
294   memcpy(this, &pos, sizeof(Position));
295 }
296
297
298 /// Position:pinned_pieces() returns a bitboard of all pinned (against the
299 /// king) pieces for the given color.
300
301 Bitboard Position::pinned_pieces(Color c) const {
302   Bitboard b1, b2, pinned, pinners, sliders;
303   Square ksq = king_square(c), s;
304   Color them = opposite_color(c);
305
306   pinned = EmptyBoardBB;
307   b1 = occupied_squares();
308
309   sliders = rooks_and_queens(them) & ~checkers();
310   if(sliders & RookPseudoAttacks[ksq]) {
311     b2 = piece_attacks<ROOK>(ksq) & pieces_of_color(c);
312     pinners = rook_attacks_bb(ksq, b1 ^ b2) & sliders;
313     while(pinners) {
314       s = pop_1st_bit(&pinners);
315       pinned |= (squares_between(s, ksq) & b2);
316     }
317   }
318
319   sliders = bishops_and_queens(them) & ~checkers();
320   if(sliders & BishopPseudoAttacks[ksq]) {
321     b2 = piece_attacks<BISHOP>(ksq) & pieces_of_color(c);
322     pinners = bishop_attacks_bb(ksq, b1 ^ b2) & sliders;
323     while(pinners) {
324       s = pop_1st_bit(&pinners);
325       pinned |= (squares_between(s, ksq) & b2);
326     }
327   }
328
329   return pinned;
330 }
331
332 /// Position:discovered_check_candidates() returns a bitboard containing all
333 /// pieces for the given side which are candidates for giving a discovered
334 /// check.  The code is almost the same as the function for finding pinned
335 /// pieces.
336
337 Bitboard Position::discovered_check_candidates(Color c) const {
338   Bitboard b1, b2, dc, checkers, sliders;
339   Square ksq = king_square(opposite_color(c)), s;
340
341   dc = EmptyBoardBB;
342   b1 = occupied_squares();
343
344   sliders = rooks_and_queens(c);
345   if(sliders & RookPseudoAttacks[ksq]) {
346     b2 = piece_attacks<ROOK>(ksq) & pieces_of_color(c);
347     checkers = rook_attacks_bb(ksq, b1 ^ b2) & sliders;
348     while(checkers) {
349       s = pop_1st_bit(&checkers);
350       dc |= (squares_between(s, ksq) & b2);
351     }
352   }
353
354   sliders = bishops_and_queens(c);
355   if(sliders & BishopPseudoAttacks[ksq]) {
356     b2 = piece_attacks<BISHOP>(ksq) & pieces_of_color(c);
357     checkers = bishop_attacks_bb(ksq, b1 ^ b2) & sliders;
358     while(checkers) {
359       s = pop_1st_bit(&checkers);
360       dc |= (squares_between(s, ksq) & b2);
361     }
362   }
363
364   return dc;
365 }
366
367
368 /// Position::square_is_attacked() checks whether the given side attacks the
369 /// given square.
370
371 bool Position::square_is_attacked(Square s, Color c) const {
372   return
373     (pawn_attacks(opposite_color(c), s) & pawns(c)) ||
374     (piece_attacks<KNIGHT>(s) & knights(c)) ||
375     (piece_attacks<KING>(s)   & kings(c)) ||
376     (piece_attacks<ROOK>(s)   & rooks_and_queens(c)) ||
377     (piece_attacks<BISHOP>(s) & bishops_and_queens(c));
378 }
379
380
381 /// Position::attacks_to() computes a bitboard containing all pieces which
382 /// attacks a given square. There are two versions of this function: One
383 /// which finds attackers of both colors, and one which only finds the
384 /// attackers for one side.
385
386 Bitboard Position::attacks_to(Square s) const {
387   return
388     (pawn_attacks(BLACK, s) & pawns(WHITE)) |
389     (pawn_attacks(WHITE, s) & pawns(BLACK)) |
390     (piece_attacks<KNIGHT>(s) & pieces_of_type(KNIGHT)) |
391     (piece_attacks<ROOK>(s) & rooks_and_queens()) |
392     (piece_attacks<BISHOP>(s) & bishops_and_queens()) |
393     (piece_attacks<KING>(s) & pieces_of_type(KING));
394 }
395
396 Bitboard Position::attacks_to(Square s, Color c) const {
397   return attacks_to(s) & pieces_of_color(c);
398 }
399
400
401 /// Position::piece_attacks_square() tests whether the piece on square f
402 /// attacks square t.
403
404 bool Position::piece_attacks_square(Square f, Square t) const {
405   assert(square_is_ok(f));
406   assert(square_is_ok(t));
407
408   switch(piece_on(f)) {
409   case WP: return white_pawn_attacks_square(f, t);
410   case BP: return black_pawn_attacks_square(f, t);
411   case WN: case BN: return knight_attacks_square(f, t);
412   case WB: case BB: return bishop_attacks_square(f, t);
413   case WR: case BR: return rook_attacks_square(f, t);
414   case WQ: case BQ: return queen_attacks_square(f, t);
415   case WK: case BK: return king_attacks_square(f, t);
416   default: return false;
417   }
418
419   return false;
420 }
421
422
423 /// Position::find_checkers() computes the checkersBB bitboard, which
424 /// contains a nonzero bit for each checking piece (0, 1 or 2).  It
425 /// currently works by calling Position::attacks_to, which is probably
426 /// inefficient.  Consider rewriting this function to use the last move
427 /// played, like in non-bitboard versions of Glaurung.
428
429 void Position::find_checkers() {
430   checkersBB = attacks_to(king_square(side_to_move()),
431                           opposite_color(side_to_move()));
432 }
433
434
435 /// Position::move_is_legal() tests whether a pseudo-legal move is legal.
436 /// There are two versions of this function:  One which takes only a
437 /// move as input, and one which takes a move and a bitboard of pinned
438 /// pieces.  The latter function is faster, and should always be preferred
439 /// when a pinned piece bitboard has already been computed.
440
441 bool Position::move_is_legal(Move m)  const {
442   return move_is_legal(m, pinned_pieces(side_to_move()));
443 }
444
445
446 bool Position::move_is_legal(Move m, Bitboard pinned) const {
447   Color us, them;
448   Square ksq, from;
449
450   assert(is_ok());
451   assert(move_is_ok(m));
452   assert(pinned == pinned_pieces(side_to_move()));
453
454   // If we're in check, all pseudo-legal moves are legal, because our
455   // check evasion generator only generates true legal moves.
456   if(is_check()) return true;
457
458   // Castling moves are checked for legality during move generation.
459   if(move_is_castle(m)) return true;
460
461   us = side_to_move();
462   them = opposite_color(us);
463
464   from = move_from(m);
465   ksq = king_square(us);
466
467   assert(color_of_piece_on(from) == us);
468   assert(piece_on(ksq) == king_of_color(us));
469
470   // En passant captures are a tricky special case.  Because they are
471   // rather uncommon, we do it simply by testing whether the king is attacked
472   // after the move is made:
473   if(move_is_ep(m)) {
474     Square to = move_to(m);
475     Square capsq = make_square(square_file(to), square_rank(from));
476     Bitboard b = occupied_squares();
477
478     assert(to == ep_square());
479     assert(piece_on(from) == pawn_of_color(us));
480     assert(piece_on(capsq) == pawn_of_color(them));
481     assert(piece_on(to) == EMPTY);
482
483     clear_bit(&b, from); clear_bit(&b, capsq); set_bit(&b, to);
484     return
485       (!(rook_attacks_bb(ksq, b) & rooks_and_queens(them)) &&
486        !(bishop_attacks_bb(ksq, b) & bishops_and_queens(them)));
487   }
488
489   // If the moving piece is a king, check whether the destination
490   // square is attacked by the opponent.
491   if(from == ksq) return !(square_is_attacked(move_to(m), them));
492
493   // A non-king move is legal if and only if it is not pinned or it
494   // is moving along the ray towards or away from the king.
495   if(!bit_is_set(pinned, from)) return true;
496   if(direction_between_squares(from, ksq) ==
497      direction_between_squares(move_to(m), ksq))
498     return true;
499
500   return false;
501 }
502
503
504 /// Position::move_is_check() tests whether a pseudo-legal move is a check.
505 /// There are two versions of this function:  One which takes only a move as
506 /// input, and one which takes a move and a bitboard of discovered check
507 /// candidates.  The latter function is faster, and should always be preferred
508 /// when a discovered check candidates bitboard has already been computed.
509
510 bool Position::move_is_check(Move m) const {
511   Bitboard dc = discovered_check_candidates(side_to_move());
512   return move_is_check(m, dc);
513 }
514
515
516 bool Position::move_is_check(Move m, Bitboard dcCandidates) const {
517   Color us, them;
518   Square ksq, from, to;
519
520   assert(is_ok());
521   assert(move_is_ok(m));
522   assert(dcCandidates ==
523          discovered_check_candidates(side_to_move()));
524
525   us = side_to_move();
526   them = opposite_color(us);
527
528   from = move_from(m);
529   to = move_to(m);
530   ksq = king_square(them);
531   assert(color_of_piece_on(from) == us);
532   assert(piece_on(ksq) == king_of_color(them));
533
534   // Proceed according to the type of the moving piece:
535   switch(type_of_piece_on(from)) {
536   case PAWN:
537     // Normal check?
538     if(bit_is_set(pawn_attacks(them, ksq), to))
539       return true;
540     // Discovered check?
541     else if(bit_is_set(dcCandidates, from) &&
542             direction_between_squares(from, ksq) !=
543             direction_between_squares(to, ksq))
544       return true;
545     // Promotion with check?
546     else if(move_promotion(m)) {
547       Bitboard b = occupied_squares();
548       clear_bit(&b, from);
549
550       switch(move_promotion(m)) {
551       case KNIGHT:
552         return knight_attacks_square(to, ksq);
553       case BISHOP:
554         return bit_is_set(bishop_attacks_bb(to, b), ksq);
555       case ROOK:
556         return bit_is_set(rook_attacks_bb(to, b), ksq);
557       case QUEEN:
558         return bit_is_set(queen_attacks_bb(to, b), ksq);
559       default:
560         assert(false);
561       }
562     }
563     // En passant capture with check?  We have already handled the case
564     // of direct checks and ordinary discovered check, the only case we
565     // need to handle is the unusual case of a discovered check through the
566     // captured pawn.
567     else if(move_is_ep(m)) {
568       Square capsq = make_square(square_file(to), square_rank(from));
569       Bitboard b = occupied_squares();
570
571       clear_bit(&b, from); clear_bit(&b, capsq); set_bit(&b, to);
572       return
573         ((rook_attacks_bb(ksq, b) & rooks_and_queens(us)) ||
574          (bishop_attacks_bb(ksq, b) & bishops_and_queens(us)));
575     }
576     return false;
577
578   case KNIGHT:
579     // Discovered check?
580     if(bit_is_set(dcCandidates, from))
581       return true;
582     // Normal check?
583     else
584       return bit_is_set(piece_attacks<KNIGHT>(ksq), to);
585
586   case BISHOP:
587     // Discovered check?
588     if(bit_is_set(dcCandidates, from))
589       return true;
590     // Normal check?
591     else
592       return bit_is_set(piece_attacks<BISHOP>(ksq), to);
593
594   case ROOK:
595     // Discovered check?
596     if(bit_is_set(dcCandidates, from))
597       return true;
598     // Normal check?
599     else
600       return bit_is_set(piece_attacks<ROOK>(ksq), to);
601
602   case QUEEN:
603     // Discovered checks are impossible!
604     assert(!bit_is_set(dcCandidates, from));
605     // Normal check?
606     return bit_is_set(piece_attacks<QUEEN>(ksq), to);
607
608   case KING:
609     // Discovered check?
610     if(bit_is_set(dcCandidates, from) &&
611        direction_between_squares(from, ksq) !=
612        direction_between_squares(to, ksq))
613       return true;
614     // Castling with check?
615     if(move_is_castle(m)) {
616       Square kfrom, kto, rfrom, rto;
617       Bitboard b = occupied_squares();
618
619       kfrom = from;
620       rfrom = to;
621       if(rfrom > kfrom) {
622         kto = relative_square(us, SQ_G1);
623         rto = relative_square(us, SQ_F1);
624       }
625       else {
626         kto = relative_square(us, SQ_C1);
627         rto = relative_square(us, SQ_D1);
628       }
629
630       clear_bit(&b, kfrom); clear_bit(&b, rfrom);
631       set_bit(&b, rto); set_bit(&b, kto);
632
633       return bit_is_set(rook_attacks_bb(rto, b), ksq);
634     }
635
636     return false;
637
638   default:
639     assert(false);
640     return false;
641   }
642
643   assert(false);
644   return false;
645 }
646
647
648 /// Position::move_is_capture() tests whether a move from the current
649 /// position is a capture.
650
651 bool Position::move_is_capture(Move m) const {
652   return
653     color_of_piece_on(move_to(m)) == opposite_color(side_to_move())
654     || move_is_ep(m);
655 }
656
657
658 /// Position::move_attacks_square() tests whether a move from the current
659 /// position attacks a given square.  Only attacks by the moving piece are
660 /// considered; the function does not handle X-ray attacks.
661
662 bool Position::move_attacks_square(Move m, Square s) const {
663   assert(move_is_ok(m));
664   assert(square_is_ok(s));
665
666   Square f = move_from(m), t = move_to(m);
667
668   assert(square_is_occupied(f));
669
670   switch(piece_on(f)) {
671   case WP: return white_pawn_attacks_square(t, s);
672   case BP: return black_pawn_attacks_square(t, s);
673   case WN: case BN: return knight_attacks_square(t, s);
674   case WB: case BB: return bishop_attacks_square(t, s);
675   case WR: case BR: return rook_attacks_square(t, s);
676   case WQ: case BQ: return queen_attacks_square(t, s);
677   case WK: case BK: return king_attacks_square(t, s);
678   default: assert(false);
679   }
680
681   return false;
682 }
683
684
685
686 /// Position::backup() is called when making a move.  All information
687 /// necessary to restore the position when the move is later unmade
688 /// is saved to an UndoInfo object.  The function Position::restore
689 /// does the reverse operation:  When one does a backup followed by
690 /// a restore with the same UndoInfo object, the position is restored
691 /// to the state before backup was called.
692
693 void Position::backup(UndoInfo &u) const {
694   u.castleRights = castleRights;
695   u.epSquare = epSquare;
696   u.checkersBB = checkersBB;
697   u.key = key;
698   u.pawnKey = pawnKey;
699   u.materialKey = materialKey;
700   u.rule50 = rule50;
701   u.lastMove = lastMove;
702   u.capture = NO_PIECE_TYPE;
703   u.mgValue = mgValue;
704   u.egValue = egValue;
705 }
706
707
708 /// Position::restore() is called when unmaking a move.  It copies back
709 /// the information backed up during a previous call to Position::backup.
710
711 void Position::restore(const UndoInfo &u) {
712   castleRights = u.castleRights;
713   epSquare = u.epSquare;
714   checkersBB = u.checkersBB;
715   key = u.key;
716   pawnKey = u.pawnKey;
717   materialKey = u.materialKey;
718   rule50 = u.rule50;
719   lastMove = u.lastMove;
720   mgValue = u.mgValue;
721   egValue = u.egValue;
722 }
723
724
725 /// Position::do_move() makes a move, and backs up all information necessary
726 /// to undo the move to an UndoInfo object.  The move is assumed to be legal.
727 /// Pseudo-legal moves should be filtered out before this function is called.
728 /// There are two versions of this function, one which takes only the move and
729 /// the UndoInfo as input, and one which takes a third parameter, a bitboard of
730 /// discovered check candidates.  The second version is faster, because knowing
731 /// the discovered check candidates makes it easier to update the checkersBB
732 /// member variable in the position object.
733
734 void Position::do_move(Move m, UndoInfo &u) {
735   do_move(m, u, discovered_check_candidates(side_to_move()));
736 }
737
738 void Position::do_move(Move m, UndoInfo &u, Bitboard dcCandidates) {
739   assert(is_ok());
740   assert(move_is_ok(m));
741
742   // Back up the necessary information to our UndoInfo object (except the
743   // captured piece, which is taken care of later:
744   backup(u);
745
746   // Save the current key to the history[] array, in order to be able to
747   // detect repetition draws:
748   history[gamePly] = key;
749
750   // Increment the 50 moves rule draw counter.  Resetting it to zero in the
751   // case of non-reversible moves is taken care of later.
752   rule50++;
753
754   if(move_is_castle(m))
755     do_castle_move(m);
756   else if(move_promotion(m))
757     do_promotion_move(m, u);
758   else if(move_is_ep(m))
759     do_ep_move(m);
760   else {
761     Color us, them;
762     Square from, to;
763     PieceType piece, capture;
764
765     us = side_to_move();
766     them = opposite_color(us);
767
768     from = move_from(m);
769     to = move_to(m);
770
771     assert(color_of_piece_on(from) == us);
772     assert(color_of_piece_on(to) == them || piece_on(to) == EMPTY);
773
774     piece = type_of_piece_on(from);
775     capture = type_of_piece_on(to);
776
777     if(capture) {
778       assert(capture != KING);
779
780       // Remove captured piece:
781       clear_bit(&(byColorBB[them]), to);
782       clear_bit(&(byTypeBB[capture]), to);
783
784       // Update hash key:
785       key ^= zobrist[them][capture][to];
786
787       // If the captured piece was a pawn, update pawn hash key:
788       if(capture == PAWN)
789         pawnKey ^= zobrist[them][PAWN][to];
790
791       // Update incremental scores:
792       mgValue -= mg_pst(them, capture, to);
793       egValue -= eg_pst(them, capture, to);
794
795       // Update material:
796       if(capture != PAWN)
797         npMaterial[them] -= piece_value_midgame(capture);
798
799       // Update material hash key:
800       materialKey ^= zobMaterial[them][capture][pieceCount[them][capture]];
801
802       // Update piece count:
803       pieceCount[them][capture]--;
804
805       // Update piece list:
806       pieceList[them][capture][index[to]] =
807         pieceList[them][capture][pieceCount[them][capture]];
808       index[pieceList[them][capture][index[to]]] = index[to];
809
810       // Remember the captured piece, in order to be able to undo the move
811       // correctly:
812       u.capture = capture;
813
814       // Reset rule 50 counter:
815       rule50 = 0;
816     }
817
818     // Move the piece:
819     clear_bit(&(byColorBB[us]), from);
820     clear_bit(&(byTypeBB[piece]), from);
821     clear_bit(&(byTypeBB[0]), from); // HACK: byTypeBB[0] == occupied squares
822     set_bit(&(byColorBB[us]), to);
823     set_bit(&(byTypeBB[piece]), to);
824     set_bit(&(byTypeBB[0]), to); // HACK: byTypeBB[0] == occupied squares
825     board[to] = board[from];
826     board[from] = EMPTY;
827
828     // Update hash key:
829     key ^= zobrist[us][piece][from] ^ zobrist[us][piece][to];
830
831     // Update incremental scores:
832     mgValue -= mg_pst(us, piece, from);
833     mgValue += mg_pst(us, piece, to);
834     egValue -= eg_pst(us, piece, from);
835     egValue += eg_pst(us, piece, to);
836
837     // If the moving piece was a king, update the king square:
838     if(piece == KING)
839       kingSquare[us] = to;
840
841     // If the move was a double pawn push, set the en passant square.
842     // This code is a bit ugly right now, and should be cleaned up later.
843     // FIXME
844     if(epSquare != SQ_NONE) {
845       key ^= zobEp[epSquare];
846       epSquare = SQ_NONE;
847     }
848     if(piece == PAWN) {
849       if(abs(int(to) - int(from)) == 16) {
850         if((us == WHITE && (pawn_attacks(WHITE, from + DELTA_N) &
851                             pawns(BLACK))) ||
852            (us == BLACK && (pawn_attacks(BLACK, from + DELTA_S) &
853                             pawns(WHITE)))) {
854           epSquare = Square((int(from) + int(to)) / 2);
855           key ^= zobEp[epSquare];
856         }
857       }
858       // Reset rule 50 draw counter.
859       rule50 = 0;
860       // Update pawn hash key:
861       pawnKey ^= zobrist[us][PAWN][from] ^ zobrist[us][PAWN][to];
862     }
863
864     // Update piece lists:
865     pieceList[us][piece][index[from]] = to;
866     index[to] = index[from];
867
868     // Update castle rights:
869     key ^= zobCastle[castleRights];
870     castleRights &= castleRightsMask[from];
871     castleRights &= castleRightsMask[to];
872     key ^= zobCastle[castleRights];
873
874     // Update checkers bitboard:
875     checkersBB = EmptyBoardBB;
876     Square ksq = king_square(them);
877
878     switch(piece) {
879
880     case PAWN:
881       if(bit_is_set(pawn_attacks(them, ksq), to))
882         set_bit(&checkersBB, to);
883       if(bit_is_set(dcCandidates, from))
884         checkersBB |=
885           ((piece_attacks<ROOK>(ksq) & rooks_and_queens(us)) |
886            (piece_attacks<BISHOP>(ksq) & bishops_and_queens(us)));
887       break;
888
889     case KNIGHT:
890       if(bit_is_set(piece_attacks<KNIGHT>(ksq), to))
891         set_bit(&checkersBB, to);
892       if(bit_is_set(dcCandidates, from))
893         checkersBB |=
894           ((piece_attacks<ROOK>(ksq) & rooks_and_queens(us)) |
895            (piece_attacks<BISHOP>(ksq) & bishops_and_queens(us)));
896       break;
897
898     case BISHOP:
899       if(bit_is_set(piece_attacks<BISHOP>(ksq), to))
900         set_bit(&checkersBB, to);
901       if(bit_is_set(dcCandidates, from))
902         checkersBB |=
903           (piece_attacks<ROOK>(ksq) & rooks_and_queens(us));
904       break;
905
906     case ROOK:
907       if(bit_is_set(piece_attacks<ROOK>(ksq), to))
908         set_bit(&checkersBB, to);
909       if(bit_is_set(dcCandidates, from))
910         checkersBB |=
911           (piece_attacks<BISHOP>(ksq) & bishops_and_queens(us));
912       break;
913
914     case QUEEN:
915       if(bit_is_set(piece_attacks<QUEEN>(ksq), to))
916         set_bit(&checkersBB, to);
917       break;
918
919     case KING:
920       if(bit_is_set(dcCandidates, from))
921         checkersBB |=
922           ((piece_attacks<ROOK>(ksq) & rooks_and_queens(us)) |
923            (piece_attacks<BISHOP>(ksq) & bishops_and_queens(us)));
924       break;
925
926     default:
927       assert(false);
928       break;
929     }
930   }
931
932   // Finish
933   key ^= zobSideToMove;
934   sideToMove = opposite_color(sideToMove);
935   gamePly++;
936
937   mgValue += (sideToMove == WHITE)? TempoValueMidgame : -TempoValueMidgame;
938   egValue += (sideToMove == WHITE)? TempoValueEndgame : -TempoValueEndgame;
939
940   assert(is_ok());
941 }
942
943
944 /// Position::do_castle_move() is a private method used to make a castling
945 /// move.  It is called from the main Position::do_move function.  Note that
946 /// castling moves are encoded as "king captures friendly rook" moves, for
947 /// instance white short castling in a non-Chess960 game is encoded as e1h1.
948
949 void Position::do_castle_move(Move m) {
950   Color us, them;
951   Square kfrom, kto, rfrom, rto;
952
953   assert(is_ok());
954   assert(move_is_ok(m));
955   assert(move_is_castle(m));
956
957   us = side_to_move();
958   them = opposite_color(us);
959
960   // Find source squares for king and rook:
961   kfrom = move_from(m);
962   rfrom = move_to(m);  // HACK: See comment at beginning of function.
963
964   assert(piece_on(kfrom) == king_of_color(us));
965   assert(piece_on(rfrom) == rook_of_color(us));
966
967   // Find destination squares for king and rook:
968   if(rfrom > kfrom) { // O-O
969     kto = relative_square(us, SQ_G1);
970     rto = relative_square(us, SQ_F1);
971   }
972   else { // O-O-O
973     kto = relative_square(us, SQ_C1);
974     rto = relative_square(us, SQ_D1);
975   }
976
977   // Remove pieces from source squares:
978   clear_bit(&(byColorBB[us]), kfrom);
979   clear_bit(&(byTypeBB[KING]), kfrom);
980   clear_bit(&(byTypeBB[0]), kfrom); // HACK: byTypeBB[0] == occupied squares
981   clear_bit(&(byColorBB[us]), rfrom);
982   clear_bit(&(byTypeBB[ROOK]), rfrom);
983   clear_bit(&(byTypeBB[0]), rfrom); // HACK: byTypeBB[0] == occupied squares
984
985   // Put pieces on destination squares:
986   set_bit(&(byColorBB[us]), kto);
987   set_bit(&(byTypeBB[KING]), kto);
988   set_bit(&(byTypeBB[0]), kto); // HACK: byTypeBB[0] == occupied squares
989   set_bit(&(byColorBB[us]), rto);
990   set_bit(&(byTypeBB[ROOK]), rto);
991   set_bit(&(byTypeBB[0]), rto); // HACK: byTypeBB[0] == occupied squares
992
993   // Update board array:
994   board[kfrom] = board[rfrom] = EMPTY;
995   board[kto] = king_of_color(us);
996   board[rto] = rook_of_color(us);
997
998   // Update king square:
999   kingSquare[us] = kto;
1000
1001   // Update piece lists:
1002   pieceList[us][KING][index[kfrom]] = kto;
1003   pieceList[us][ROOK][index[rfrom]] = rto;
1004   int tmp = index[rfrom];
1005   index[kto] = index[kfrom];
1006   index[rto] = tmp;
1007
1008   // Update incremental scores:
1009   mgValue -= mg_pst(us, KING, kfrom);
1010   mgValue += mg_pst(us, KING, kto);
1011   egValue -= eg_pst(us, KING, kfrom);
1012   egValue += eg_pst(us, KING, kto);
1013   mgValue -= mg_pst(us, ROOK, rfrom);
1014   mgValue += mg_pst(us, ROOK, rto);
1015   egValue -= eg_pst(us, ROOK, rfrom);
1016   egValue += eg_pst(us, ROOK, rto);
1017
1018   // Update hash key:
1019   key ^= zobrist[us][KING][kfrom] ^ zobrist[us][KING][kto];
1020   key ^= zobrist[us][ROOK][rfrom] ^ zobrist[us][ROOK][rto];
1021
1022   // Clear en passant square:
1023   if(epSquare != SQ_NONE) {
1024     key ^= zobEp[epSquare];
1025     epSquare = SQ_NONE;
1026   }
1027
1028   // Update castling rights:
1029   key ^= zobCastle[castleRights];
1030   castleRights &= castleRightsMask[kfrom];
1031   key ^= zobCastle[castleRights];
1032
1033   // Reset rule 50 counter:
1034   rule50 = 0;
1035
1036   // Update checkers BB:
1037   checkersBB = attacks_to(king_square(them), us);
1038 }
1039
1040
1041 /// Position::do_promotion_move() is a private method used to make a promotion
1042 /// move.  It is called from the main Position::do_move function.  The
1043 /// UndoInfo object, which has been initialized in Position::do_move, is
1044 /// used to store the captured piece (if any).
1045
1046 void Position::do_promotion_move(Move m, UndoInfo &u) {
1047   Color us, them;
1048   Square from, to;
1049   PieceType capture, promotion;
1050
1051   assert(is_ok());
1052   assert(move_is_ok(m));
1053   assert(move_promotion(m));
1054
1055   us = side_to_move();
1056   them = opposite_color(us);
1057
1058   from = move_from(m);
1059   to = move_to(m);
1060
1061   assert(relative_rank(us, to) == RANK_8);
1062   assert(piece_on(from) == pawn_of_color(us));
1063   assert(color_of_piece_on(to) == them || square_is_empty(to));
1064
1065   capture = type_of_piece_on(to);
1066
1067   if(capture) {
1068     assert(capture != KING);
1069
1070     // Remove captured piece:
1071     clear_bit(&(byColorBB[them]), to);
1072     clear_bit(&(byTypeBB[capture]), to);
1073
1074     // Update hash key:
1075     key ^= zobrist[them][capture][to];
1076
1077     // Update incremental scores:
1078     mgValue -= mg_pst(them, capture, to);
1079     egValue -= eg_pst(them, capture, to);
1080
1081     // Update material.  Because our move is a promotion, we know that the
1082     // captured piece is not a pawn.
1083     assert(capture != PAWN);
1084     npMaterial[them] -= piece_value_midgame(capture);
1085
1086     // Update material hash key:
1087     materialKey ^= zobMaterial[them][capture][pieceCount[them][capture]];
1088
1089     // Update piece count:
1090     pieceCount[them][capture]--;
1091
1092     // Update piece list:
1093     pieceList[them][capture][index[to]] =
1094       pieceList[them][capture][pieceCount[them][capture]];
1095     index[pieceList[them][capture][index[to]]] = index[to];
1096
1097     // Remember the captured piece, in order to be able to undo the move
1098     // correctly:
1099     u.capture = capture;
1100   }
1101
1102   // Remove pawn:
1103   clear_bit(&(byColorBB[us]), from);
1104   clear_bit(&(byTypeBB[PAWN]), from);
1105   clear_bit(&(byTypeBB[0]), from); // HACK: byTypeBB[0] == occupied squares
1106   board[from] = EMPTY;
1107
1108   // Insert promoted piece:
1109   promotion = move_promotion(m);
1110   assert(promotion >= KNIGHT && promotion <= QUEEN);
1111   set_bit(&(byColorBB[us]), to);
1112   set_bit(&(byTypeBB[promotion]), to);
1113   set_bit(&(byTypeBB[0]), to); // HACK: byTypeBB[0] == occupied squares
1114   board[to] = piece_of_color_and_type(us, promotion);
1115
1116   // Update hash key:
1117   key ^= zobrist[us][PAWN][from] ^ zobrist[us][promotion][to];
1118
1119   // Update pawn hash key:
1120   pawnKey ^= zobrist[us][PAWN][from];
1121
1122   // Update material key:
1123   materialKey ^= zobMaterial[us][PAWN][pieceCount[us][PAWN]];
1124   materialKey ^= zobMaterial[us][promotion][pieceCount[us][promotion]+1];
1125
1126   // Update piece counts:
1127   pieceCount[us][PAWN]--;
1128   pieceCount[us][promotion]++;
1129
1130   // Update piece lists:
1131   pieceList[us][PAWN][index[from]] =
1132     pieceList[us][PAWN][pieceCount[us][PAWN]];
1133   index[pieceList[us][PAWN][index[from]]] = index[from];
1134   pieceList[us][promotion][pieceCount[us][promotion] - 1] = to;
1135   index[to] = pieceCount[us][promotion] - 1;
1136
1137   // Update incremental scores:
1138   mgValue -= mg_pst(us, PAWN, from);
1139   mgValue += mg_pst(us, promotion, to);
1140   egValue -= eg_pst(us, PAWN, from);
1141   egValue += eg_pst(us, promotion, to);
1142
1143   // Update material:
1144   npMaterial[us] += piece_value_midgame(promotion);
1145
1146   // Clear the en passant square:
1147   if(epSquare != SQ_NONE) {
1148     key ^= zobEp[epSquare];
1149     epSquare = SQ_NONE;
1150   }
1151
1152   // Update castle rights:
1153   key ^= zobCastle[castleRights];
1154   castleRights &= castleRightsMask[to];
1155   key ^= zobCastle[castleRights];
1156
1157   // Reset rule 50 counter:
1158   rule50 = 0;
1159
1160   // Update checkers BB:
1161   checkersBB = attacks_to(king_square(them), us);
1162 }
1163
1164
1165 /// Position::do_ep_move() is a private method used to make an en passant
1166 /// capture.  It is called from the main Position::do_move function.  Because
1167 /// the captured piece is always a pawn, we don't need to pass an UndoInfo
1168 /// object in which to store the captured piece.
1169
1170 void Position::do_ep_move(Move m) {
1171   Color us, them;
1172   Square from, to, capsq;
1173
1174   assert(is_ok());
1175   assert(move_is_ok(m));
1176   assert(move_is_ep(m));
1177
1178   us = side_to_move();
1179   them = opposite_color(us);
1180
1181   // Find from, to and capture squares:
1182   from = move_from(m);
1183   to = move_to(m);
1184   capsq = (us == WHITE)? (to - DELTA_N) : (to - DELTA_S);
1185
1186   assert(to == epSquare);
1187   assert(relative_rank(us, to) == RANK_6);
1188   assert(piece_on(to) == EMPTY);
1189   assert(piece_on(from) == pawn_of_color(us));
1190   assert(piece_on(capsq) == pawn_of_color(them));
1191
1192   // Remove captured piece:
1193   clear_bit(&(byColorBB[them]), capsq);
1194   clear_bit(&(byTypeBB[PAWN]), capsq);
1195   clear_bit(&(byTypeBB[0]), capsq); // HACK: byTypeBB[0] == occupied squares
1196   board[capsq] = EMPTY;
1197
1198   // Remove moving piece from source square:
1199   clear_bit(&(byColorBB[us]), from);
1200   clear_bit(&(byTypeBB[PAWN]), from);
1201   clear_bit(&(byTypeBB[0]), from); // HACK: byTypeBB[0] == occupied squares
1202
1203   // Put moving piece on destination square:
1204   set_bit(&(byColorBB[us]), to);
1205   set_bit(&(byTypeBB[PAWN]), to);
1206   set_bit(&(byTypeBB[0]), to); // HACK: byTypeBB[0] == occupied squares
1207   board[to] = board[from];
1208   board[from] = EMPTY;
1209
1210   // Update material hash key:
1211   materialKey ^= zobMaterial[them][PAWN][pieceCount[them][PAWN]];
1212
1213   // Update piece count:
1214   pieceCount[them][PAWN]--;
1215
1216   // Update piece list:
1217   pieceList[us][PAWN][index[from]] = to;
1218   index[to] = index[from];
1219   pieceList[them][PAWN][index[capsq]] =
1220     pieceList[them][PAWN][pieceCount[them][PAWN]];
1221   index[pieceList[them][PAWN][index[capsq]]] = index[capsq];
1222
1223   // Update hash key:
1224   key ^= zobrist[us][PAWN][from] ^ zobrist[us][PAWN][to];
1225   key ^= zobrist[them][PAWN][capsq];
1226   key ^= zobEp[epSquare];
1227
1228   // Update pawn hash key:
1229   pawnKey ^= zobrist[us][PAWN][from] ^ zobrist[us][PAWN][to];
1230   pawnKey ^= zobrist[them][PAWN][capsq];
1231
1232   // Update incremental scores:
1233   mgValue -= mg_pst(them, PAWN, capsq);
1234   mgValue -= mg_pst(us, PAWN, from);
1235   mgValue += mg_pst(us, PAWN, to);
1236   egValue -= eg_pst(them, PAWN, capsq);
1237   egValue -= eg_pst(us, PAWN, from);
1238   egValue += eg_pst(us, PAWN, to);
1239
1240   // Reset en passant square:
1241   epSquare = SQ_NONE;
1242
1243   // Reset rule 50 counter:
1244   rule50 = 0;
1245
1246   // Update checkers BB:
1247   checkersBB = attacks_to(king_square(them), us);
1248 }
1249
1250
1251 /// Position::undo_move() unmakes a move.  When it returns, the position should
1252 /// be restored to exactly the same state as before the move was made.  It is
1253 /// important that Position::undo_move is called with the same move and UndoInfo
1254 /// object as the earlier call to Position::do_move.
1255
1256 void Position::undo_move(Move m, const UndoInfo &u) {
1257   assert(is_ok());
1258   assert(move_is_ok(m));
1259
1260   gamePly--;
1261   sideToMove = opposite_color(sideToMove);
1262
1263   // Restore information from our UndoInfo object (except the captured piece,
1264   // which is taken care of later):
1265   restore(u);
1266
1267   if(move_is_castle(m))
1268     undo_castle_move(m);
1269   else if(move_promotion(m))
1270     undo_promotion_move(m, u);
1271   else if(move_is_ep(m))
1272     undo_ep_move(m);
1273   else {
1274     Color us, them;
1275     Square from, to;
1276     PieceType piece, capture;
1277
1278     us = side_to_move();
1279     them = opposite_color(us);
1280
1281     from = move_from(m);
1282     to = move_to(m);
1283
1284     assert(piece_on(from) == EMPTY);
1285     assert(color_of_piece_on(to) == us);
1286
1287     // Put the piece back at the source square:
1288     piece = type_of_piece_on(to);
1289     set_bit(&(byColorBB[us]), from);
1290     set_bit(&(byTypeBB[piece]), from);
1291     set_bit(&(byTypeBB[0]), from); // HACK: byTypeBB[0] == occupied squares
1292     board[from] = piece_of_color_and_type(us, piece);
1293
1294     // Clear the destination square
1295     clear_bit(&(byColorBB[us]), to);
1296     clear_bit(&(byTypeBB[piece]), to);
1297     clear_bit(&(byTypeBB[0]), to); // HACK: byTypeBB[0] == occupied squares
1298
1299     // If the moving piece was a king, update the king square:
1300     if(piece == KING)
1301       kingSquare[us] = from;
1302
1303     // Update piece list:
1304     pieceList[us][piece][index[to]] = from;
1305     index[from] = index[to];
1306
1307     capture = u.capture;
1308
1309     if(capture) {
1310       assert(capture != KING);
1311       // Replace the captured piece:
1312       set_bit(&(byColorBB[them]), to);
1313       set_bit(&(byTypeBB[capture]), to);
1314       set_bit(&(byTypeBB[0]), to);
1315       board[to] = piece_of_color_and_type(them, capture);
1316
1317       // Update material:
1318       if(capture != PAWN)
1319         npMaterial[them] += piece_value_midgame(capture);
1320
1321       // Update piece list:
1322       pieceList[them][capture][pieceCount[them][capture]] = to;
1323       index[to] = pieceCount[them][capture];
1324
1325       // Update piece count:
1326       pieceCount[them][capture]++;
1327     }
1328     else
1329       board[to] = EMPTY;
1330   }
1331
1332   assert(is_ok());
1333 }
1334
1335
1336 /// Position::undo_castle_move() is a private method used to unmake a castling
1337 /// move.  It is called from the main Position::undo_move function.  Note that
1338 /// castling moves are encoded as "king captures friendly rook" moves, for
1339 /// instance white short castling in a non-Chess960 game is encoded as e1h1.
1340
1341 void Position::undo_castle_move(Move m) {
1342   Color us, them;
1343   Square kfrom, kto, rfrom, rto;
1344
1345   assert(move_is_ok(m));
1346   assert(move_is_castle(m));
1347
1348   // When we have arrived here, some work has already been done by
1349   // Position::undo_move.  In particular, the side to move has been switched,
1350   // so the code below is correct.
1351   us = side_to_move();
1352   them = opposite_color(us);
1353
1354   // Find source squares for king and rook:
1355   kfrom = move_from(m);
1356   rfrom = move_to(m);  // HACK: See comment at beginning of function.
1357
1358   // Find destination squares for king and rook:
1359   if(rfrom > kfrom) { // O-O
1360     kto = relative_square(us, SQ_G1);
1361     rto = relative_square(us, SQ_F1);
1362   }
1363   else { // O-O-O
1364     kto = relative_square(us, SQ_C1);
1365     rto = relative_square(us, SQ_D1);
1366   }
1367
1368   assert(piece_on(kto) == king_of_color(us));
1369   assert(piece_on(rto) == rook_of_color(us));
1370
1371   // Remove pieces from destination squares:
1372   clear_bit(&(byColorBB[us]), kto);
1373   clear_bit(&(byTypeBB[KING]), kto);
1374   clear_bit(&(byTypeBB[0]), kto); // HACK: byTypeBB[0] == occupied squares
1375   clear_bit(&(byColorBB[us]), rto);
1376   clear_bit(&(byTypeBB[ROOK]), rto);
1377   clear_bit(&(byTypeBB[0]), rto); // HACK: byTypeBB[0] == occupied squares
1378
1379   // Put pieces on source squares:
1380   set_bit(&(byColorBB[us]), kfrom);
1381   set_bit(&(byTypeBB[KING]), kfrom);
1382   set_bit(&(byTypeBB[0]), kfrom); // HACK: byTypeBB[0] == occupied squares
1383   set_bit(&(byColorBB[us]), rfrom);
1384   set_bit(&(byTypeBB[ROOK]), rfrom);
1385   set_bit(&(byTypeBB[0]), rfrom); // HACK: byTypeBB[0] == occupied squares
1386
1387   // Update board:
1388   board[rto] = board[kto] = EMPTY;
1389   board[rfrom] = rook_of_color(us);
1390   board[kfrom] = king_of_color(us);
1391
1392   // Update king square:
1393   kingSquare[us] = kfrom;
1394
1395   // Update piece lists:
1396   pieceList[us][KING][index[kto]] = kfrom;
1397   pieceList[us][ROOK][index[rto]] = rfrom;
1398   int tmp = index[rto];  // Necessary because we may have rto == kfrom in FRC.
1399   index[kfrom] = index[kto];
1400   index[rfrom] = tmp;
1401 }
1402
1403
1404 /// Position::undo_promotion_move() is a private method used to unmake a
1405 /// promotion move.  It is called from the main Position::do_move
1406 /// function.  The UndoInfo object, which has been initialized in
1407 /// Position::do_move, is used to put back the captured piece (if any).
1408
1409 void Position::undo_promotion_move(Move m, const UndoInfo &u) {
1410   Color us, them;
1411   Square from, to;
1412   PieceType capture, promotion;
1413
1414   assert(move_is_ok(m));
1415   assert(move_promotion(m));
1416
1417   // When we have arrived here, some work has already been done by
1418   // Position::undo_move.  In particular, the side to move has been switched,
1419   // so the code below is correct.
1420   us = side_to_move();
1421   them = opposite_color(us);
1422
1423   from = move_from(m);
1424   to = move_to(m);
1425
1426   assert(relative_rank(us, to) == RANK_8);
1427   assert(piece_on(from) == EMPTY);
1428
1429   // Remove promoted piece:
1430   promotion = move_promotion(m);
1431   assert(piece_on(to)==piece_of_color_and_type(us, promotion));
1432   assert(promotion >= KNIGHT && promotion <= QUEEN);
1433   clear_bit(&(byColorBB[us]), to);
1434   clear_bit(&(byTypeBB[promotion]), to);
1435   clear_bit(&(byTypeBB[0]), to); // HACK: byTypeBB[0] == occupied squares
1436
1437   // Insert pawn at source square:
1438   set_bit(&(byColorBB[us]), from);
1439   set_bit(&(byTypeBB[PAWN]), from);
1440   set_bit(&(byTypeBB[0]), from); // HACK: byTypeBB[0] == occupied squares
1441   board[from] = pawn_of_color(us);
1442
1443   // Update material:
1444   npMaterial[us] -= piece_value_midgame(promotion);
1445
1446   // Update piece list:
1447   pieceList[us][PAWN][pieceCount[us][PAWN]] = from;
1448   index[from] = pieceCount[us][PAWN];
1449   pieceList[us][promotion][index[to]] =
1450     pieceList[us][promotion][pieceCount[us][promotion] - 1];
1451   index[pieceList[us][promotion][index[to]]] = index[to];
1452
1453   // Update piece counts:
1454   pieceCount[us][promotion]--;
1455   pieceCount[us][PAWN]++;
1456
1457   capture = u.capture;
1458   if(capture) {
1459     assert(capture != KING);
1460
1461     // Insert captured piece:
1462     set_bit(&(byColorBB[them]), to);
1463     set_bit(&(byTypeBB[capture]), to);
1464     set_bit(&(byTypeBB[0]), to); // HACK: byTypeBB[0] == occupied squares
1465     board[to] = piece_of_color_and_type(them, capture);
1466
1467     // Update material.  Because the move is a promotion move, we know
1468     // that the captured piece cannot be a pawn.
1469     assert(capture != PAWN);
1470     npMaterial[them] += piece_value_midgame(capture);
1471
1472     // Update piece list:
1473     pieceList[them][capture][pieceCount[them][capture]] = to;
1474     index[to] = pieceCount[them][capture];
1475
1476     // Update piece count:
1477     pieceCount[them][capture]++;
1478   }
1479   else
1480     board[to] = EMPTY;
1481 }
1482
1483
1484 /// Position::undo_ep_move() is a private method used to unmake an en passant
1485 /// capture.  It is called from the main Position::undo_move function.  Because
1486 /// the captured piece is always a pawn, we don't need to pass an UndoInfo
1487 /// object from which to retrieve the captured piece.
1488
1489 void Position::undo_ep_move(Move m) {
1490   Color us, them;
1491   Square from, to, capsq;
1492
1493   assert(move_is_ok(m));
1494   assert(move_is_ep(m));
1495
1496   // When we have arrived here, some work has already been done by
1497   // Position::undo_move.  In particular, the side to move has been switched,
1498   // so the code below is correct.
1499   us = side_to_move();
1500   them = opposite_color(us);
1501
1502   // Find from, to and captures squares:
1503   from = move_from(m);
1504   to = move_to(m);
1505   capsq = (us == WHITE)? (to - DELTA_N) : (to - DELTA_S);
1506
1507   assert(to == ep_square());
1508   assert(relative_rank(us, to) == RANK_6);
1509   assert(piece_on(to) == pawn_of_color(us));
1510   assert(piece_on(from) == EMPTY);
1511   assert(piece_on(capsq) == EMPTY);
1512
1513   // Replace captured piece:
1514   set_bit(&(byColorBB[them]), capsq);
1515   set_bit(&(byTypeBB[PAWN]), capsq);
1516   set_bit(&(byTypeBB[0]), capsq);
1517   board[capsq] = pawn_of_color(them);
1518
1519   // Remove moving piece from destination square:
1520   clear_bit(&(byColorBB[us]), to);
1521   clear_bit(&(byTypeBB[PAWN]), to);
1522   clear_bit(&(byTypeBB[0]), to);
1523   board[to] = EMPTY;
1524
1525   // Replace moving piece at source square:
1526   set_bit(&(byColorBB[us]), from);
1527   set_bit(&(byTypeBB[PAWN]), from);
1528   set_bit(&(byTypeBB[0]), from);
1529   board[from] = pawn_of_color(us);
1530
1531   // Update piece list:
1532   pieceList[us][PAWN][index[to]] = from;
1533   index[from] = index[to];
1534   pieceList[them][PAWN][pieceCount[them][PAWN]] = capsq;
1535   index[capsq] = pieceCount[them][PAWN];
1536
1537   // Update piece count:
1538   pieceCount[them][PAWN]++;
1539 }
1540
1541
1542 /// Position::do_null_move makes() a "null move": It switches the side to move
1543 /// and updates the hash key without executing any move on the board.
1544
1545 void Position::do_null_move(UndoInfo &u) {
1546   assert(is_ok());
1547   assert(!is_check());
1548
1549   // Back up the information necessary to undo the null move to the supplied
1550   // UndoInfo object.  In the case of a null move, the only thing we need to
1551   // remember is the last move made and the en passant square.
1552   u.lastMove = lastMove;
1553   u.epSquare = epSquare;
1554
1555   // Save the current key to the history[] array, in order to be able to
1556   // detect repetition draws:
1557   history[gamePly] = key;
1558
1559   // Update the necessary information.
1560   sideToMove = opposite_color(sideToMove);
1561   if(epSquare != SQ_NONE)
1562     key ^= zobEp[epSquare];
1563   epSquare = SQ_NONE;
1564   rule50++;
1565   gamePly++;
1566   key ^= zobSideToMove;
1567
1568   mgValue += (sideToMove == WHITE)? TempoValueMidgame : -TempoValueMidgame;
1569   egValue += (sideToMove == WHITE)? TempoValueEndgame : -TempoValueEndgame;
1570
1571   assert(is_ok());
1572 }
1573
1574
1575 /// Position::undo_null_move() unmakes a "null move".
1576
1577 void Position::undo_null_move(const UndoInfo &u) {
1578   assert(is_ok());
1579   assert(!is_check());
1580
1581   // Restore information from the supplied UndoInfo object:
1582   lastMove = u.lastMove;
1583   epSquare = u.epSquare;
1584   if(epSquare != SQ_NONE)
1585     key ^= zobEp[epSquare];
1586
1587   // Update the necessary information.
1588   sideToMove = opposite_color(sideToMove);
1589   rule50--;
1590   gamePly--;
1591   key ^= zobSideToMove;
1592
1593   mgValue += (sideToMove == WHITE)? TempoValueMidgame : -TempoValueMidgame;
1594   egValue += (sideToMove == WHITE)? TempoValueEndgame : -TempoValueEndgame;
1595
1596   assert(is_ok());
1597 }
1598
1599
1600 /// Position::see() is a static exchange evaluator:  It tries to estimate the
1601 /// material gain or loss resulting from a move.  There are two versions of
1602 /// this function: One which takes a move as input, and one which takes a
1603 /// 'from' and a 'to' square.  The function does not yet understand promotions
1604 /// or en passant captures.
1605
1606 int Position::see(Square from, Square to) const {
1607   // Approximate material values, with pawn = 1:
1608   static const int seeValues[18] = {
1609     0, 1, 3, 3, 5, 10, 100, 0, 0, 1, 3, 3, 5, 10, 100, 0, 0, 0
1610   };
1611   Color us, them;
1612   Piece piece, capture;
1613   Bitboard attackers, occ, b;
1614
1615   assert(square_is_ok(from));
1616   assert(square_is_ok(to));
1617
1618   // Initialize colors:
1619   us = color_of_piece_on(from);
1620   them = opposite_color(us);
1621
1622   // Initialize pieces:
1623   piece = piece_on(from);
1624   capture = piece_on(to);
1625
1626   // Find all attackers to the destination square, with the moving piece
1627   // removed, but possibly an X-ray attacker added behind it:
1628   occ = occupied_squares();
1629   clear_bit(&occ, from);
1630   attackers =
1631     (rook_attacks_bb(to, occ) & rooks_and_queens()) |
1632     (bishop_attacks_bb(to, occ) & bishops_and_queens()) |
1633     (piece_attacks<KNIGHT>(to) & knights()) |
1634     (piece_attacks<KING>(to) & kings()) |
1635     (pawn_attacks(WHITE, to) & pawns(BLACK)) |
1636     (pawn_attacks(BLACK, to) & pawns(WHITE));
1637   attackers &= occ;
1638
1639   // If the opponent has no attackers, we are finished:
1640   if((attackers & pieces_of_color(them)) == EmptyBoardBB)
1641     return seeValues[capture];
1642
1643   // The destination square is defended, which makes things rather more
1644   // difficult to compute.  We proceed by building up a "swap list" containing
1645   // the material gain or loss at each stop in a sequence of captures to the
1646   // destianation square, where the sides alternately capture, and always
1647   // capture with the least valuable piece.  After each capture, we look for
1648   // new X-ray attacks from behind the capturing piece.
1649   int lastCapturingPieceValue = seeValues[piece];
1650   int swapList[32], n = 1;
1651   Color c = them;
1652   PieceType pt;
1653
1654   swapList[0] = seeValues[capture];
1655
1656   do {
1657     // Locate the least valuable attacker for the side to move.  The loop
1658     // below looks like it is potentially infinite, but it isn't.  We know
1659     // that the side to move still has at least one attacker left.
1660     for(pt = PAWN; !(attackers&pieces_of_color_and_type(c, pt)); pt++)
1661       assert(pt < KING);
1662
1663     // Remove the attacker we just found from the 'attackers' bitboard,
1664     // and scan for new X-ray attacks behind the attacker:
1665     b = attackers & pieces_of_color_and_type(c, pt);
1666     occ ^= (b & -b);
1667     attackers |=
1668       (rook_attacks_bb(to, occ) & rooks_and_queens()) |
1669       (bishop_attacks_bb(to, occ) & bishops_and_queens());
1670     attackers &= occ;
1671
1672     // Add the new entry to the swap list:
1673     assert(n < 32);
1674     swapList[n] = -swapList[n - 1] + lastCapturingPieceValue;
1675     n++;
1676
1677     // Remember the value of the capturing piece, and change the side to move
1678     // before beginning the next iteration:
1679     lastCapturingPieceValue = seeValues[pt];
1680     c = opposite_color(c);
1681
1682     // Stop after a king capture:
1683     if(pt == KING && (attackers & pieces_of_color(c))) {
1684       assert(n < 32);
1685       swapList[n++] = 100;
1686       break;
1687     }
1688   } while(attackers & pieces_of_color(c));
1689
1690   // Having built the swap list, we negamax through it to find the best
1691   // achievable score from the point of view of the side to move:
1692   while(--n) swapList[n-1] = Min(-swapList[n], swapList[n-1]);
1693
1694   return swapList[0];
1695 }
1696
1697
1698 int Position::see(Move m) const {
1699   assert(move_is_ok(m));
1700   return see(move_from(m), move_to(m));
1701 }
1702
1703
1704 /// Position::clear() erases the position object to a pristine state, with an
1705 /// empty board, white to move, and no castling rights.
1706
1707 void Position::clear() {
1708   int i, j;
1709
1710   for(i = 0; i < 64; i++) {
1711     board[i] = EMPTY;
1712     index[i] = 0;
1713   }
1714
1715   for(i = 0; i < 2; i++)
1716     byColorBB[i] = EmptyBoardBB;
1717
1718   for(i = 0; i < 7; i++) {
1719     byTypeBB[i] = EmptyBoardBB;
1720     pieceCount[0][i] = pieceCount[1][i] = 0;
1721     for(j = 0; j < 8; j++)
1722       pieceList[0][i][j] = pieceList[1][i][j] = SQ_NONE;
1723   }
1724
1725   checkersBB = EmptyBoardBB;
1726
1727   lastMove = MOVE_NONE;
1728
1729   sideToMove = WHITE;
1730   castleRights = NO_CASTLES;
1731   initialKFile = FILE_E;
1732   initialKRFile = FILE_H;
1733   initialQRFile = FILE_A;
1734   epSquare = SQ_NONE;
1735   rule50 = 0;
1736   gamePly = 0;
1737 }
1738
1739
1740 /// Position::reset_game_ply() simply sets gamePly to 0.  It is used from the
1741 /// UCI interface code, whenever a non-reversible move is made in a
1742 /// 'position fen <fen> moves m1 m2 ...' command.  This makes it possible
1743 /// for the program to handle games of arbitrary length, as long as the GUI
1744 /// handles draws by the 50 move rule correctly.
1745
1746 void Position::reset_game_ply() {
1747   gamePly = 0;
1748 }
1749
1750
1751 /// Position::put_piece() puts a piece on the given square of the board,
1752 /// updating the board array, bitboards, and piece counts.
1753
1754 void Position::put_piece(Piece p, Square s) {
1755   Color c = color_of_piece(p);
1756   PieceType pt = type_of_piece(p);
1757
1758   board[s] = p;
1759   index[s] = pieceCount[c][pt];
1760   pieceList[c][pt][index[s]] = s;
1761
1762   set_bit(&(byTypeBB[pt]), s);
1763   set_bit(&(byColorBB[c]), s);
1764   set_bit(&byTypeBB[0], s); // HACK: byTypeBB[0] contains all occupied squares.
1765
1766   pieceCount[c][pt]++;
1767
1768   if(pt == KING)
1769     kingSquare[c] = s;
1770 }
1771
1772
1773 /// Position::allow_oo() gives the given side the right to castle kingside.
1774 /// Used when setting castling rights during parsing of FEN strings.
1775
1776 void Position::allow_oo(Color c) {
1777   castleRights |= (1 + int(c));
1778 }
1779
1780
1781 /// Position::allow_ooo() gives the given side the right to castle queenside.
1782 /// Used when setting castling rights during parsing of FEN strings.
1783
1784 void Position::allow_ooo(Color c) {
1785   castleRights |= (4 + 4*int(c));
1786 }
1787
1788
1789 /// Position::compute_key() computes the hash key of the position.  The hash
1790 /// key is usually updated incrementally as moves are made and unmade, the
1791 /// compute_key() function is only used when a new position is set up, and
1792 /// to verify the correctness of the hash key when running in debug mode.
1793
1794 Key Position::compute_key() const {
1795   Key result = Key(0ULL);
1796
1797   for(Square s = SQ_A1; s <= SQ_H8; s++)
1798     if(square_is_occupied(s))
1799       result ^=
1800         zobrist[color_of_piece_on(s)][type_of_piece_on(s)][s];
1801
1802   if(ep_square() != SQ_NONE)
1803     result ^= zobEp[ep_square()];
1804   result ^= zobCastle[castleRights];
1805   if(side_to_move() == BLACK) result ^= zobSideToMove;
1806
1807   return result;
1808 }
1809
1810
1811 /// Position::compute_pawn_key() computes the hash key of the position.  The
1812 /// hash key is usually updated incrementally as moves are made and unmade,
1813 /// the compute_pawn_key() function is only used when a new position is set
1814 /// up, and to verify the correctness of the pawn hash key when running in
1815 /// debug mode.
1816
1817 Key Position::compute_pawn_key() const {
1818   Key result = Key(0ULL);
1819   Bitboard b;
1820   Square s;
1821
1822   for(Color c = WHITE; c <= BLACK; c++) {
1823     b = pawns(c);
1824     while(b) {
1825       s = pop_1st_bit(&b);
1826       result ^= zobrist[c][PAWN][s];
1827     }
1828   }
1829   return result;
1830 }
1831
1832
1833 /// Position::compute_material_key() computes the hash key of the position.
1834 /// The hash key is usually updated incrementally as moves are made and unmade,
1835 /// the compute_material_key() function is only used when a new position is set
1836 /// up, and to verify the correctness of the material hash key when running in
1837 /// debug mode.
1838
1839 Key Position::compute_material_key() const {
1840   Key result = Key(0ULL);
1841   for(Color c = WHITE; c <= BLACK; c++)
1842     for(PieceType pt = PAWN; pt <= QUEEN; pt++) {
1843       int count = piece_count(c, pt);
1844       for(int i = 0; i <= count; i++)
1845         result ^= zobMaterial[c][pt][i];
1846     }
1847   return result;
1848 }
1849
1850
1851 /// Position::compute_mg_value() and Position::compute_eg_value() compute the
1852 /// incremental scores for the middle game and the endgame.  These functions
1853 /// are used to initialize the incremental scores when a new position is set
1854 /// up, and to verify that the scores are correctly updated by do_move
1855 /// and undo_move when the program is running in debug mode.
1856
1857 Value Position::compute_mg_value() const {
1858   Value result = Value(0);
1859   Bitboard b;
1860   Square s;
1861
1862   for(Color c = WHITE; c <= BLACK; c++)
1863     for(PieceType pt = PAWN; pt <= KING; pt++) {
1864       b = pieces_of_color_and_type(c, pt);
1865       while(b) {
1866         s = pop_1st_bit(&b);
1867         assert(piece_on(s) == piece_of_color_and_type(c, pt));
1868         result += mg_pst(c, pt, s);
1869       }
1870     }
1871   result += (side_to_move() == WHITE)?
1872     (TempoValueMidgame / 2) : -(TempoValueMidgame / 2);
1873   return result;
1874 }
1875
1876 Value Position::compute_eg_value() const {
1877   Value result = Value(0);
1878   Bitboard b;
1879   Square s;
1880
1881   for(Color c = WHITE; c <= BLACK; c++)
1882     for(PieceType pt = PAWN; pt <= KING; pt++) {
1883       b = pieces_of_color_and_type(c, pt);
1884       while(b) {
1885         s = pop_1st_bit(&b);
1886         assert(piece_on(s) == piece_of_color_and_type(c, pt));
1887         result += eg_pst(c, pt, s);
1888       }
1889     }
1890   result += (side_to_move() == WHITE)?
1891     (TempoValueEndgame / 2) : -(TempoValueEndgame / 2);
1892   return result;
1893 }
1894
1895
1896 /// Position::compute_non_pawn_material() computes the total non-pawn middle
1897 /// game material score for the given side.  Material scores are updated
1898 /// incrementally during the search, this function is only used while
1899 /// initializing a new Position object.
1900
1901 Value Position::compute_non_pawn_material(Color c) const {
1902   Value result = Value(0);
1903   Square s;
1904
1905   for(PieceType pt = KNIGHT; pt <= QUEEN; pt++) {
1906     Bitboard b = pieces_of_color_and_type(c, pt);
1907     while(b) {
1908       s = pop_1st_bit(&b);
1909       assert(piece_on(s) == piece_of_color_and_type(c, pt));
1910       result += piece_value_midgame(pt);
1911     }
1912   }
1913   return result;
1914 }
1915
1916
1917 /// Position::is_mate() returns true or false depending on whether the
1918 /// side to move is checkmated.  Note that this function is currently very
1919 /// slow, and shouldn't be used frequently inside the search.
1920
1921 bool Position::is_mate() {
1922   if(is_check()) {
1923     MovePicker mp = MovePicker(*this, false, MOVE_NONE, MOVE_NONE, MOVE_NONE,
1924                                MOVE_NONE, Depth(0));
1925     return mp.get_next_move() == MOVE_NONE;
1926   }
1927   else
1928     return false;
1929 }
1930
1931
1932 /// Position::is_draw() tests whether the position is drawn by material,
1933 /// repetition, or the 50 moves rule.  It does not detect stalemates, this
1934 /// must be done by the search.
1935
1936 bool Position::is_draw() const {
1937   // Draw by material?
1938   if(!pawns() &&
1939      non_pawn_material(WHITE) + non_pawn_material(BLACK)
1940      <= BishopValueMidgame)
1941     return true;
1942
1943   // Draw by the 50 moves rule?
1944   if(rule50 > 100 || (rule50 == 100 && !is_check()))
1945     return true;
1946
1947   // Draw by repetition?
1948   for(int i = 2; i < Min(gamePly, rule50); i += 2)
1949     if(history[gamePly - i] == key)
1950       return true;
1951
1952   return false;
1953 }
1954
1955
1956 /// Position::has_mate_threat() tests whether a given color has a mate in one
1957 /// from the current position.  This function is quite slow, but it doesn't
1958 /// matter, because it is currently only called from PV nodes, which are rare.
1959
1960 bool Position::has_mate_threat(Color c) {
1961   UndoInfo u1, u2;
1962   Color stm = side_to_move();
1963
1964   // The following lines are useless and silly, but prevents gcc from
1965   // emitting a stupid warning stating that u1.lastMove and u1.epSquare might
1966   // be used uninitialized.
1967   u1.lastMove = lastMove;
1968   u1.epSquare = epSquare;
1969
1970   if(is_check())
1971     return false;
1972
1973   // If the input color is not equal to the side to move, do a null move
1974   if(c != stm) do_null_move(u1);
1975
1976   MoveStack mlist[120];
1977   int count;
1978   bool result = false;
1979
1980   // Generate legal moves
1981   count = generate_legal_moves(*this, mlist);
1982
1983   // Loop through the moves, and see if one of them is mate.
1984   for(int i = 0; i < count; i++) {
1985     do_move(mlist[i].move, u2);
1986     if(is_mate()) result = true;
1987     undo_move(mlist[i].move, u2);
1988   }
1989
1990   // Undo null move, if necessary
1991   if(c != stm) undo_null_move(u1);
1992
1993   return result;
1994 }
1995
1996
1997 /// Position::init_zobrist() is a static member function which initializes the
1998 /// various arrays used to compute hash keys.
1999
2000 void Position::init_zobrist() {
2001
2002   for(int i = 0; i < 2; i++)
2003     for(int j = 0; j < 8; j++)
2004       for(int k = 0; k < 64; k++)
2005         zobrist[i][j][k] = Key(genrand_int64());
2006
2007   for(int i = 0; i < 64; i++)
2008     zobEp[i] = Key(genrand_int64());
2009
2010   for(int i = 0; i < 16; i++)
2011     zobCastle[i] = genrand_int64();
2012
2013   zobSideToMove = genrand_int64();
2014
2015   for(int i = 0; i < 2; i++)
2016     for(int j = 0; j < 8; j++)
2017       for(int k = 0; k < 16; k++)
2018         zobMaterial[i][j][k] = (k > 0)? Key(genrand_int64()) : Key(0LL);
2019
2020   for(int i = 0; i < 16; i++)
2021     zobMaterial[0][KING][i] = zobMaterial[1][KING][i] = Key(0ULL);
2022 }
2023
2024
2025 /// Position::init_piece_square_tables() initializes the piece square tables.
2026 /// This is a two-step operation:  First, the white halves of the tables are
2027 /// copied from the MgPST[][] and EgPST[][] arrays, with a small random number
2028 /// added to each entry if the "Randomness" UCI parameter is non-zero.
2029 /// Second, the black halves of the tables are initialized by mirroring
2030 /// and changing the sign of the corresponding white scores.
2031
2032 void Position::init_piece_square_tables() {
2033   int r = get_option_value_int("Randomness"), i;
2034   for(Square s = SQ_A1; s <= SQ_H8; s++) {
2035     for(Piece p = WP; p <= WK; p++) {
2036       i = (r == 0)? 0 : (genrand_int32() % (r*2) - r);
2037       MgPieceSquareTable[p][s] = Value(MgPST[p][s] + i);
2038       EgPieceSquareTable[p][s] = Value(EgPST[p][s] + i);
2039     }
2040   }
2041   for(Square s = SQ_A1; s <= SQ_H8; s++)
2042     for(Piece p = BP; p <= BK; p++) {
2043       MgPieceSquareTable[p][s] = -MgPieceSquareTable[p-8][flip_square(s)];
2044       EgPieceSquareTable[p][s] = -EgPieceSquareTable[p-8][flip_square(s)];
2045     }
2046 }
2047
2048
2049 /// Position::flipped_copy() makes a copy of the input position, but with
2050 /// the white and black sides reversed.  This is only useful for debugging,
2051 /// especially for finding evaluation symmetry bugs.
2052
2053 void Position::flipped_copy(const Position &pos) {
2054   assert(pos.is_ok());
2055
2056   clear();
2057
2058   // Board
2059   for(Square s = SQ_A1; s <= SQ_H8; s++)
2060     if(!pos.square_is_empty(s))
2061       put_piece(Piece(int(pos.piece_on(s)) ^ 8), flip_square(s));
2062
2063   // Side to move
2064   sideToMove = opposite_color(pos.side_to_move());
2065
2066   // Castling rights
2067   if(pos.can_castle_kingside(WHITE)) allow_oo(BLACK);
2068   if(pos.can_castle_queenside(WHITE)) allow_ooo(BLACK);
2069   if(pos.can_castle_kingside(BLACK)) allow_oo(WHITE);
2070   if(pos.can_castle_queenside(BLACK)) allow_ooo(WHITE);
2071
2072   initialKFile = pos.initialKFile;
2073   initialKRFile = pos.initialKRFile;
2074   initialQRFile = pos.initialQRFile;
2075
2076   for(Square sq = SQ_A1; sq <= SQ_H8; sq++)
2077     castleRightsMask[sq] = ALL_CASTLES;
2078   castleRightsMask[make_square(initialKFile, RANK_1)] ^= (WHITE_OO|WHITE_OOO);
2079   castleRightsMask[make_square(initialKFile, RANK_8)] ^= (BLACK_OO|BLACK_OOO);
2080   castleRightsMask[make_square(initialKRFile, RANK_1)] ^= WHITE_OO;
2081   castleRightsMask[make_square(initialKRFile, RANK_8)] ^= BLACK_OO;
2082   castleRightsMask[make_square(initialQRFile, RANK_1)] ^= WHITE_OOO;
2083   castleRightsMask[make_square(initialQRFile, RANK_8)] ^= BLACK_OOO;
2084
2085   // En passant square
2086   if(pos.epSquare != SQ_NONE)
2087     epSquare = flip_square(pos.epSquare);
2088
2089   // Checkers
2090   find_checkers();
2091
2092   // Hash keys
2093   key = compute_key();
2094   pawnKey = compute_pawn_key();
2095   materialKey = compute_material_key();
2096
2097   // Incremental scores
2098   mgValue = compute_mg_value();
2099   egValue = compute_eg_value();
2100
2101   // Material
2102   npMaterial[WHITE] = compute_non_pawn_material(WHITE);
2103   npMaterial[BLACK] = compute_non_pawn_material(BLACK);
2104
2105   assert(is_ok());
2106 }
2107
2108
2109 /// Position::is_ok() performs some consitency checks for the position object.
2110 /// This is meant to be helpful when debugging.
2111
2112 bool Position::is_ok(int* failedStep) const {
2113
2114   // What features of the position should be verified?
2115   static const bool debugBitboards = false;
2116   static const bool debugKingCount = false;
2117   static const bool debugKingCapture = false;
2118   static const bool debugCheckerCount = false;
2119   static const bool debugKey = false;
2120   static const bool debugMaterialKey = false;
2121   static const bool debugPawnKey = false;
2122   static const bool debugIncrementalEval = false;
2123   static const bool debugNonPawnMaterial = false;
2124   static const bool debugPieceCounts = false;
2125   static const bool debugPieceList = false;
2126
2127   if (failedStep) *failedStep = 1;
2128
2129   // Side to move OK?
2130   if(!color_is_ok(side_to_move()))
2131     return false;
2132
2133   // Are the king squares in the position correct?
2134   if (failedStep) (*failedStep)++;
2135   if(piece_on(king_square(WHITE)) != WK)
2136     return false;
2137
2138   if (failedStep) (*failedStep)++;
2139   if(piece_on(king_square(BLACK)) != BK)
2140     return false;
2141
2142   // Castle files OK?
2143   if (failedStep) (*failedStep)++;
2144   if(!file_is_ok(initialKRFile))
2145     return false;
2146   if(!file_is_ok(initialQRFile))
2147     return false;
2148
2149   // Do both sides have exactly one king?
2150   if (failedStep) (*failedStep)++;
2151   if(debugKingCount) {
2152     int kingCount[2] = {0, 0};
2153     for(Square s = SQ_A1; s <= SQ_H8; s++)
2154       if(type_of_piece_on(s) == KING)
2155         kingCount[color_of_piece_on(s)]++;
2156     if(kingCount[0] != 1 || kingCount[1] != 1)
2157       return false;
2158   }
2159
2160   // Can the side to move capture the opponent's king?
2161   if (failedStep) (*failedStep)++;
2162   if(debugKingCapture) {
2163     Color us = side_to_move();
2164     Color them = opposite_color(us);
2165     Square ksq = king_square(them);
2166     if(square_is_attacked(ksq, us))
2167       return false;
2168   }
2169
2170   // Is there more than 2 checkers?
2171   if (failedStep) (*failedStep)++;
2172   if(debugCheckerCount && count_1s(checkersBB) > 2)
2173     return false;
2174
2175   // Bitboards OK?
2176   if (failedStep) (*failedStep)++;
2177   if(debugBitboards) {
2178     // The intersection of the white and black pieces must be empty:
2179     if((pieces_of_color(WHITE) & pieces_of_color(BLACK))
2180        != EmptyBoardBB)
2181       return false;
2182
2183     // The union of the white and black pieces must be equal to all
2184     // occupied squares:
2185     if((pieces_of_color(WHITE) | pieces_of_color(BLACK))
2186        != occupied_squares())
2187       return false;
2188
2189     // Separate piece type bitboards must have empty intersections:
2190     for(PieceType p1 = PAWN; p1 <= KING; p1++)
2191       for(PieceType p2 = PAWN; p2 <= KING; p2++)
2192         if(p1 != p2 && (pieces_of_type(p1) & pieces_of_type(p2)))
2193           return false;
2194   }
2195
2196   // En passant square OK?
2197   if (failedStep) (*failedStep)++;
2198   if(ep_square() != SQ_NONE) {
2199     // The en passant square must be on rank 6, from the point of view of the
2200     // side to move.
2201     if(relative_rank(side_to_move(), ep_square()) != RANK_6)
2202       return false;
2203   }
2204
2205   // Hash key OK?
2206   if (failedStep) (*failedStep)++;
2207   if(debugKey && key != compute_key())
2208     return false;
2209
2210   // Pawn hash key OK?
2211   if (failedStep) (*failedStep)++;
2212   if(debugPawnKey && pawnKey != compute_pawn_key())
2213     return false;
2214
2215   // Material hash key OK?
2216   if (failedStep) (*failedStep)++;
2217   if(debugMaterialKey && materialKey != compute_material_key())
2218     return false;
2219
2220   // Incremental eval OK?
2221   if (failedStep) (*failedStep)++;
2222   if(debugIncrementalEval) {
2223     if(mgValue != compute_mg_value())
2224       return false;
2225     if(egValue != compute_eg_value())
2226       return false;
2227   }
2228
2229   // Non-pawn material OK?
2230   if (failedStep) (*failedStep)++;
2231   if(debugNonPawnMaterial) {
2232     if(npMaterial[WHITE] != compute_non_pawn_material(WHITE))
2233       return false;
2234     if(npMaterial[BLACK] != compute_non_pawn_material(BLACK))
2235       return false;
2236   }
2237
2238   // Piece counts OK?
2239   if (failedStep) (*failedStep)++;
2240   if(debugPieceCounts)
2241     for(Color c = WHITE; c <= BLACK; c++)
2242       for(PieceType pt = PAWN; pt <= KING; pt++)
2243         if(pieceCount[c][pt] != count_1s(pieces_of_color_and_type(c, pt)))
2244           return false;
2245
2246   if (failedStep) (*failedStep)++;
2247   if(debugPieceList) {
2248     for(Color c = WHITE; c <= BLACK; c++)
2249       for(PieceType pt = PAWN; pt <= KING; pt++)
2250         for(int i = 0; i < pieceCount[c][pt]; i++) {
2251           if(piece_on(piece_list(c, pt, i)) !=
2252              piece_of_color_and_type(c, pt))
2253             return false;
2254           if(index[piece_list(c, pt, i)] != i)
2255             return false;
2256         }
2257   }
2258   if (failedStep) *failedStep = 0;
2259   return true;
2260 }