Add castling to generation of checking moves
authorMarco Costalba <mcostalba@gmail.com>
Sun, 8 Jan 2012 11:08:16 +0000 (12:08 +0100)
committerMarco Costalba <mcostalba@gmail.com>
Sun, 8 Jan 2012 11:28:51 +0000 (12:28 +0100)
During generation of non-captures checks (in qsearch)
we don't consider castling moves that give check,
this patch includes also this rare case. Verified with
perft that all the non-capture checks are now generated.

There should be a very little slowdown due to the extra
work, but actually I failed to measure it. I don't expect
any ELO improvment, there is even no functional change on
the standard depth 12 search, it is just to have a correct
move generator.

Signed-off-by: Marco Costalba <mcostalba@gmail.com>
src/movegen.cpp

index 272807b9aa4b4444adf81250dba2c90c2d9459bf..1820fee2fbcb2af58aeeacae07db46df9e126efb 100644 (file)
@@ -34,7 +34,7 @@ namespace {
 
   enum CastlingSide { KING_SIDE, QUEEN_SIDE };
 
-  template<CastlingSide Side>
+  template<CastlingSide Side, bool OnlyChecks>
   MoveStack* generate_castle_moves(const Position& pos, MoveStack* mlist, Color us) {
 
     const CastleRight CR[] = { Side ? WHITE_OOO : WHITE_OO,
@@ -81,6 +81,9 @@ namespace {
 
     (*mlist++).move = make_castle(kfrom, rfrom);
 
+    if (OnlyChecks && !pos.move_gives_check((mlist - 1)->move, CheckInfo(pos)))
+        mlist--;
+
     return mlist;
   }
 
@@ -360,8 +363,8 @@ MoveStack* generate(const Position& pos, MoveStack* mlist) {
 
   if (Type != MV_CAPTURE && pos.can_castle(us))
   {
-      mlist = generate_castle_moves<KING_SIDE>(pos, mlist, us);
-      mlist = generate_castle_moves<QUEEN_SIDE>(pos, mlist, us);
+      mlist = generate_castle_moves<KING_SIDE, false>(pos, mlist, us);
+      mlist = generate_castle_moves<QUEEN_SIDE, false>(pos, mlist, us);
   }
 
   return mlist;
@@ -410,7 +413,15 @@ MoveStack* generate<MV_NON_CAPTURE_CHECK>(const Position& pos, MoveStack* mlist)
   mlist = generate_direct_checks<KNIGHT>(pos, mlist, us, dc, ksq);
   mlist = generate_direct_checks<BISHOP>(pos, mlist, us, dc, ksq);
   mlist = generate_direct_checks<ROOK>(pos, mlist, us, dc, ksq);
-  return  generate_direct_checks<QUEEN>(pos, mlist, us, dc, ksq);
+  mlist = generate_direct_checks<QUEEN>(pos, mlist, us, dc, ksq);
+
+  if (pos.can_castle(us))
+  {
+      mlist = generate_castle_moves<KING_SIDE, true>(pos, mlist, us);
+      mlist = generate_castle_moves<QUEEN_SIDE, true>(pos, mlist, us);
+  }
+
+  return mlist;
 }