LCOV - code coverage report
Current view: top level - src - common.h (source / functions) Hit Total Coverage
Test: test_coverage.info Lines: 37 39 94.9 %
Date: 2017-06-21 14:32:49 Functions: 2 2 100.0 %

          Line data    Source code
       1             : //////////////////////////////////////////////////////////////////////
       2             : //
       3             : //  FILE:       common.h
       4             : //              Common macros, structures and constants.
       5             : //
       6             : //  Part of:    Scid (Shane's Chess Information Database)
       7             : //  Version:    3.6.6
       8             : //
       9             : //  Notice:     Copyright (c) 2000-2004  Shane Hudson.  All rights reserved.
      10             : //
      11             : //  Author:     Shane Hudson (sgh@users.sourceforge.net)
      12             : //              Copyright (c) 2006-2007 Pascal Georges
      13             : //
      14             : //////////////////////////////////////////////////////////////////////
      15             : 
      16             : #ifndef SCID_COMMON_H
      17             : #define SCID_COMMON_H
      18             : 
      19             : #if __cplusplus >= 201103L || defined(__GXX_EXPERIMENTAL_CXX0X__) || _MSC_VER > 1600
      20             :         #define CPP11_SUPPORT 1
      21             : #else
      22             :         #define CPP11_SUPPORT 0
      23             : #endif
      24             : 
      25             : #include <cstddef>
      26             : #if defined(_MSC_VER) && _MSC_VER <= 1600
      27             : typedef unsigned __int8   uint8_t;
      28             : typedef unsigned __int16  uint16_t;
      29             : typedef unsigned __int32  uint32_t;
      30             : typedef unsigned __int64  uint64_t;
      31             : typedef __int32  int32_t;
      32             : #else
      33             : #include <stdint.h>
      34             : #endif // _MSC_VER <= 1600
      35             : 
      36             : #include "error.h"
      37             : 
      38             : //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
      39             : // CONSTANTS:
      40             : 
      41             : // Buffer sizes
      42             : #define BBUF_SIZE 256000 //120000
      43             : 
      44             : typedef unsigned short versionT;
      45             : 
      46             : // Version: div by 100 for major number, modulo 100 for minor number
      47             : // so 109 = 1.9, 110 = 1.10, etc.
      48             : 
      49             : const versionT SCID_VERSION = 400;     // Current file format version = 4.0
      50             : const versionT SCID_OLDEST_VERSION = 300; // Oldest readable file format: 3.0
      51             : 
      52             : const char SCID_VERSION_STRING[] = "4.6.5";     // Current Scid version
      53             : const char SCID_WEBSITE[] = "http://scid.sourceforge.net/";
      54             : 
      55             : const char GZIP_SUFFIX[] = ".gz";
      56             : const char ZIP_SUFFIX[] = ".zip";
      57             : const char PGN_SUFFIX[] = ".pgn";
      58             : 
      59             : 
      60             : //////////////////////////////////////////////////////////////////////
      61             : // ASSERT macro: asserts an expression. Differs from the standard
      62             : //    assert in that it does NOT print the expression (this is a waste,
      63             : //    if an assert fails you can go to the code to see why) and that
      64             : //    it MUST be a statement, not part of a larger expression.
      65             : //    Adapted from the book "Writing Solid Code".
      66             : #include <assert.h>
      67             : #define ASSERT(f) assert(f)
      68             : 
      69             : 
      70             : // Bit Manipulations
      71             : 
      72             : #define BIT_7(x)            ((x) & 128)
      73             : #define BIT_6(x)            ((x) &  64)
      74             : #define BIT_5(x)            ((x) &  32)
      75             : #define BIT_4(x)            ((x) &  16)
      76             : #define BIT_3(x)            ((x) &   8)
      77             : #define BIT_2(x)            ((x) &   4)
      78             : #define BIT_1(x)            ((x) &   2)
      79             : #define BIT_0(x)            ((x) &   1)
      80             : 
      81             : // Upper or lower 4 bits of a byte, in the range 0..15
      82             : 
      83             : #define UPPER_4_BITS(x)     (((x) & 240) >> 4)      // 240 is (15 * 16)
      84             : #define LOWER_4_BITS(x)     ((x) &  15)
      85             : 
      86             : //  Upper or lower 12 bits of an integer, in the range 0..4095
      87             : //
      88             : #define UPPER_12_BITS(x)    (((x) & (4096 * 4095)) >> 12)
      89             : #define LOWER_12_BITS(x)    ((x) &  4095)
      90             : 
      91             : 
      92             : //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
      93             : // TYPE DEFINITIONS
      94             : 
      95             : //  General types
      96             : 
      97             : typedef unsigned char byte;      //  8 bit unsigned
      98             : typedef uint16_t ushort;         // 16 bit unsigned
      99             : typedef uint32_t uint;           // 32 bit unsigned
     100             : typedef int32_t  sint;           // 32 bit signed
     101             : 
     102             : 
     103             : //  compareT: comparison type
     104             : 
     105             : typedef signed int    compareT;
     106             : const compareT
     107             :     LESS_THAN = -1,   EQUAL_TO = 0,   GREATER_THAN = 1;
     108             : 
     109             : //  Chess Types
     110             : 
     111             : typedef byte                    pieceT;      // e.g ROOK or WK
     112             : typedef byte                    colorT;      // WHITE or BLACK
     113             : typedef byte                    squareT;     // e.g. A3
     114             : typedef byte                    directionT;  // e.g. UP_LEFT
     115             : typedef byte                    rankT;       // Chess board rank
     116             : typedef byte                    fyleT;       // Chess board file
     117             : typedef byte                    leftDiagT;   // Up-left diagonals
     118             : typedef byte                    rightDiagT;  // Up-right diagonals
     119             : 
     120             : // boardT: 64 squares plus two extra squares: one for storing the side
     121             : //   to move as a byte and one for the string terminator, so boards can
     122             : //   be compared using regular string functions:
     123             : typedef pieceT                  boardT [66];
     124             : 
     125             : typedef byte                    smallBoardT [32];
     126             :                                     // A more densely packed board, 2 squares
     127             :                                     // per byte.
     128             : 
     129             : typedef byte                    castleDirT;  // LEFT or RIGHT
     130             : 
     131             : //  Other Small Types
     132             : 
     133             : typedef ushort                  statusT;
     134             : 
     135             : //  Fixed String Types
     136             : 
     137             : typedef char    sanStringT [ 10];   // SAN Move Notation
     138             : 
     139             : //  File-related Types
     140             : 
     141             : typedef char    fileNameT [512];
     142             : typedef uint    fileLengthT;
     143             : 
     144             : enum fileModeT {
     145             :     FMODE_None = 0,
     146             :     FMODE_ReadOnly,
     147             :     FMODE_WriteOnly,
     148             :     FMODE_Both,
     149             :     FMODE_Create,
     150             :     FMODE_Memory
     151             : };
     152             : 
     153             : //  Date type: see date.h and date.cpp
     154             : 
     155             : typedef uint    dateT;
     156             : 
     157             : //  Game Information types
     158             : 
     159             : typedef uint            gamenumT;
     160             : typedef ushort          eloT;
     161             : typedef ushort          ecoT;
     162             : typedef char            ecoStringT [6];   /* "A00j1" */
     163             : 
     164             : const ecoT ECO_None = 0;
     165             : 
     166             : // Rating types:
     167             : 
     168             : const byte RATING_Elo = 0;
     169             : const byte RATING_Rating = 1;
     170             : const byte RATING_Rapid = 2;
     171             : const byte RATING_ICCF = 3;
     172             : const byte RATING_USCF = 4;
     173             : const byte RATING_DWZ = 5;
     174             : const byte RATING_BCF = 6;
     175             : 
     176             : extern const char * ratingTypeNames [17];   // Defined in game.cpp
     177             : 
     178             : 
     179             : 
     180             : // Result Type
     181             : 
     182             : const uint NUM_RESULT_TYPES = 4;
     183             : typedef byte    resultT;
     184             : const resultT
     185             :     RESULT_None  = 0,
     186             :     RESULT_White = 1,
     187             :     RESULT_Black = 2,
     188             :     RESULT_Draw  = 3;
     189             : 
     190             : const uint RESULT_SCORE[4] = { 1, 2, 0, 1 };
     191             : const char RESULT_CHAR [4]       = { '*',  '1',    '0',    '='       };
     192             : const char RESULT_STR [4][4]     = { "*",  "1-0",  "0-1",  "=-="     };
     193             : const char RESULT_LONGSTR [4][8] = { "*",  "1-0",  "0-1",  "1/2-1/2" };
     194             : const resultT RESULT_OPPOSITE [4] = {
     195             :     RESULT_None, RESULT_Black, RESULT_White, RESULT_Draw
     196             : };
     197             : 
     198             : //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
     199             : // CHESS PIECES, COLORS AND THEIR MACROS
     200             : 
     201             : const uint NUM_COLOR_TYPES = 2;
     202             : const colorT
     203             :     WHITE = 0,
     204             :     BLACK = 1,
     205             :     NOCOLOR = 2;
     206             : 
     207             : const char COLOR_CHAR [3] = {'W', 'B', '_' };
     208             : 
     209             :   inline colorT
     210    27787579 : color_Flip (colorT c) { return 1 - c; }
     211             : 
     212             :   inline char
     213             : color_Char(colorT c)  { return COLOR_CHAR[c]; }
     214             : 
     215             : const castleDirT  QSIDE = 0,  KSIDE = 1;
     216             : 
     217             : 
     218             : // PIECE TYPES (without color; same value as a white piece)
     219             : 
     220             : const pieceT
     221             :     KING = 1,
     222             :     QUEEN = 2,
     223             :     ROOK = 3,
     224             :     BISHOP = 4,
     225             :     KNIGHT = 5,
     226             :     PAWN = 6;
     227             : 
     228             : // PIECES:
     229             : //   Note that color(x) == ((x & 0x8) >> 3)  and  type(x) == (x & 0x7)
     230             : //   EMPTY is deliberately nonzero, and END_OF_BOARD is zero, so that
     231             : //   a board can be used as a regular 0-terminated string, provided
     232             : //   that board[NULL_SQUARE] == END_OF_BOARD, as it always should be.
     233             : 
     234             : const pieceT  EMPTY = 7;
     235             : const pieceT  END_OF_BOARD = 0;
     236             : const pieceT  WK =  1, WQ =  2, WR =  3, WB =  4, WN =  5, WP =  6;
     237             : const pieceT  BK =  9, BQ = 10, BR = 11, BB = 12, BN = 13, BP = 14;
     238             : 
     239             : // Minor piece definitions, used for searching by material only:
     240             : const pieceT  WM = 16, BM = 17;
     241             : 
     242             : const uint MAX_PIECE_TYPES = 18;
     243             : 
     244             : 
     245             : // PIECE_CHAR[]: array of piece characters, capitals for White pieces.
     246             : 
     247             : const char PIECE_CHAR [] = "xKQRBNP.xkqrbnpxMm";
     248             : 
     249             : // PIECE_FLIP[]: array of pieces, with colors reversed.
     250             : 
     251             : const pieceT PIECE_FLIP [MAX_PIECE_TYPES] = {
     252             :     END_OF_BOARD,
     253             :     BK, BQ, BR, BB, BN, BP,
     254             :     EMPTY, EMPTY,
     255             :     WK, WQ, WR, WB, WN, WP,
     256             :     EMPTY, BM, WM
     257             : };
     258             : 
     259             : const bool PIECE_IS_SLIDER [8] = {
     260             :     false,
     261             :     false, true, true, true, false, false,
     262             :     false,
     263             : };
     264             : 
     265             : // PIECE_VALUE: Piece values, K=1000, Q=9, R=5, B=N=3, P=1
     266             : 
     267             : const int PIECE_VALUE [MAX_PIECE_TYPES] = {
     268             :     0,
     269             :     100, 9, 5, 3, 3, 1,
     270             :     0, 0,
     271             :     -100, -9, -5, -3, -3, -1,
     272             :     0, 3, -3
     273             : };
     274             : 
     275             : //
     276             : // INLINE FUNCTIONS for pieces
     277             : //
     278             : 
     279             :   inline colorT
     280   239420293 : piece_Color(pieceT p)  { return (p == EMPTY) ? NOCOLOR : ((p & 8) >> 3); }
     281             : 
     282             : // Slightly faster piece_Color when we are sure the piece is not empty:
     283             :   inline colorT
     284     4429363 : piece_Color_NotEmpty(pieceT p)  { return (p & 8) >> 3; }
     285             : 
     286             :   inline pieceT
     287    79086967 : piece_Type(pieceT p)  { return (p & 7); }
     288             : 
     289             :   inline pieceT
     290     8633933 : piece_Make(colorT c, pieceT p)  { return ((c << 3) | (p & 7)); }
     291             : 
     292             :   inline bool
     293             : piece_IsWhite(pieceT p)  { return (p>=WK && p<=WP); }
     294             : 
     295             :   inline bool
     296             : piece_IsBlack(pieceT p)  { return (p>=BK && p<=BP); }
     297             : 
     298             :   inline bool
     299           0 : piece_IsKing(pieceT p)  { return (piece_Type(p) == KING); }
     300             : 
     301             :   inline bool
     302             : piece_IsQueen(pieceT p)  { return (piece_Type(p) == QUEEN); }
     303             : 
     304             :   inline bool
     305             : piece_IsRook(pieceT p)  { return (piece_Type(p) == ROOK); }
     306             : 
     307             :   inline bool
     308             : piece_IsBishop(pieceT p)  { return (piece_Type(p) == BISHOP); }
     309             : 
     310             :   inline bool
     311             : piece_IsKnight(pieceT p)  { return (piece_Type(p) == KNIGHT); }
     312             : 
     313             :   inline bool
     314             : piece_IsPawn(pieceT p)  { return (piece_Type(p) == PAWN); }
     315             : 
     316             :   inline bool
     317           0 : piece_IsSlider(pieceT p) { return PIECE_IS_SLIDER[piece_Type(p)]; }
     318             : 
     319             :   inline char
     320      862323 : piece_Char(pieceT p)  { return PIECE_CHAR[piece_Type(p)]; }
     321             : 
     322             :   inline pieceT
     323             : piece_FromChar(char x)
     324             : {
     325     1372117 :     switch (x) {
     326             :     case 'K': return KING;
     327             :     case 'Q': return QUEEN;
     328             :     case 'R': return ROOK;
     329             :     case 'N': return KNIGHT;
     330             :     case 'B': return BISHOP;
     331             :     default:  return EMPTY;
     332             :     }
     333             : }
     334             : 
     335             : inline int
     336             : piece_Value (pieceT p)  { return PIECE_VALUE[p]; }
     337             : 
     338             : 
     339             : //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
     340             : // SQUARES AND SQUARE MACROS
     341             : 
     342             : const squareT
     343             :     A1 = 0, B1 = 1, C1 = 2, D1 = 3, E1 = 4, F1 = 5, G1 = 6, H1 = 7,
     344             :     A2 = 8, B2 = 9, C2 =10, D2 =11, E2 =12, F2 =13, G2 =14, H2 =15,
     345             :     A3 =16, B3 =17, C3 =18, D3 =19, E3 =20, F3 =21, G3 =22, H3 =23,
     346             :     A4 =24, B4 =25, C4 =26, D4 =27, E4 =28, F4 =29, G4 =30, H4 =31,
     347             :     A5 =32, B5 =33, C5 =34, D5 =35, E5 =36, F5 =37, G5 =38, H5 =39,
     348             :     A6 =40, B6 =41, C6 =42, D6 =43, E6 =44, F6 =45, G6 =46, H6 =47,
     349             :     A7 =48, B7 =49, C7 =50, D7 =51, E7 =52, F7 =53, G7 =54, H7 =55,
     350             :     A8 =56, B8 =57, C8 =58, D8 =59, E8 =60, F8 =61, G8 =62, H8 =63,
     351             :     COLOR_SQUARE = 64,
     352             :     NULL_SQUARE = 65, NS = 65;    // NS is abbreviation for NULL_SQUARE.
     353             : 
     354             : const rankT
     355             :     RANK_1 = 0, RANK_2 = 1, RANK_3 = 2, RANK_4 = 3, RANK_5 = 4, RANK_6 = 5,
     356             :     RANK_7 = 6, RANK_8 = 7, NO_RANK = 64;
     357             : 
     358             : const fyleT
     359             :     // we use "fyle" instead of "file" to avoid confusion with disk files.
     360             :     A_FYLE = 0, B_FYLE = 1, C_FYLE = 2, D_FYLE = 3, E_FYLE = 4, F_FYLE = 5,
     361             :     G_FYLE = 6, H_FYLE = 7, NO_FYLE = 64;
     362             : 
     363             :   inline rankT
     364             : rank_FromChar(char c)
     365     1560131 : {   if (c < '1'  ||  c > '8') { return NO_RANK; } else return (c - '1');  }
     366             : 
     367             :   inline fyleT
     368             : fyle_FromChar(char c)
     369     1558049 : {   if (c < 'a'  ||  c > 'h') { return NO_FYLE; } else return (c - 'a');  }
     370             : 
     371             :   inline squareT
     372             : square_Make(fyleT f, rankT r)
     373             : {
     374     1928459 :     ASSERT (f <= H_FYLE  &&  r <= RANK_8);
     375     1928459 :     return ((r << 3) | f);
     376             : }
     377             : 
     378             :   inline fyleT
     379             : square_Fyle(squareT sq)
     380             : {
     381    73067143 :     return (sq & 0x7);
     382             : }
     383             : 
     384             :   inline rankT
     385             : square_Rank(squareT sq)
     386             : {
     387    92339089 :     return ((sq >> 3) & 0x7);
     388             : }
     389             : 
     390             :   inline leftDiagT
     391             : square_LeftDiag (squareT sq)
     392             : {
     393    90971828 :     return square_Rank(sq) + square_Fyle(sq);
     394             : }
     395             : 
     396             :   inline rightDiagT
     397             : square_RightDiag (squareT sq)
     398             : {
     399    40321103 :     return (7 + square_Rank(sq) - square_Fyle(sq));
     400             : }
     401             : 
     402             : // square_Color:
     403             : //   Return WHITE for a light square, BLACK for a dark square.
     404             :   inline colorT
     405             : square_Color (squareT sq)
     406             : {
     407    38725120 :     return 1 - (square_LeftDiag(sq) & 1);
     408             : }
     409             : 
     410             : // square_FlipFyle:
     411             : //   Return the square with its file flipped: a1 <-> h1, b1 <-> g1, etc.
     412             :   inline squareT
     413             : square_FlipFyle (squareT sq)
     414             : {
     415             :     return square_Make (A_FYLE + H_FYLE - square_Fyle(sq), square_Rank(sq));
     416             : }
     417             : 
     418             : // square_FlipRank:
     419             : //   Return the square with its rank flipped: a1 <-> a8, a2 <-> a7, etc.
     420             :   inline squareT
     421             : square_FlipRank (squareT sq)
     422             : {
     423             :     return square_Make (square_Fyle(sq), RANK_1 + RANK_8 - square_Rank(sq));
     424             : }
     425             : 
     426             : // square_FlipDiag:
     427             : //   Return the square flipped along the a1-h8 diagonal.
     428             :   inline squareT
     429             : square_FlipDiag (squareT sq)
     430             : {
     431             :     return square_Make (square_Rank(sq), square_Fyle(sq));
     432             : }
     433             : 
     434             : const uint
     435             : rankFyleDist[64] = {
     436             :     0, 1, 2, 3, 4, 5, 6, 7,
     437             :     1, 0, 1, 2, 3, 4, 5, 6,
     438             :     2, 1, 0, 1, 2, 3, 4, 5,
     439             :     3, 2, 1, 0, 1, 2, 3, 4,
     440             :     4, 3, 2, 1, 0, 1, 2, 3,
     441             :     5, 4, 3, 2, 1, 0, 1, 2,
     442             :     6, 5, 4, 3, 2, 1, 0, 1,
     443             :     7, 6, 5, 4, 3, 2, 1, 0
     444             : };
     445             : 
     446             : // square_Distance:
     447             : //   Return the distance in king moves between two squares.
     448             :   inline uint
     449             : square_Distance (squareT from, squareT to)
     450             : {
     451             :     ASSERT (from <= H8  &&  to <= H8);
     452             :     uint rankd = rankFyleDist[(square_Rank(from) << 3) | square_Rank(to)];
     453             :     uint fyled = rankFyleDist[(square_Fyle(from) << 3) | square_Fyle(to)];
     454             :     return (rankd > fyled) ? rankd : fyled;
     455             : }
     456             : 
     457             : // square_NearestCorner:
     458             : //   Return the corner (A1/H1/A8/H8) closest to the specified square.
     459             :   inline squareT
     460             : square_NearestCorner (squareT sq)
     461             : {
     462             :     if (square_Rank(sq) <= RANK_4) {
     463             :         return (square_Fyle(sq) <= D_FYLE)? A1 : H1;
     464             :     } else {
     465             :         return (square_Fyle(sq) <= D_FYLE)? A8 : H8;
     466             :     }
     467             : }
     468             : 
     469             :   inline bool
     470             : square_IsCornerSquare (squareT sq)
     471             : {
     472             :     return (sq == A1  ||  sq == H1  ||  sq == A8  ||  sq == H8);
     473             : }
     474             : 
     475             :   inline bool
     476             : square_IsEdgeSquare (squareT sq)
     477             : {
     478             :     rankT rank = square_Rank(sq);
     479             :     if (rank == RANK_1  ||  rank == RANK_8) { return true; }
     480             :     fyleT fyle = square_Fyle(sq);
     481             :     if (fyle == A_FYLE  ||  fyle == H_FYLE) { return true; }
     482             :     return false;
     483             : }
     484             : 
     485             : const int edgeDist[66] = {
     486             :     0, 0, 0, 0, 0, 0, 0, 0,
     487             :     0, 1, 1, 1, 1, 1, 1, 0,
     488             :     0, 1, 2, 2, 2, 2, 1, 0,
     489             :     0, 1, 2, 3, 3, 2, 1, 0,
     490             :     0, 1, 2, 3, 3, 2, 1, 0,
     491             :     0, 1, 2, 2, 2, 2, 1, 0,
     492             :     0, 1, 1, 1, 1, 1, 1, 0,
     493             :     0, 0, 0, 0, 0, 0, 0, 0,
     494             :     -1, -1
     495             : };
     496             : 
     497             :   inline int
     498             : square_EdgeDistance (squareT sq)
     499             : {
     500             :     return edgeDist[sq];
     501             : }
     502             : 
     503             :   inline bool
     504      530573 : square_IsKnightHop (squareT from, squareT to)
     505             : {
     506      530573 :     ASSERT (from <= H8  &&  to <= H8);
     507     1061146 :     uint rdist = rankFyleDist [(square_Rank(from) << 3) | square_Rank(to)];
     508     1061146 :     uint fdist = rankFyleDist [(square_Fyle(from) << 3) | square_Fyle(to)];
     509             :     // It is a knight hop only if one distance is two squares and the
     510             :     // other is one square -- that is, only if their product equals two.
     511      530573 :     return ((rdist * fdist) == 2);
     512             : }
     513             : 
     514             :   inline char
     515             : square_FyleChar (squareT sq)
     516             : {
     517     1982155 :     return square_Fyle(sq) + 'a';
     518             : }
     519             : 
     520             :   inline char
     521             : square_RankChar (squareT sq)
     522             : {
     523     1949652 :     return square_Rank(sq) + '1';
     524             : }
     525             : 
     526             :   inline void
     527             : square_Print (squareT sq, char * str)
     528             : {
     529             :     if (sq <= H8) {
     530             :         str[0] = square_FyleChar(sq);
     531             :         str[1] = square_RankChar(sq);
     532             :         str[2] = 0;
     533             :     } else if (sq == NULL_SQUARE) {
     534             :         str[0] = 'N'; str[1] = 'S'; str[2] = 0;
     535             :     } else {
     536             :         str[0] = 'X'; str[1] = 'X'; str[2] = 0;
     537             :     }
     538             :     return;
     539             : }
     540             : 
     541             : // Directions:
     542             : // Up = 1, Down = 2, Left = 4, Right = 8, UpLeft = 5, UpRight = 9,
     543             : // DownLeft = 6, DownRight = 10
     544             : 
     545             : const directionT
     546             :     NULL_DIR = 0,
     547             :     UP = 1,
     548             :     DOWN = 2,
     549             :     LEFT = 4,
     550             :     RIGHT = 8,
     551             :     UP_LEFT = (UP | LEFT),
     552             :     UP_RIGHT = (UP | RIGHT),
     553             :     DOWN_LEFT = (DOWN | LEFT),
     554             :     DOWN_RIGHT = (DOWN | RIGHT);
     555             : 
     556             : const directionT dirOpposite[11] = {
     557             :     NULL_DIR,
     558             :     DOWN,       // opposite of UP (1)
     559             :     UP,         // opposite of DOWN (2)
     560             :     NULL_DIR,
     561             :     RIGHT,      // opposite of LEFT (4)
     562             :     DOWN_RIGHT, // opposite of UP_LEFT (5)
     563             :     UP_RIGHT,   // opposite of DOWN_LEFT (6)
     564             :     NULL_DIR,
     565             :     LEFT,       // opposite of RIGHT (8)
     566             :     DOWN_LEFT,  // opposite of UP_RIGHT (9)
     567             :     UP_LEFT     // opposite of DOWN_RIGHT (10)
     568             : };
     569             : 
     570             : // direction_Opposite(): return the opposite direction to d
     571             :   inline directionT
     572             : direction_Opposite (directionT d)
     573             : {
     574     2768749 :     return dirOpposite[d];
     575             : }
     576             : 
     577             : // dirIsDiagonal[]: array listing the diagonal directions, for fast
     578             : //      lookup of whether a direction is a diagonal.
     579             :   const bool
     580             : dirIsDiagonal [11] = {
     581             :     false,   //  0 = NULL_DIR
     582             :     false,   //  1 = UP
     583             :     false,   //  2 = DOWN
     584             :     false,   //  3 = Invalid
     585             :     false,   //  4 = LEFT
     586             :     true,    //  5 = UP_LEFT
     587             :     true,    //  6 = DOWN_LEFT
     588             :     false,   //  7 = Invalid
     589             :     false,   //  8 = RIGHT
     590             :     true,    //  9 = UP_RIGHT
     591             :     true     // 10 = DOWN_RIGHT
     592             : };
     593             : 
     594             :   inline bool
     595             : direction_IsDiagonal (directionT dir)
     596             : {
     597     1136451 :     return dirIsDiagonal[dir];
     598             : }
     599             : 
     600             : // dirDelta:
     601             : //   Array giving the board delta of moving to the next square
     602             : //   in that direction.
     603             :   const int
     604             : dirDelta[11] = {
     605             :     0,    // NULL_DIR
     606             :     8,    // UP
     607             :    -8,    // DOWN
     608             :     0,    // Invalid
     609             :    -1,    // LEFT
     610             :     7,    // UP_LEFT
     611             :    -9,    // DOWN_LEFT
     612             :     0,    // Invalid
     613             :     1,    // RIGHT
     614             :     9,    // UP_RIGHT
     615             :    -7     // DOWN_RIGHT
     616             : };
     617             : 
     618             :   inline int
     619             : direction_Delta (directionT dir)
     620             : {
     621    13936400 :     return dirDelta[dir];
     622             : }
     623             : 
     624             : // sqDir[][]: Array listing the direction between any two squares.
     625             : //    For example, sqDir[A1][B2] == UP_RIGHT, and sqDir[A1][C2] == NULL_DIR.
     626             : //    It is initialised with the function scid_Init() in misc.cpp
     627             : extern directionT  sqDir[66][66];
     628             : 
     629             : // The starting Board
     630             : //
     631             :   const boardT
     632             : START_BOARD =
     633             : {
     634             :     WR, WN, WB, WQ, WK, WB, WN, WR,    // A1--H1
     635             :     WP, WP, WP, WP, WP, WP, WP, WP,    // A2--H2
     636             :     EMPTY, EMPTY, EMPTY, EMPTY, EMPTY, EMPTY, EMPTY, EMPTY,
     637             :     EMPTY, EMPTY, EMPTY, EMPTY, EMPTY, EMPTY, EMPTY, EMPTY,
     638             :     EMPTY, EMPTY, EMPTY, EMPTY, EMPTY, EMPTY, EMPTY, EMPTY,
     639             :     EMPTY, EMPTY, EMPTY, EMPTY, EMPTY, EMPTY, EMPTY, EMPTY,
     640             :     BP, BP, BP, BP, BP, BP, BP, BP,
     641             :     BR, BN, BB, BQ, BK, BB, BN, BR,
     642             :     EMPTY, // COLOR_SQUARE
     643             :     END_OF_BOARD  // NULL_SQUARE
     644             : };
     645             : 
     646             : 
     647             : // Square colors for the standard chess board:
     648             : //
     649             :   const colorT
     650             : BOARD_SQUARECOLOR[66] = {
     651             :     BLACK, WHITE, BLACK, WHITE, BLACK, WHITE, BLACK, WHITE,  // a1-h1
     652             :     WHITE, BLACK, WHITE, BLACK, WHITE, BLACK, WHITE, BLACK,  // a2-h2
     653             :     BLACK, WHITE, BLACK, WHITE, BLACK, WHITE, BLACK, WHITE,  // a3-h3
     654             :     WHITE, BLACK, WHITE, BLACK, WHITE, BLACK, WHITE, BLACK,  // a4-h4
     655             :     BLACK, WHITE, BLACK, WHITE, BLACK, WHITE, BLACK, WHITE,  // a5-h5
     656             :     WHITE, BLACK, WHITE, BLACK, WHITE, BLACK, WHITE, BLACK,  // a6-h6
     657             :     BLACK, WHITE, BLACK, WHITE, BLACK, WHITE, BLACK, WHITE,  // a7-h7
     658             :     WHITE, BLACK, WHITE, BLACK, WHITE, BLACK, WHITE, BLACK,  // a8-h8
     659             :     NOCOLOR, NOCOLOR  // Color square and Null square
     660             : };
     661             : 
     662             :   inline int
     663             : board_Compare (const pieceT * b1, const pieceT * b2)
     664             : {
     665             :     for (uint i=0; i < 64; i++) {
     666             :         if (*b1 < *b2) { return -1; }
     667             :         if (*b1 > *b2) { return 1; }
     668             :         b1++; b2++;
     669             :     }
     670             :     return 0;
     671             : }
     672             : 
     673             : // square_Adjacent: returns 1 if the two squares are adjacent. Note that
     674             : //    diagonal adjacency is included: a1 and b2 are adjacent.
     675             : //    Also note that a square is adjacent to itself.
     676             :   inline bool
     677     4571678 : square_Adjacent (squareT from, squareT to)
     678             : {
     679     4571678 :     ASSERT (from <= H8  &&  to <= H8);
     680     4571678 :     rankT fromRank = square_Rank(from);
     681     4571678 :     rankT toRank = square_Rank(to);
     682     4571678 :     int rdist = (int)fromRank - (int)toRank;
     683     4571678 :     if (rdist < -1  ||  rdist > 1) { return false; }
     684      640464 :     fyleT fromFyle = square_Fyle(from);
     685      640464 :     fyleT toFyle = square_Fyle(to);
     686      640464 :     int fdist = (int)fromFyle - (int)toFyle;
     687      640464 :     if (fdist < -1  ||  fdist > 1) { return false; }
     688      124449 :     return true;
     689             : }
     690             : 
     691             : #endif  // #ifdef SCID_COMMON_H
     692             : 
     693             : //////////////////////////////////////////////////////////////////////
     694             : //  EOF:  common.h
     695             : //////////////////////////////////////////////////////////////////////
     696             : 

Generated by: LCOV version 1.12