X-Git-Url: https://git.sesse.net/?p=stockfish;a=blobdiff_plain;f=src%2Fsearch.cpp;h=2c4d5ece2eb237f861890d7ac4add6c1c8c273ed;hp=64cdf1c4e5fac5f27d679e7ed4c2ad865c961a19;hb=a1b8c8109b464abd9d026b1ef740f1bace814b29;hpb=72e1e9b986fc4c656c3a3db24e5504e3edbb63cc diff --git a/src/search.cpp b/src/search.cpp index 64cdf1c4..2c4d5ece 100644 --- a/src/search.cpp +++ b/src/search.cpp @@ -23,6 +23,7 @@ //// #include +#include #include #include #include @@ -235,6 +236,10 @@ namespace { bool UseLogFile; std::ofstream LogFile; + // Natural logarithmic lookup table and its getter function + double lnArray[512]; + inline double ln(int i) { return lnArray[i]; } + // MP related variables int ActiveThreads = 1; Depth MinimumSplitDepth; @@ -319,13 +324,6 @@ namespace { //// Functions //// -//FIXME: HACK -static double lnArray[512]; - -inline double ln(int i) -{ - return lnArray[i]; -} /// perft() is our utility to verify move generation is bug free. All the legal /// moves up to given depth are generated and counted and the sum returned. @@ -559,20 +557,18 @@ bool think(const Position& pos, bool infinite, bool ponder, int side_to_move, /// and initializes the split point stack and the global locks and condition /// objects. -#include //FIXME: HACK - void init_threads() { - // FIXME: HACK!! - for (int i = 0; i < 512; i++) - lnArray[i] = log(double(i)); - volatile int i; #if !defined(_MSC_VER) pthread_t pthread[1]; #endif + // Init our logarithmic lookup table + for (int i = 0; i < 512; i++) + lnArray[i] = log(double(i)); // log() returns base-e logarithm + for (i = 0; i < THREAD_MAX; i++) Threads[i].activeSplitPoints = 0; @@ -653,6 +649,7 @@ void SearchStack::init(int ply) { currentMove = threatMove = MOVE_NONE; reduction = Depth(0); eval = VALUE_NONE; + evalInfo = NULL; } void SearchStack::initKillers() { @@ -886,7 +883,7 @@ namespace { Value root_search(Position& pos, SearchStack ss[], RootMoveList& rml, Value alpha, Value beta) { Value oldAlpha = alpha; - Value value; + Value value = -VALUE_INFINITE; CheckInfo ci(pos); // Loop through all the moves in the root move list @@ -955,6 +952,8 @@ namespace { { // Try to reduce non-pv search depth by one ply if move seems not problematic, // if the move fails high will be re-searched at full depth. + bool doFullDepthSearch = true; + if ( depth >= 3*OnePly // FIXME was newDepth && !dangerous && !captureOrPromotion @@ -965,13 +964,11 @@ namespace { { ss[0].reduction = Depth(int(floor(red * int(OnePly)))); value = -search(pos, ss, -alpha, newDepth-ss[0].reduction, 1, true, 0); + doFullDepthSearch = (value > alpha); } - else - value = alpha + 1; // Just to trigger next condition - } else - value = alpha + 1; // Just to trigger next condition + } - if (value > alpha) + if (doFullDepthSearch) { value = -search(pos, ss, -alpha, newDepth, 1, true, 0); @@ -1105,7 +1102,7 @@ namespace { Value oldAlpha, value; bool isCheck, mateThreat, singleEvasion, moveIsCheck, captureOrPromotion, dangerous; int moveCount = 0; - Value bestValue = -VALUE_INFINITE; + Value bestValue = value = -VALUE_INFINITE; if (depth < OnePly) return qsearch(pos, ss, alpha, beta, Depth(0), ply, threadID); @@ -1207,6 +1204,8 @@ namespace { { // Try to reduce non-pv search depth by one ply if move seems not problematic, // if the move fails high will be re-searched at full depth. + bool doFullDepthSearch = true; + if ( depth >= 3*OnePly && !dangerous && !captureOrPromotion @@ -1218,14 +1217,11 @@ namespace { { ss[ply].reduction = Depth(int(floor(red * int(OnePly)))); value = -search(pos, ss, -alpha, newDepth-ss[ply].reduction, ply+1, true, threadID); + doFullDepthSearch = (value > alpha); } - else - value = alpha + 1; // Just to trigger next condition } - else - value = alpha + 1; // Just to trigger next condition - if (value > alpha) // Go with full depth non-pv search + if (doFullDepthSearch) // Go with full depth non-pv search { ss[ply].reduction = Depth(0); value = -search(pos, ss, -alpha, newDepth, ply+1, true, threadID); @@ -1332,7 +1328,7 @@ namespace { bool isCheck, useFutilityPruning, singleEvasion, moveIsCheck, captureOrPromotion, dangerous; bool mateThreat = false; int moveCount = 0; - futilityValue = staticValue = bestValue = -VALUE_INFINITE; + futilityValue = staticValue = bestValue = value = -VALUE_INFINITE; if (depth < OnePly) return qsearch(pos, ss, beta-1, beta, Depth(0), ply, threadID); @@ -1376,14 +1372,15 @@ namespace { const int FutilityValueMargin = 112 * bitScanReverse32(int(depth) * int(depth) / 2); // Evaluate the position statically - if (isCheck) - ss[ply].eval = VALUE_NONE; - else + if (!isCheck) { if (tte && (tte->type() & VALUE_TYPE_EVAL)) staticValue = value_from_tt(tte->value(), ply); else + { staticValue = evaluate(pos, ei, threadID); + ss[ply].evalInfo = &ei; + } ss[ply].eval = staticValue; futilityValue = staticValue + FutilityValueMargin; @@ -1456,7 +1453,7 @@ namespace { // Go with internal iterative deepening if we don't have a TT move if (UseIIDAtNonPVNodes && ttMove == MOVE_NONE && depth >= 8*OnePly && - !isCheck && evaluate(pos, ei, threadID) >= beta - IIDMargin) + !isCheck && ss[ply].eval >= beta - IIDMargin) { search(pos, ss, beta, Min(depth/2, depth-2*OnePly), ply, false, threadID); ttMove = ss[ply].pv[ply]; @@ -1541,6 +1538,8 @@ namespace { // Try to reduce non-pv search depth by one ply if move seems not problematic, // if the move fails high will be re-searched at full depth. + bool doFullDepthSearch = true; + if ( depth >= 3*OnePly && !dangerous && !captureOrPromotion @@ -1553,14 +1552,11 @@ namespace { { ss[ply].reduction = Depth(int(floor(red * int(OnePly)))); value = -search(pos, ss, -(beta-1), newDepth-ss[ply].reduction, ply+1, true, threadID); + doFullDepthSearch = (value >= beta); } - else - value = beta; // Just to trigger next condition } - else - value = beta; // Just to trigger next condition - if (value >= beta) // Go with full depth non-pv search + if (doFullDepthSearch) // Go with full depth non-pv search { ss[ply].reduction = Depth(0); value = -search(pos, ss, -(beta-1), newDepth, ply+1, true, threadID); @@ -1810,7 +1806,7 @@ namespace { Position pos = Position(sp->pos); CheckInfo ci(pos); SearchStack* ss = sp->sstack[threadID]; - Value value; + Value value = -VALUE_INFINITE; Move move; bool isCheck = pos.is_check(); bool useFutilityPruning = sp->depth < SelectiveDepth @@ -1871,6 +1867,8 @@ namespace { // Try to reduce non-pv search depth by one ply if move seems not problematic, // if the move fails high will be re-searched at full depth. + bool doFullDepthSearch = true; + if ( !dangerous && !captureOrPromotion && !move_is_castle(move) @@ -1881,14 +1879,11 @@ namespace { { ss[sp->ply].reduction = Depth(int(floor(red * int(OnePly)))); value = -search(pos, ss, -(sp->beta-1), newDepth-ss[sp->ply].reduction, sp->ply+1, true, threadID); + doFullDepthSearch = (value >= sp->beta); } - else - value = sp->beta; // Just to trigger next condition } - else - value = sp->beta; // Just to trigger next condition - if (value >= sp->beta) // Go with full depth non-pv search + if (doFullDepthSearch) // Go with full depth non-pv search { ss[sp->ply].reduction = Depth(0); value = -search(pos, ss, -(sp->beta - 1), newDepth, sp->ply+1, true, threadID); @@ -1953,7 +1948,7 @@ namespace { Position pos = Position(sp->pos); CheckInfo ci(pos); SearchStack* ss = sp->sstack[threadID]; - Value value; + Value value = -VALUE_INFINITE; Move move; while ( sp->alpha < sp->beta @@ -1982,6 +1977,8 @@ namespace { // Try to reduce non-pv search depth by one ply if move seems not problematic, // if the move fails high will be re-searched at full depth. + bool doFullDepthSearch = true; + if ( !dangerous && !captureOrPromotion && !move_is_castle(move) @@ -1990,24 +1987,23 @@ namespace { double red = 0.5 + ln(moveCount) * ln(sp->depth / 2) / 6.0; if (red >= 1.0) { + Value localAlpha = sp->alpha; ss[sp->ply].reduction = Depth(int(floor(red * int(OnePly)))); - value = -search(pos, ss, -sp->alpha, newDepth-ss[sp->ply].reduction, sp->ply+1, true, threadID); + value = -search(pos, ss, -localAlpha, newDepth-ss[sp->ply].reduction, sp->ply+1, true, threadID); + doFullDepthSearch = (value > localAlpha); } - else - value = sp->alpha + 1; // Just to trigger next condition } - else - value = sp->alpha + 1; // Just to trigger next condition - if (value > sp->alpha) // Go with full depth non-pv search + if (doFullDepthSearch) // Go with full depth non-pv search { + Value localAlpha = sp->alpha; ss[sp->ply].reduction = Depth(0); - value = -search(pos, ss, -sp->alpha, newDepth, sp->ply+1, true, threadID); + value = -search(pos, ss, -localAlpha, newDepth, sp->ply+1, true, threadID); - if (value > sp->alpha && value < sp->beta) + if (value > localAlpha && value < sp->beta) { // When the search fails high at ply 1 while searching the first - // move at the root, set the flag failHighPly1. This is used for + // move at the root, set the flag failHighPly1. This is used for // time managment: We don't want to stop the search early in // such cases, because resolving the fail high at ply 1 could // result in a big drop in score at the root.