static InfoBits SqSqInfo[SqLen][SqLen]; // For each from-square, for each to-square: properties
Where InfoBits is an unsigned 32 bit integer with each bit giving the value of a some boolean function PropertyN(from-square, to-square). The contents of SqSqInfo are assigned during initialization and remain constant thereafter. Oscar gets a big speed improvement by avoiding the need to calculate simple property values more than once.
Currently, only 24 of the bits have a property function assignment; eight bits are just spare entries for now.
// SqSqInfo[frsq][tosq] array element coding
#define InfoHasDir BX(0x1f) // Has a directional relationship; if 0 then all bits are 0
#define InfoAdjSqs BX(0x1e) // Squares are adjacent
#define InfoResB1d BX(0x1d) // Reserved bit 0x1d
#define InfoResB1c BX(0x1c) // Reserved bit 0x1c
#define InfoResB1b BX(0x1b) // Reserved bit 0x1b
#define InfoResB1a BX(0x1a) // Reserved bit 0x1a
#define InfoResB19 BX(0x19) // Reserved bit 0x19
#define InfoResB18 BX(0x18) // Reserved bit 0x18
#define InfoResB17 BX(0x17) // Reserved bit 0x17
#define InfoResB16 BX(0x16) // Reserved bit 0x16
#define InfoSmRank BX(0x15) // Squares are on same rank
#define InfoSmFile BX(0x14) // Squares are on same file
#define InfoPromBP BX(0x13) // Promotion: black pawn
#define InfoPromWP BX(0x12) // Promotion: white pawn
#define InfoDAdvBP BX(0x11) // Double square advance: black pawn
#define InfoDAdvWP BX(0x10) // Double square advance: white pawn
#define InfoSAdvBP BX(0x0f) // Single square advance: black pawn
#define InfoSAdvWP BX(0x0e) // Single square advance: white pawn
#define InfoPathBP BX(0x0d) // Forward path of black pawn on from square includes to square
#define InfoPathWP BX(0x0c) // Forward path of white pawn on from square includes to square
#define InfoAtkfBP BX(0x0b) // From square has a black pawn attack on the to square
#define InfoAtkfWP BX(0x0a) // From square has a white pawn attack on the to square
#define InfoBdrBt1 BX(0x09) // Bidirection bit 1
#define InfoBdrBt0 BX(0x08) // Bidirection bit 0
#define InfoDOrtho BX(0x07) // Direction is ortho
#define InfoDDiago BX(0x06) // Direction is diago
#define InfoDCrook BX(0x05) // Direction is crook
#define InfoDSweep BX(0x04) // Direction is sweep
#define InfoDirBt3 BX(0x03) // Direction bit 3
#define InfoDirBt2 BX(0x02) // Direction bit 2
#define InfoDirBt1 BX(0x01) // Direction bit 1
#define InfoDirBt0 BX(0x00) // Direction bit 0
static bool PositionSqAttacksSq(const Position * const positionptr, const Sq frsq, const Sq tosq)
{
// This routine tests for an attack from one square to another in the given position.
bool result = false;
const InfoBits infobits = SqSqInfo[frsq][tosq];
if (infobits)
{
switch (positionptr->board.manvec[frsq])
{
case ManWhitePawn:
if (infobits & InfoAtkfWP)
result = true;
break;
case ManBlackPawn:
if (infobits & InfoAtkfBP)
result = true;
break;
case ManWhiteKnight:
case ManBlackKnight:
if (infobits & InfoDCrook)
result = true;
break;
case ManWhiteBishop:
case ManBlackBishop:
if ((infobits & InfoDDiago) &&
((infobits & InfoAdjSqs) ||
BoardTestClearPath(&positionptr->board, MapInfoBitsToDir(infobits), frsq, tosq)))
result = true;
break;
case ManWhiteRook:
case ManBlackRook:
if ((infobits & InfoDOrtho) &&
((infobits & InfoAdjSqs) ||
BoardTestClearPath(&positionptr->board, MapInfoBitsToDir(infobits), frsq, tosq)))
result = true;
break;
case ManWhiteQueen:
case ManBlackQueen:
if ((infobits & InfoDSweep) &&
((infobits & InfoAdjSqs) ||
BoardTestClearPath(&positionptr->board, MapInfoBitsToDir(infobits), frsq, tosq)))
result = true;
break;
case ManWhiteKing:
case ManBlackKing:
if (infobits & InfoAdjSqs)
result = true;
break;
default:
break;
};
};
return result;
}