From 5e91c5dcc8066e9f346a10010ddce70f2d317ef6 Mon Sep 17 00:00:00 2001 From: Vizvezdenec Date: Sat, 11 Jul 2020 00:06:55 +0300 Subject: [PATCH 1/9] Maximize usage of transposition table in probcut Probcut is a heuristic that wasn't changed a lot in past years, all attempts to change it using information / writing info to transposition table failed. This patch has a number of differences that can be summarized as follows: * For TT write/read we use depth - 3. Because probcut search is depth - 4 but we actually do the move prior to it so effectively we do depth - 3 search; * In any case of depth of eval from transposition table being >= depth - 3 we either produce cutoff or refuse to even do probcut search, this is allowing us to write info of probcut to transposition table because we know that we wouldn't be overwriting some deeper data with our depth - 3 search - this is an important aspect of this patch; * For some not really known reason this patch completely ignores tte->bound() - which was the case for previous patch that made probcut interact with TT, maybe 2) is the reason, although it's unproven. A first version of this patch passed STC and LTC passed STC https://tests.stockfishchess.org/tests/view/5f05908a59f6f03532894613 LLR: 2.95 (-2.94,2.94) {-0.50,1.50} Total: 95776 W: 18300 L: 17973 D: 59503 Ptnml(0-2): 1646, 10944, 22377, 11279, 1642 passed LTC https://tests.stockfishchess.org/tests/view/5f06b54059f6f035328946bb LLR: 2.94 (-2.94,2.94) {0.25,1.75} Total: 57128 W: 7266 L: 6938 D: 42924 Ptnml(0-2): 372, 5163, 17217, 5389, 423 However, an additional bugfix was needed to avoid checking a condition on ttMove if was not available. This passed non-regression bounds on top of the first version: at STC https://tests.stockfishchess.org/tests/view/5f080e5059f6f03532894766 LLR: 2.94 (-2.94,2.94) {-1.50,0.50} Total: 14096 W: 2800 L: 2628 D: 8668 Ptnml(0-2): 225, 1620, 3238, 1688, 277 at LTC https://tests.stockfishchess.org/tests/view/5f0836a559f6f0353289479c LLR: 2.95 (-2.94,2.94) {-1.50,0.50} Total: 25352 W: 3228 L: 3139 D: 18985 Ptnml(0-2): 175, 2350, 7549, 2415, 187 closes https://github.com/official-stockfish/Stockfish/pull/2804 Bench 4540940 --- src/search.cpp | 41 ++++++++++++++++++++++++++++------------- 1 file changed, 28 insertions(+), 13 deletions(-) diff --git a/src/search.cpp b/src/search.cpp index 720a91009..6cf2f90d4 100644 --- a/src/search.cpp +++ b/src/search.cpp @@ -596,7 +596,7 @@ namespace { Key posKey; Move ttMove, move, excludedMove, bestMove; Depth extension, newDepth; - Value bestValue, value, ttValue, eval, maxValue; + Value bestValue, value, ttValue, eval, maxValue, probcutBeta; bool ttHit, ttPv, formerPv, givesCheck, improving, didLMR, priorCapture; bool captureOrPromotion, doFullDepthSearch, moveCountPruning, ttCapture, singularQuietLMR; @@ -871,23 +871,33 @@ namespace { } } + probcutBeta = beta + 176 - 49 * improving; + // Step 10. ProbCut (~10 Elo) // If we have a good enough capture and a reduced search returns a value // much above beta, we can (almost) safely prune the previous move. if ( !PvNode && depth > 4 - && abs(beta) < VALUE_TB_WIN_IN_MAX_PLY) + && abs(beta) < VALUE_TB_WIN_IN_MAX_PLY + && !( ttHit + && tte->depth() >= depth - 3 + && ttValue != VALUE_NONE + && ttValue < probcutBeta)) { - Value raisedBeta = beta + 176 - 49 * improving; - assert(raisedBeta < VALUE_INFINITE); - MovePicker mp(pos, ttMove, raisedBeta - ss->staticEval, &captureHistory); + if ( ttHit + && tte->depth() >= depth - 3 + && ttValue != VALUE_NONE + && ttValue >= probcutBeta + && ttMove + && pos.capture_or_promotion(ttMove)) + return probcutBeta; + + assert(probcutBeta < VALUE_INFINITE); + MovePicker mp(pos, ttMove, probcutBeta - ss->staticEval, &captureHistory); int probCutCount = 0; while ( (move = mp.next_move()) != MOVE_NONE - && probCutCount < 2 + 2 * cutNode - && !( move == ttMove - && tte->depth() >= depth - 4 - && ttValue < raisedBeta)) + && probCutCount < 2 + 2 * cutNode) if (move != excludedMove && pos.legal(move)) { assert(pos.capture_or_promotion(move)); @@ -905,16 +915,21 @@ namespace { pos.do_move(move, st); // Perform a preliminary qsearch to verify that the move holds - value = -qsearch(pos, ss+1, -raisedBeta, -raisedBeta+1); + value = -qsearch(pos, ss+1, -probcutBeta, -probcutBeta+1); // If the qsearch held, perform the regular search - if (value >= raisedBeta) - value = -search(pos, ss+1, -raisedBeta, -raisedBeta+1, depth - 4, !cutNode); + if (value >= probcutBeta) + value = -search(pos, ss+1, -probcutBeta, -probcutBeta+1, depth - 4, !cutNode); pos.undo_move(move); - if (value >= raisedBeta) + if (value >= probcutBeta) + { + tte->save(posKey, value_to_tt(value, ss->ply), ttPv, + BOUND_LOWER, + depth - 3, move, ss->staticEval); return value; + } } } From 1f3bd968bb194a1f42af661cca9ec445c13978e8 Mon Sep 17 00:00:00 2001 From: SFisGOD Date: Wed, 8 Jul 2020 10:09:32 +0800 Subject: [PATCH 2/9] Introduce bad outpost penalty In some French games, Stockfish likes to bring the Knight to a bad outpost spot. This is evident in TCEC S18 Superfinal Game 63, where there is a Knight outpost on the queenside but is actually useless. Stockfish is effectively playing a piece down while holding ground against Leela's break on the kingside. This patch turns the +56 mg bonus for a Knight outpost into a -7 mg penalty if it satisfies the following conditions: * The outpost square is not on the CenterFiles (i.e. not on files C,D,E and F) * The knight is not attacking non pawn enemies. * The side where the outpost is located contains only few enemies, with a particular conditional_more_than_two() implementation Thank you to apospa...@gmail.com for bringing this to our attention and for providing insights. See https://groups.google.com/forum/?fromgroups=#!topic/fishcooking/dEXNzSIBgZU Reference game: https://tcec-chess.com/#div=sf&game=63&season=18 Passed STC: LLR: 2.93 (-2.94,2.94) {-0.50,1.50} Total: 6960 W: 1454 L: 1247 D: 4259 Ptnml(0-2): 115, 739, 1610, 856, 160 https://tests.stockfishchess.org/tests/view/5f08221059f6f0353289477e Passed LTC: LLR: 2.98 (-2.94,2.94) {0.25,1.75} Total: 21440 W: 2767 L: 2543 D: 16130 Ptnml(0-2): 122, 1904, 6462, 2092, 140 https://tests.stockfishchess.org/tests/view/5f0838ed59f6f035328947a2 various related tests show strong test results, but so far no generalizations or simplifications of conditional_more_than_two() are found. See PR for details. closes https://github.com/official-stockfish/Stockfish/pull/2803 Bench: 4366686 --- src/bitboard.h | 7 +++++++ src/evaluate.cpp | 9 ++++++++- 2 files changed, 15 insertions(+), 1 deletion(-) diff --git a/src/bitboard.h b/src/bitboard.h index afeb40ec1..15ec41533 100644 --- a/src/bitboard.h +++ b/src/bitboard.h @@ -130,6 +130,13 @@ constexpr bool more_than_one(Bitboard b) { return b & (b - 1); } +/// Counts the occupation of the bitboard depending on the occupation of SQ_A1 +/// as in `b & (1ULL << SQ_A1) ? more_than_two(b) : more_than_one(b)` + +constexpr bool conditional_more_than_two(Bitboard b) { + return b & (b - 1) & (b - 2); +} + constexpr bool opposite_colors(Square s1, Square s2) { return (s1 + rank_of(s1) + s2 + rank_of(s2)) & 1; } diff --git a/src/evaluate.cpp b/src/evaluate.cpp index 6f2dd69ba..ca6ea5c44 100644 --- a/src/evaluate.cpp +++ b/src/evaluate.cpp @@ -134,6 +134,7 @@ namespace { }; // Assorted bonuses and penalties + constexpr Score BadOutpost = S( -7, 36); constexpr Score BishopOnKingRing = S( 24, 0); constexpr Score BishopPawns = S( 3, 7); constexpr Score BishopXRayPawns = S( 4, 5); @@ -310,7 +311,13 @@ namespace { { // Bonus if piece is on an outpost square or can reach one bb = OutpostRanks & attackedBy[Us][PAWN] & ~pe->pawn_attacks_span(Them); - if (bb & s) + if ( Pt == KNIGHT + && bb & s & ~CenterFiles + && !(b & pos.pieces(Them) & ~pos.pieces(PAWN)) + && !conditional_more_than_two( + pos.pieces(Them) & ~pos.pieces(PAWN) & (s & QueenSide ? QueenSide : KingSide))) + score += BadOutpost; + else if (bb & s) score += Outpost[Pt == BISHOP]; else if (Pt == KNIGHT && bb & b & ~pos.pieces(Us)) score += ReachableOutpost; From 6c197c3964ca0c637ff1f646dc7e6653b1bb4b45 Mon Sep 17 00:00:00 2001 From: syzygy1 <3028851+syzygy1@users.noreply.github.com> Date: Sat, 11 Jul 2020 16:25:34 +0200 Subject: [PATCH 3/9] Corrects a functional change in a cleanup patch. This corrects a functional change in https://github.com/official-stockfish/Stockfish/commit/ddcbacd04d1c860e808202ce8c1206c8acdca627 changing evaluation of KPPvK. Bench remains unchanged at low depth With this patch, 8/8/5k1p/8/7p/7K/8/8 b - - 1 11 is again correctly evaluated as a draw. closes https://github.com/official-stockfish/Stockfish/pull/2807 Bench: 4366686 --- src/endgame.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/endgame.cpp b/src/endgame.cpp index 40f49dce5..a8ceb6487 100644 --- a/src/endgame.cpp +++ b/src/endgame.cpp @@ -589,8 +589,8 @@ ScaleFactor Endgame::operator()(const Position& pos) const { Bitboard strongPawns = pos.pieces(strongSide, PAWN); // If all pawns are ahead of the king on a single rook file, it's a draw. - if (!((strongPawns & ~FileABB) || (strongPawns & ~FileHBB)) && - !(strongPawns & ~passed_pawn_span(weakSide, weakKing))) + if ( !(strongPawns & ~(FileABB | FileHBB)) + && !(strongPawns & ~passed_pawn_span(weakSide, weakKing))) return SCALE_FACTOR_DRAW; return SCALE_FACTOR_NONE; From c3092c54bc6fb837137365fc60eb57bd188deaca Mon Sep 17 00:00:00 2001 From: mstembera Date: Sun, 12 Jul 2020 13:58:00 -0700 Subject: [PATCH 4/9] Multiple lazy stages. An extension of the lazy eval idea: when the score is sufficiently large we now skip more granular parts of the eval. Inspired by an original patch by Moez Jellouli https://tests.stockfishchess.org/tests/view/5f03b2a159f6f03532894529 Credit to him! STC https://tests.stockfishchess.org/tests/view/5f0a862c59f6f03532894924 LLR: 2.95 (-2.94,2.94) {-0.50,1.50} Total: 13504 W: 2684 L: 2472 D: 8348 Ptnml(0-2): 229, 1496, 3111, 1666, 250 LTC https://tests.stockfishchess.org/tests/view/5f0ac0e159f6f0353289495b LLR: 2.94 (-2.94,2.94) {0.25,1.75} Total: 31312 W: 3926 L: 3677 D: 23709 Ptnml(0-2): 185, 2773, 9509, 2986, 203 closes https://github.com/official-stockfish/Stockfish/pull/2814 bench: 4541608 --- src/evaluate.cpp | 25 +++++++++++++++++-------- 1 file changed, 17 insertions(+), 8 deletions(-) diff --git a/src/evaluate.cpp b/src/evaluate.cpp index ca6ea5c44..dbb725d4d 100644 --- a/src/evaluate.cpp +++ b/src/evaluate.cpp @@ -74,7 +74,8 @@ using namespace Trace; namespace { // Threshold for lazy and space evaluation - constexpr Value LazyThreshold = Value(1400); + constexpr Value LazyThreshold1 = Value(1400); + constexpr Value LazyThreshold2 = Value(1300); constexpr Value SpaceThreshold = Value(12222); // KingAttackWeights[PieceType] contains king attack weights by piece type @@ -786,7 +787,7 @@ namespace { && pos.non_pawn_material(BLACK) == RookValueMg && pos.count(strongSide) - pos.count(~strongSide) <= 1 && bool(KingSide & pos.pieces(strongSide, PAWN)) != bool(QueenSide & pos.pieces(strongSide, PAWN)) - && (attackedBy[~strongSide][KING] & pos.pieces(~strongSide, PAWN))) + && (attacks_bb(pos.square(~strongSide)) & pos.pieces(~strongSide, PAWN))) sf = 36; else if (pos.count() == 1) sf = 37 + 3 * (pos.count(WHITE) == 1 ? pos.count(BLACK) + pos.count(BLACK) @@ -837,9 +838,12 @@ namespace { score += pe->pawn_score(WHITE) - pe->pawn_score(BLACK); // Early exit if score is high - Value v = (mg_value(score) + eg_value(score)) / 2; - if (abs(v) > LazyThreshold + pos.non_pawn_material() / 64) - return pos.side_to_move() == WHITE ? v : -v; + auto lazy_skip = [&](Value lazyThreshold) { + return abs(mg_value(score) + eg_value(score)) / 2 > lazyThreshold + pos.non_pawn_material() / 64; + }; + + if (lazy_skip(LazyThreshold1)) + goto make_v; // Main evaluation begins here initialize(); @@ -856,12 +860,17 @@ namespace { // More complex interactions that require fully populated attack bitboards score += king< WHITE>() - king< BLACK>() - + threats() - threats() - + passed< WHITE>() - passed< BLACK>() + + passed< WHITE>() - passed< BLACK>(); + + if (lazy_skip(LazyThreshold2)) + goto make_v; + + score += threats() - threats() + space< WHITE>() - space< BLACK>(); +make_v: // Derive single value from mg and eg parts of score - v = winnable(score); + Value v = winnable(score); // In case of tracing add all remaining individual evaluation terms if (T) From d89730d5c8dcf10eb9e1d91a81f903d9fc3c949a Mon Sep 17 00:00:00 2001 From: Vizvezdenec Date: Mon, 13 Jul 2020 20:30:58 +0300 Subject: [PATCH 5/9] Do not overwrite valuable TT data after probcut. This patch allows an engine to write probcut data only in case the probcut search depth is greater than transposition table depth. passed STC https://tests.stockfishchess.org/tests/view/5f0b52e959f6f035328949a6 LLR: 2.97 (-2.94,2.94) {-0.50,1.50} Total: 52544 W: 10145 L: 9880 D: 32519 Ptnml(0-2): 853, 6097, 12121, 6334, 867 passed LTC https://tests.stockfishchess.org/tests/view/5f0bd94c59f6f035328949f3 LLR: 2.93 (-2.94,2.94) {0.25,1.75} Total: 49576 W: 6164 L: 5863 D: 37549 Ptnml(0-2): 297, 4371, 15218, 4538, 364 closes https://github.com/official-stockfish/Stockfish/pull/2815 bench 4578298 --- src/search.cpp | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/src/search.cpp b/src/search.cpp index 6cf2f90d4..17ccab925 100644 --- a/src/search.cpp +++ b/src/search.cpp @@ -925,9 +925,12 @@ namespace { if (value >= probcutBeta) { - tte->save(posKey, value_to_tt(value, ss->ply), ttPv, - BOUND_LOWER, - depth - 3, move, ss->staticEval); + if ( !(ttHit + && tte->depth() >= depth - 3 + && ttValue != VALUE_NONE)) + tte->save(posKey, value_to_tt(value, ss->ply), ttPv, + BOUND_LOWER, + depth - 3, move, ss->staticEval); return value; } } From f0abde241d39ee4507778bf41b392492c5391652 Mon Sep 17 00:00:00 2001 From: protonspring Date: Sat, 25 Jul 2020 07:32:19 -0600 Subject: [PATCH 6/9] Remove conditional_more_than_two(). This is a functional simplification that removes the conditional_more_than_two() function, which was quite strange and kooky. Note the very minor change to the bench value. See this thread for relevant comments on the passing branch: protonspring/Stockfish@d89730d...ff35b50 STC LLR: 2.95 (-2.94,2.94) {-1.50,0.50} Total: 59760 W: 11411 L: 11311 D: 37038 Ptnml(0-2): 992, 6863, 14044, 7015, 966 https://tests.stockfishchess.org/tests/view/5f179988c09435d870cb9b9a LTC LLR: 2.93 (-2.94,2.94) {-1.50,0.50} Total: 45208 W: 5553 L: 5497 D: 34158 Ptnml(0-2): 315, 4081, 13761, 4127, 320 https://tests.stockfishchess.org/tests/view/5f184847c09435d870cb9bee closes https://github.com/official-stockfish/Stockfish/pull/2826 Bench: 4578290 --- src/bitboard.h | 6 ------ src/evaluate.cpp | 12 +++++++----- 2 files changed, 7 insertions(+), 11 deletions(-) diff --git a/src/bitboard.h b/src/bitboard.h index 15ec41533..8c95de8c6 100644 --- a/src/bitboard.h +++ b/src/bitboard.h @@ -130,12 +130,6 @@ constexpr bool more_than_one(Bitboard b) { return b & (b - 1); } -/// Counts the occupation of the bitboard depending on the occupation of SQ_A1 -/// as in `b & (1ULL << SQ_A1) ? more_than_two(b) : more_than_one(b)` - -constexpr bool conditional_more_than_two(Bitboard b) { - return b & (b - 1) & (b - 2); -} constexpr bool opposite_colors(Square s1, Square s2) { return (s1 + rank_of(s1) + s2 + rank_of(s2)) & 1; diff --git a/src/evaluate.cpp b/src/evaluate.cpp index dbb725d4d..d16648a84 100644 --- a/src/evaluate.cpp +++ b/src/evaluate.cpp @@ -310,13 +310,15 @@ namespace { if (Pt == BISHOP || Pt == KNIGHT) { - // Bonus if piece is on an outpost square or can reach one + // Bonus if the piece is on an outpost square or can reach one + // Reduced bonus for knights (BadOutpost) if few relevant targets bb = OutpostRanks & attackedBy[Us][PAWN] & ~pe->pawn_attacks_span(Them); + Bitboard targets = pos.pieces(Them) & ~pos.pieces(PAWN); + if ( Pt == KNIGHT - && bb & s & ~CenterFiles - && !(b & pos.pieces(Them) & ~pos.pieces(PAWN)) - && !conditional_more_than_two( - pos.pieces(Them) & ~pos.pieces(PAWN) & (s & QueenSide ? QueenSide : KingSide))) + && bb & s & ~CenterFiles // on a side outpost + && !(b & targets) // no relevant attacks + && (!more_than_one(targets & (s & QueenSide ? QueenSide : KingSide)))) score += BadOutpost; else if (bb & s) score += Outpost[Pt == BISHOP]; From 62d3106caa2f5acf5ba32500cc19912b8f10612c Mon Sep 17 00:00:00 2001 From: UnaiCorzo Date: Sat, 25 Jul 2020 22:30:05 +0200 Subject: [PATCH 7/9] Remove late irreversible move extension We simplify away the late irreversible move extension, which does not seem to be necessary in the current master. STC LLR: 2.93 (-2.94,2.94) {-1.50,0.50} Total: 38584 W: 7464 L: 7342 D: 23778 Ptnml(0-2): 581, 4328, 9365, 4424, 594 https://tests.stockfishchess.org/tests/view/5f1c9669c09435d870cb9de9 LTC LLR: 2.94 (-2.94,2.94) {-1.50,0.50} Total: 27840 W: 3417 L: 3353 D: 21070 Ptnml(0-2): 120, 2315, 8994, 2363, 128 https://tests.stockfishchess.org/tests/view/5f1d2e22c09435d870cb9e21 closes https://github.com/official-stockfish/Stockfish/pull/2836 bench: 4829420 --- src/search.cpp | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/src/search.cpp b/src/search.cpp index 17ccab925..6ec4d8032 100644 --- a/src/search.cpp +++ b/src/search.cpp @@ -1067,7 +1067,7 @@ namespace { // search of (alpha-s, beta-s), and just one fails high on (alpha, beta), // then that move is singular and should be extended. To verify this we do // a reduced search on all the other moves but the ttMove and if the - // result is lower than ttValue minus a margin then we will extend the ttMove. + // result is lower than ttValue minus a margin, then we will extend the ttMove. if ( depth >= 6 && move == ttMove && !rootNode @@ -1131,12 +1131,6 @@ namespace { if (type_of(move) == CASTLING) extension = 1; - // Late irreversible move extension - if ( move == ttMove - && pos.rule50_count() > 80 - && (captureOrPromotion || type_of(movedPiece) == PAWN)) - extension = 2; - // Add extension to new depth newDepth += extension; From 33f3cfae0093b934563e1eca78486261f18e4650 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?St=C3=A9phane=20Nicolet?= Date: Tue, 28 Jul 2020 10:08:09 +0200 Subject: [PATCH 8/9] Improve handling of queen imbalance We double the bonus for potential threats by minors and rooks against our queen, in case of "queen vs pieces imbalance". Hopefully this will improve a little bit the evaluation for this well-known Stockfish weakness. passed STC: LLR: 2.93 (-2.94,2.94) {-0.50,1.50} Total: 72976 W: 14003 L: 13710 D: 45263 Ptnml(0-2): 1218, 8370, 17094, 8513, 1293 https://tests.stockfishchess.org/tests/view/5efa50eb020eec13834a977d passed LTC: LLR: 2.93 (-2.94,2.94) {0.25,1.75} Total: 22232 W: 2779 L: 2560 D: 16893 Ptnml(0-2): 129, 1885, 6896, 2050, 156 https://tests.stockfishchess.org/tests/view/5f1fdd2dc09435d870cb9f13 closes https://github.com/official-stockfish/Stockfish/pull/2864 Bench: 4367349 --- src/evaluate.cpp | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/src/evaluate.cpp b/src/evaluate.cpp index d16648a84..b34d82f66 100644 --- a/src/evaluate.cpp +++ b/src/evaluate.cpp @@ -579,17 +579,21 @@ namespace { // Bonus for threats on the next moves against enemy queen if (pos.count(Them) == 1) { + bool queenImbalance = pos.count() == 1; + Square s = pos.square(Them); - safe = mobilityArea[Us] & ~stronglyProtected; + safe = mobilityArea[Us] + & ~pos.pieces(Us, PAWN) + & ~stronglyProtected; b = attackedBy[Us][KNIGHT] & attacks_bb(s); - score += KnightOnQueen * popcount(b & safe); + score += KnightOnQueen * popcount(b & safe) * (1 + queenImbalance); b = (attackedBy[Us][BISHOP] & attacks_bb(s, pos.pieces())) | (attackedBy[Us][ROOK ] & attacks_bb(s, pos.pieces())); - score += SliderOnQueen * popcount(b & safe & attackedBy2[Us]); + score += SliderOnQueen * popcount(b & safe & attackedBy2[Us]) * (1 + queenImbalance); } if (T) From 9587eeeb5ed29f834d4f956b92e0e732877c47a7 Mon Sep 17 00:00:00 2001 From: Stefan Geschwentner Date: Thu, 30 Jul 2020 18:56:11 +0200 Subject: [PATCH 9/9] Tweak cutnode reduction Less reduction for second move at non-check CUT node with depth <= 10. STC: LLR: 2.94 (-2.94,2.94) {-0.50,1.50} Total: 38680 W: 7490 L: 7245 D: 23945 Ptnml(0-2): 643, 4441, 8967, 4606, 683 https://tests.stockfishchess.org/tests/view/5f21e1782f7e63962b99f451 LTC: LLR: 2.95 (-2.94,2.94) {0.25,1.75} Total: 71976 W: 9003 L: 8636 D: 54337 Ptnml(0-2): 440, 6414, 21972, 6663, 499 https://tests.stockfishchess.org/tests/view/5f2245762f7e63962b99f4bd closes https://github.com/official-stockfish/Stockfish/pull/2868 Bench: 4746616 --- src/search.cpp | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/src/search.cpp b/src/search.cpp index 6ec4d8032..91ac60ad4 100644 --- a/src/search.cpp +++ b/src/search.cpp @@ -1167,6 +1167,13 @@ namespace { { Depth r = reduction(improving, depth, moveCount); + // Decrease reduction at non-check cut nodes for second move at low depths + if ( cutNode + && depth <= 10 + && moveCount <= 2 + && !ss->inCheck) + r--; + // Decrease reduction if the ttHit running average is large if (thisThread->ttHitAverage > 473 * TtHitAverageResolution * TtHitAverageWindow / 1024) r--;