mirror of
https://github.com/opelly27/Stockfish.git
synced 2026-05-20 07:27:46 +00:00
prefetch in do_move()
this allows removing Position::key_after() STC LLR: 2.93 (-2.94,2.94) <-1.75,0.25> Total: 24960 W: 6556 L: 6336 D: 12068 Ptnml(0-2): 59, 2554, 7056, 2730, 81 LTC LLR: 2.94 (-2.94,2.94) <-1.75,0.25> Total: 115080 W: 29319 L: 29204 D: 56557 Ptnml(0-2): 51, 10736, 35864, 10825, 64 STC with 2MB hash LLR: 3.04 (-2.94,2.94) <-1.75,0.25> Total: 182176 W: 46998 L: 46932 D: 88246 Ptnml(0-2): 526, 19711, 50544, 19785, 522 LTC with 8MB hash LLR: 2.94 (-2.94,2.94) <-1.75,0.25> Total: 441180 W: 111557 L: 111746 D: 217877 Ptnml(0-2): 229, 39698, 140929, 39501, 233 closes https://github.com/official-stockfish/Stockfish/pull/5770 bench: 1379150
This commit is contained in:
committed by
Joost VandeVondele
parent
c085670b84
commit
aaafaaecf2
+11
-21
@@ -689,7 +689,12 @@ bool Position::gives_check(Move m) const {
|
|||||||
// Makes a move, and saves all information necessary
|
// Makes a move, and saves all information necessary
|
||||||
// to a StateInfo object. The move is assumed to be legal. Pseudo-legal
|
// to a StateInfo object. The move is assumed to be legal. Pseudo-legal
|
||||||
// moves should be filtered out before this function is called.
|
// moves should be filtered out before this function is called.
|
||||||
void Position::do_move(Move m, StateInfo& newSt, bool givesCheck) {
|
// If a pointer to the TT table is passed, the entry for the new position
|
||||||
|
// will be prefetched
|
||||||
|
void Position::do_move(Move m,
|
||||||
|
StateInfo& newSt,
|
||||||
|
bool givesCheck,
|
||||||
|
const TranspositionTable* tt = nullptr) {
|
||||||
|
|
||||||
assert(m.is_ok());
|
assert(m.is_ok());
|
||||||
assert(&newSt != st);
|
assert(&newSt != st);
|
||||||
@@ -887,11 +892,13 @@ void Position::do_move(Move m, StateInfo& newSt, bool givesCheck) {
|
|||||||
st->minorPieceKey ^= Zobrist::psq[pc][from] ^ Zobrist::psq[pc][to];
|
st->minorPieceKey ^= Zobrist::psq[pc][from] ^ Zobrist::psq[pc][to];
|
||||||
}
|
}
|
||||||
|
|
||||||
// Set capture piece
|
|
||||||
st->capturedPiece = captured;
|
|
||||||
|
|
||||||
// Update the key with the final value
|
// Update the key with the final value
|
||||||
st->key = k;
|
st->key = k;
|
||||||
|
if (tt)
|
||||||
|
prefetch(tt->first_entry(key()));
|
||||||
|
|
||||||
|
// Set capture piece
|
||||||
|
st->capturedPiece = captured;
|
||||||
|
|
||||||
// Calculate checkers bitboard (if move gives check)
|
// Calculate checkers bitboard (if move gives check)
|
||||||
st->checkersBB = givesCheck ? attackers_to(square<KING>(them)) & pieces(us) : 0;
|
st->checkersBB = givesCheck ? attackers_to(square<KING>(them)) & pieces(us) : 0;
|
||||||
@@ -1069,23 +1076,6 @@ void Position::undo_null_move() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Computes the new hash key after the given move. Needed
|
|
||||||
// for speculative prefetch. It doesn't recognize special moves like castling,
|
|
||||||
// en passant and promotions.
|
|
||||||
Key Position::key_after(Move m) const {
|
|
||||||
|
|
||||||
Square from = m.from_sq();
|
|
||||||
Square to = m.to_sq();
|
|
||||||
Piece pc = piece_on(from);
|
|
||||||
Piece captured = piece_on(to);
|
|
||||||
Key k = st->key ^ Zobrist::side;
|
|
||||||
|
|
||||||
k ^= Zobrist::psq[captured][to] ^ Zobrist::psq[pc][to] ^ Zobrist::psq[pc][from];
|
|
||||||
|
|
||||||
return (captured || type_of(pc) == PAWN) ? k : adjust_key50<true>(k);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Tests if the SEE (Static Exchange Evaluation)
|
// Tests if the SEE (Static Exchange Evaluation)
|
||||||
// value of move is greater or equal to the given threshold. We'll use an
|
// value of move is greater or equal to the given threshold. We'll use an
|
||||||
// algorithm similar to alpha-beta pruning with a null window.
|
// algorithm similar to alpha-beta pruning with a null window.
|
||||||
|
|||||||
+5
-4
@@ -141,8 +141,8 @@ class Position {
|
|||||||
Piece captured_piece() const;
|
Piece captured_piece() const;
|
||||||
|
|
||||||
// Doing and undoing moves
|
// Doing and undoing moves
|
||||||
void do_move(Move m, StateInfo& newSt);
|
void do_move(Move m, StateInfo& newSt, const TranspositionTable* tt);
|
||||||
void do_move(Move m, StateInfo& newSt, bool givesCheck);
|
void do_move(Move m, StateInfo& newSt, bool givesCheck, const TranspositionTable* tt);
|
||||||
void undo_move(Move m);
|
void undo_move(Move m);
|
||||||
void do_null_move(StateInfo& newSt, const TranspositionTable& tt);
|
void do_null_move(StateInfo& newSt, const TranspositionTable& tt);
|
||||||
void undo_null_move();
|
void undo_null_move();
|
||||||
@@ -152,7 +152,6 @@ class Position {
|
|||||||
|
|
||||||
// Accessing hash keys
|
// Accessing hash keys
|
||||||
Key key() const;
|
Key key() const;
|
||||||
Key key_after(Move m) const;
|
|
||||||
Key material_key() const;
|
Key material_key() const;
|
||||||
Key pawn_key() const;
|
Key pawn_key() const;
|
||||||
Key major_piece_key() const;
|
Key major_piece_key() const;
|
||||||
@@ -369,7 +368,9 @@ inline void Position::move_piece(Square from, Square to) {
|
|||||||
board[to] = pc;
|
board[to] = pc;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline void Position::do_move(Move m, StateInfo& newSt) { do_move(m, newSt, gives_check(m)); }
|
inline void Position::do_move(Move m, StateInfo& newSt, const TranspositionTable* tt = nullptr) {
|
||||||
|
do_move(m, newSt, gives_check(m), tt);
|
||||||
|
}
|
||||||
|
|
||||||
inline StateInfo* Position::state() const { return st; }
|
inline StateInfo* Position::state() const { return st; }
|
||||||
|
|
||||||
|
|||||||
+18
-23
@@ -872,17 +872,16 @@ Value Search::Worker::search(
|
|||||||
|
|
||||||
assert(pos.capture_stage(move));
|
assert(pos.capture_stage(move));
|
||||||
|
|
||||||
// Prefetch the TT entry for the resulting position
|
movedPiece = pos.moved_piece(move);
|
||||||
prefetch(tt.first_entry(pos.key_after(move)));
|
|
||||||
|
pos.do_move(move, st, &tt);
|
||||||
|
thisThread->nodes.fetch_add(1, std::memory_order_relaxed);
|
||||||
|
|
||||||
ss->currentMove = move;
|
ss->currentMove = move;
|
||||||
ss->continuationHistory =
|
ss->continuationHistory =
|
||||||
&this->continuationHistory[ss->inCheck][true][pos.moved_piece(move)][move.to_sq()];
|
&this->continuationHistory[ss->inCheck][true][movedPiece][move.to_sq()];
|
||||||
ss->continuationCorrectionHistory =
|
ss->continuationCorrectionHistory =
|
||||||
&this->continuationCorrectionHistory[pos.moved_piece(move)][move.to_sq()];
|
&this->continuationCorrectionHistory[movedPiece][move.to_sq()];
|
||||||
|
|
||||||
thisThread->nodes.fetch_add(1, std::memory_order_relaxed);
|
|
||||||
pos.do_move(move, st);
|
|
||||||
|
|
||||||
// Perform a preliminary qsearch to verify that the move holds
|
// Perform a preliminary qsearch to verify that the move holds
|
||||||
value = -qsearch<NonPV>(pos, ss + 1, -probCutBeta, -probCutBeta + 1);
|
value = -qsearch<NonPV>(pos, ss + 1, -probCutBeta, -probCutBeta + 1);
|
||||||
@@ -1118,12 +1117,13 @@ moves_loop: // When in check, search starts here
|
|||||||
extension = 1;
|
extension = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Step 16. Make the move
|
||||||
|
pos.do_move(move, st, givesCheck, &tt);
|
||||||
|
thisThread->nodes.fetch_add(1, std::memory_order_relaxed);
|
||||||
|
|
||||||
// Add extension to new depth
|
// Add extension to new depth
|
||||||
newDepth += extension;
|
newDepth += extension;
|
||||||
|
|
||||||
// Speculative prefetch as early as possible
|
|
||||||
prefetch(tt.first_entry(pos.key_after(move)));
|
|
||||||
|
|
||||||
// Update the current move (this must be done after singular extension search)
|
// Update the current move (this must be done after singular extension search)
|
||||||
ss->currentMove = move;
|
ss->currentMove = move;
|
||||||
ss->continuationHistory =
|
ss->continuationHistory =
|
||||||
@@ -1132,10 +1132,6 @@ moves_loop: // When in check, search starts here
|
|||||||
&thisThread->continuationCorrectionHistory[movedPiece][move.to_sq()];
|
&thisThread->continuationCorrectionHistory[movedPiece][move.to_sq()];
|
||||||
uint64_t nodeCount = rootNode ? uint64_t(nodes) : 0;
|
uint64_t nodeCount = rootNode ? uint64_t(nodes) : 0;
|
||||||
|
|
||||||
// Step 16. Make the move
|
|
||||||
thisThread->nodes.fetch_add(1, std::memory_order_relaxed);
|
|
||||||
pos.do_move(move, st, givesCheck);
|
|
||||||
|
|
||||||
// These reduction adjustments have proven non-linear scaling.
|
// These reduction adjustments have proven non-linear scaling.
|
||||||
// They are optimized to time controls of 180 + 1.8 and longer,
|
// They are optimized to time controls of 180 + 1.8 and longer,
|
||||||
// so changing them or adding conditions that are similar requires
|
// so changing them or adding conditions that are similar requires
|
||||||
@@ -1637,20 +1633,19 @@ Value Search::Worker::qsearch(Position& pos, Stack* ss, Value alpha, Value beta)
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Speculative prefetch as early as possible
|
// Step 7. Make and search the move
|
||||||
prefetch(tt.first_entry(pos.key_after(move)));
|
Piece movedPiece = pos.moved_piece(move);
|
||||||
|
|
||||||
|
pos.do_move(move, st, givesCheck, &tt);
|
||||||
|
thisThread->nodes.fetch_add(1, std::memory_order_relaxed);
|
||||||
|
|
||||||
// Update the current move
|
// Update the current move
|
||||||
ss->currentMove = move;
|
ss->currentMove = move;
|
||||||
ss->continuationHistory =
|
ss->continuationHistory =
|
||||||
&thisThread
|
&thisThread->continuationHistory[ss->inCheck][capture][movedPiece][move.to_sq()];
|
||||||
->continuationHistory[ss->inCheck][capture][pos.moved_piece(move)][move.to_sq()];
|
|
||||||
ss->continuationCorrectionHistory =
|
ss->continuationCorrectionHistory =
|
||||||
&thisThread->continuationCorrectionHistory[pos.moved_piece(move)][move.to_sq()];
|
&thisThread->continuationCorrectionHistory[movedPiece][move.to_sq()];
|
||||||
|
|
||||||
// Step 7. Make and search the move
|
|
||||||
thisThread->nodes.fetch_add(1, std::memory_order_relaxed);
|
|
||||||
pos.do_move(move, st, givesCheck);
|
|
||||||
value = -qsearch<nodeType>(pos, ss + 1, -beta, -alpha);
|
value = -qsearch<nodeType>(pos, ss + 1, -beta, -alpha);
|
||||||
pos.undo_move(move);
|
pos.undo_move(move);
|
||||||
|
|
||||||
@@ -2148,7 +2143,7 @@ bool RootMove::extract_ponder_from_tt(const TranspositionTable& tt, Position& po
|
|||||||
if (pv[0] == Move::none())
|
if (pv[0] == Move::none())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
pos.do_move(pv[0], st);
|
pos.do_move(pv[0], st, &tt);
|
||||||
|
|
||||||
auto [ttHit, ttData, ttWriter] = tt.probe(pos.key());
|
auto [ttHit, ttData, ttWriter] = tt.probe(pos.key());
|
||||||
if (ttHit)
|
if (ttHit)
|
||||||
|
|||||||
Reference in New Issue
Block a user