summaryrefslogtreecommitdiff
path: root/src/lmr_testing/generate_counter_move_block.c
blob: f58efda362685cdf6003b7be25f666e6b92422a3 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
// generate.c changes to restore counter-move scoring. Three pieces, in
// the same function (the one with PRECOMP_KILLERS sKillers[...] and the
// "Pre-populate killer/bonuses" comment -- search for that to find it).

// LOCATION 1: local var decls at top of the function -- add mvLast and
// pi, bump sKillers to 6:
//
//   PLY_INFO *pi = &ctx->sPlyInfo[ctx->uPly];      // ADD
//   ULONG uPly = ctx->uPly;
//   POSITION *pos = &ctx->sPosition;
//   ULONG u;
//   MOVE mv;
//   MOVE mvLast = (pi-1)->mv;                        // ADD
//   SCORE s;
//   MOVE_STACK_MOVE_VALUE_FLAGS mvf;
//   ULONG uHashMoveLoc = (ULONG)-1;
//   ULONG uColor = pos->uToMove;
//   PRECOMP_KILLERS sKillers[6];                     // was [4]
//   COOR cEnprise = FindEnprisePiece(ctx, uColor);

// LOCATION 2: right after the killer sKillers[0..3] population block
// (after the SORT_THESE_FIRST |= lines for sKillers[0..3]), insert:

    //
    // Pre-populate counter-move bonuses -- keyed by whatever move the
    // opponent just played to reach this node, not by ply.  A/B test:
    // applied as a small *additive* nudge (like history counters),
    // not a hard priority-tier flag -- the ~56% measured hit rate
    // isn't confident enough to justify unconditionally outranking
    // ordinary PSQT-scored quiet moves.  Bonus scales with the ply
    // depth the entry was recorded at (deeper = more confident),
    // capped at the same 400/200 ceiling the flat version used.
    //
    sKillers[4].mv.uMove = sKillers[5].mv.uMove = 0;
    if (mvLast.uMove != 0)
    {
        u = MOVE_TO_INDEX(mvLast);
        sKillers[4].mv = ctx->mvCounter[u][0];
        sKillers[4].uBonus = 400;
        sKillers[5].mv = ctx->mvCounter[u][1];
        sKillers[5].uBonus = 200;
    }

// LOCATION 3: in the quiet-move scoring branch (the `else` branch that
// computes `s = g_iPSQT[...]` and applies killer bonuses via `s |= ...`),
// right after the GOOD_MOVE/cEnprise line and before `ASSERT(s >= 0);`,
// add (note: additive `+=`, not `|=` -- this was the measured-best
// config vs. a hard flag):

                s += (IS_SAME_MOVE(sKillers[4].mv, mv) * sKillers[4].uBonus);
                s += (IS_SAME_MOVE(sKillers[5].mv, mv) * sKillers[5].uBonus);

// This same three-part change applies in BOTH scoring functions in
// generate.c that have this sKillers array (there are two -- one for
// the normal move-scoring path, one for escaping-check; check whether
// the second one had the counter-move block too before assuming it's
// identical -- verify via `grep -n PRECOMP_KILLERS generate.c` and
// diff both call sites against this file's saved state if unsure).