diff --git a/src/search/pvs.rs b/src/search/pvs.rs index 448d5594..18ea43be 100644 --- a/src/search/pvs.rs +++ b/src/search/pvs.rs @@ -150,6 +150,7 @@ fn pvs( // Position and node type considerations. let is_check = position.is_check(); let may_be_zug = may_be_zugzwang(position); + let is_pv = alpha != beta - 1; // Null move pruning: if we "pass" our turn and still get a beta cutoff, // this position is far too good to be true. @@ -183,6 +184,23 @@ fn pvs( } } + // Internal iterative deepening: get a hash move from a reduced search. + // This is useless in most cases, but can be very useful in some + // where standard move ordering fails to be decent. + if is_pv && !is_check && !ROOT && depth >= 4 && table.get_hash_move(position).is_none() { + let (_, iid_count) = pvs::( + position, + depth.saturating_sub(2), + alpha, + beta, + table.clone(), + constraint, + history, + ply, + ); + count += iid_count; + } + // Prepare move generation and sorting. This is lazy and works in stages. let mut picker = MovePicker::::new(position, table.clone(), ply, ROOT && !MAIN_THREAD).peekable(); @@ -282,7 +300,7 @@ fn pvs( best_move, depth, ply, - ROOT && MAIN_THREAD, + ROOT, ); }