- if ( pos.is_capture(threat)
- && ( PieceValue[Mg][pos.piece_on(tfrom)] >= PieceValue[Mg][pos.piece_on(tto)]
- || type_of(pos.piece_on(tfrom)) == KING)
- && pos.move_attacks_square(m, tto))
- return true;
+ if ( pos.is_capture(threat)
+ && ( PieceValue[MG][pos.piece_on(tfrom)] >= PieceValue[MG][pos.piece_on(tto)]
+ || type_of(pos.piece_on(tfrom)) == KING))
+ {
+ // Update occupancy as if the piece and the threat are moving
+ Bitboard occ = pos.pieces() ^ mfrom ^ mto ^ tfrom;
+ Piece piece = pos.piece_on(mfrom);
+
+ // The moved piece attacks the square 'tto' ?
+ if (pos.attacks_from(piece, mto, occ) & tto)
+ return true;
+
+ // Scan for possible X-ray attackers behind the moved piece
+ Bitboard xray = (attacks_bb< ROOK>(tto, occ) & pos.pieces(color_of(piece), QUEEN, ROOK))
+ | (attacks_bb<BISHOP>(tto, occ) & pos.pieces(color_of(piece), QUEEN, BISHOP));
+
+ // Verify attackers are triggered by our move and not already existing
+ if (xray && (xray ^ (xray & pos.attacks_from<QUEEN>(tto))))
+ return true;
+ }