&& (ss-1)->statScore < 17329
&& eval >= beta
&& eval >= ss->staticEval
- && ss->staticEval >= beta - 21 * depth - improvement * 99 / 1300 + 258
+ && ss->staticEval >= beta - 21 * depth - improvement / 13 + 258
&& !excludedMove
&& pos.non_pawn_material(us)
&& (ss->ply >= thisThread->nmpMinPly))
}
}
+ // Step 10. If the position doesn't a have ttMove, decrease depth by 2
+ // (or by 4 if the TT entry for the current position was hit and the stored depth is greater than or equal to the current depth).
+ // Use qsearch if depth is equal or below zero (~9 Elo)
+ if ( PvNode
+ && !ttMove)
+ depth -= 2 + 2 * (ss->ttHit && tte->depth() >= depth);
+
+ if (depth <= 0)
+ return qsearch<PV>(pos, ss, alpha, beta);
+
+ if ( cutNode
+ && depth >= 8
+ && !ttMove)
+ depth -= 2;
+
probCutBeta = beta + 168 - 61 * improving;
- // Step 10. ProbCut (~10 Elo)
+ // Step 11. ProbCut (~10 Elo)
// If we have a good enough capture (or queen promotion) and a reduced search returns a value
// much above beta, we can (almost) safely prune the previous move.
if ( !PvNode
Eval::NNUE::hint_common_parent_position(pos);
}
- // Step 11. If the position is not in TT, decrease depth by 2 (or by 4 if the TT entry for the current position was hit and the stored depth is greater than or equal to the current depth).
- // Use qsearch if depth is equal or below zero (~9 Elo)
- if ( PvNode
- && !ttMove)
- depth -= 2 + 2 * (ss->ttHit && tte->depth() >= depth);
-
- if (depth <= 0)
- return qsearch<PV>(pos, ss, alpha, beta);
-
- if ( cutNode
- && depth >= 8
- && !ttMove)
- depth -= 2;
-
moves_loop: // When in check, search starts here
// Step 12. A small Probcut idea, when we are in check (~4 Elo)
Bitboard occupied;
// SEE based pruning (~11 Elo)
- if (!pos.see_ge(move, occupied, Value(-212) * depth))
+ if (!pos.see_ge(move, occupied, Value(-205) * depth))
{
- // Don't prune the move if opponent King/Queen/Rook gets a discovered attack during or after the exchanges
- Bitboard leftEnemies = pos.pieces(~us, KING, QUEEN, ROOK);
- Bitboard attacks = 0;
- occupied |= to_sq(move);
- while (leftEnemies && !attacks)
- {
+ if (depth < 2 - capture)
+ continue;
+ // Don't prune the move if opponent Queen/Rook is under discovered attack after the exchanges
+ // Don't prune the move if opponent King is under discovered attack after or during the exchanges
+ Bitboard leftEnemies = (pos.pieces(~us, KING, QUEEN, ROOK)) & occupied;
+ Bitboard attacks = 0;
+ occupied |= to_sq(move);
+ while (leftEnemies && !attacks)
+ {
Square sq = pop_lsb(leftEnemies);
- attacks = pos.attackers_to(sq, occupied) & pos.pieces(us) & occupied;
- // Exclude Queen/Rook(s) which were already threatened before SEE (opponent King can't be in check when it's our turn)
- if (attacks && sq != pos.square<KING>(~us) && (pos.attackers_to(sq, pos.pieces()) & pos.pieces(us)))
- attacks = 0;
- }
- if (!attacks)
- continue;
+ attacks |= pos.attackers_to(sq, occupied) & pos.pieces(us) & occupied;
+ // don't consider pieces which were already threatened/hanging before SEE exchanges
+ if (attacks && (sq != pos.square<KING>(~us) && (pos.attackers_to(sq, pos.pieces()) & pos.pieces(us))))
+ attacks = 0;
+ }
+ if (!attacks)
+ continue;
}
}
else
}
// Check extensions (~1 Elo)
- else if ( givesCheck && depth > 8)
+ else if ( givesCheck
+ && depth > 9)
extension = 1;
// Quiet ttMove extensions (~1 Elo)
// to search the moves. Because the depth is <= 0 here, only captures,
// queen promotions, and other checks (only if depth >= DEPTH_QS_CHECKS)
// will be generated.
- Square prevSq = (ss-1)->currentMove != MOVE_NULL ? to_sq((ss-1)->currentMove) : SQ_NONE;
+ Square prevSq = is_ok((ss-1)->currentMove) ? to_sq((ss-1)->currentMove) : SQ_NONE;
MovePicker mp(pos, ttMove, depth, &thisThread->mainHistory,
&thisThread->captureHistory,
contHist,