* FILE: init.c
*
* ----------------------------------------------------------------------
- *
- * Copyright (c) 2012 Free Software Foundation
+ * Copyright (c) 1993, 1994, 1995 Matthias Mutz
+ * Copyright (c) 1999 Michael Vanier and the Free Software Foundation
*
* GNU SHOGI is based on GNU CHESS
*
+ * Copyright (c) 1988, 1989, 1990 John Stanback
+ * Copyright (c) 1992 Free Software Foundation
+ *
* This file is part of GNU SHOGI.
*
* GNU Shogi is free software; you can redistribute it and/or modify it
display_t display_type = DISPLAY_X;
-unsigned int ttbllimit;
-
/* .... MOVE GENERATION VARIABLES AND INITIALIZATIONS .... */
-
-#define max(a, b) (((a) < (b))?(b):(a))
-#define odd(a) ((a) & 1)
-
-
-const small_short piece_of_ptype[NO_PTYPE_PIECES] =
-{
- pawn, lance, knight, silver, gold, bishop, rook, pbishop, prook, king,
- pawn, lance, knight, silver, gold
-};
-
-
-const small_short side_of_ptype[NO_PTYPE_PIECES] =
-{
- black, black, black, black, black, black, black, black, black, black,
- white, white, white, white, white
-};
-
#ifdef SAVE_NEXTPOS
const small_short psweep[NO_PTYPE_PIECES] =
{
const small_short sweep[NO_PIECES] =
{
- false, false, true, false, false, false, true, true,
- false, false, false, false, true, true, false
-};
-
-
-#if !defined EXTLANGFILE
-
-char *CP[CPSIZE] =
-
-{
-/* 000: eng: */ "",
-#ifdef LANGFILE
-#include LANGFILE
-#else
-#include "gnushogi.lng"
+ false, false,
+#ifndef MINISHOGI
+ true, false,
#endif
-};
-
-#else
-
-char *CP[CPSIZE];
-
+ false, false, true, true,
+ false,
+#ifndef MINISHOGI
+ false, false,
#endif
-
-
-/*
- * Determine the minimum number of moves for a piece from
- * square "f" to square "t". If the piece cannot reach "t",
- * the count is set to CANNOT_REACH.
- */
-
-#define csquare(sq) ((side == black) ? sq : (NO_SQUARES - 1 - sq))
-#define crow(sq) row(csquare(sq))
-#define ccol(sq) column(csquare(sq))
-
-short
-ptype_distance(short ptyp, short f, short t)
-{
- short side, piece;
- short colf, colt, rowf, rowt, dcol, drow;
-
- if (f == t)
- return 0;
-
- piece = piece_of_ptype[ptyp];
- side = side_of_ptype[ptyp];
-
- dcol = (colt = ccol(t)) - (colf = ccol(f));
- drow = (rowt = crow(t)) - (rowf = crow(f));
-
- switch (piece)
- {
- case pawn:
- if ((dcol != 0) || (drow < 1))
- return CANNOT_REACH;
- else
- return drow;
-
- case lance:
- if ((dcol != 0) || (drow < 1))
- return CANNOT_REACH;
- else
- return 1;
-
- case knight:
- if (odd(drow) || (odd(drow / 2) != odd(dcol)))
- return CANNOT_REACH;
- else if ((drow == 0) || ((drow / 2) < abs(dcol)))
- return CANNOT_REACH;
- else
- return (drow / 2);
-
- case silver:
- if (drow > 0)
- {
- if (odd(drow) == odd(dcol))
- {
- return max(abs(drow), abs(dcol));
- }
- else
- {
- if (abs(dcol) <= drow)
- return drow;
- else
- return (max(abs(drow), abs(dcol)) + 1);
- }
- }
- else
- {
- if (odd(drow) == odd(dcol))
- return (max(abs(drow), abs(dcol)));
- else
- return (max(abs(drow) + 1, abs(dcol)) + 1);
- };
-
- case gold:
- case ppawn:
- case pknight:
- case plance:
- case psilver:
- if (abs(dcol) == 0)
- return (abs(drow));
- else if (drow >= 0)
- return max(drow, abs(dcol));
- else
- return (abs(dcol) - drow);
-
- case bishop:
- if (odd(dcol) != odd(drow))
- return CANNOT_REACH;
- else
- return ((abs(dcol) == abs(drow)) ? 1 : 2);
-
- case pbishop:
- if (odd(dcol) != odd(drow))
- {
- if ((abs(dcol) <= 1) && (abs(drow) <= 1))
- return 1;
- else if (abs(abs(dcol) - abs(drow)) == 1)
- return 2;
- else
- return 3;
- }
- else
- {
- return ((abs(dcol) == abs(drow)) ? 1 : 2);
- }
-
- case rook:
- if ((dcol == 0) || (drow == 0))
- return 1;
- else
- return 2;
-
- case prook:
- if ((dcol == 0) || (drow == 0))
- return 1;
- else if ((abs(dcol) == 1) && (abs(drow) == 1))
- return 1;
- else
- return 2;
-
- case king:
- return max(abs(drow), abs(dcol));
-
- default:
- /* should never occur */
- return (CANNOT_REACH);
- }
-}
+ false, true, true, false
+};
#ifdef SAVE_DISTDATA
#endif
-#ifdef SAVE_PTYPE_DISTDATA
-short
-piece_distance(short side, short piece, short f, short t)
-{
- return ((f > NO_SQUARES)
- ? (short)1
- : (short)ptype_distance(ptype[side][piece], f, t));
-}
-#else
-short
-piece_distance(short side, short piece, short f, short t)
-{
- return ((f > NO_SQUARES)
- ? (short)1
- : (use_ptype_distdata
- ? (short)(*ptype_distdata[ptype[side][piece]])[f][t]
- : (short)ptype_distance(ptype[side][piece], f, t)));
-}
-#endif
-
-
void
Initialize_dist(void)
{
/*
- * nextpos[piece][from-square], nextdir[piece][from-square] gives vector
- * of positions reachable from from-square in ppos with piece such that the
+ * nextpos[ptype][from-square], nextdir[ptype][from-square] gives vector
+ * of positions reachable from from-square in ppos with ptype such that the
* sequence
*
- * ppos = nextpos[piece][from-square];
- * pdir = nextdir[piece][from-square];
+ * ppos = nextpos[ptype][from-square];
+ * pdir = nextdir[ptype][from-square];
* u = ppos[sq];
*
* do
*/
-/*
- * ptype is used to separate black and white pawns, like this; ptyp =
- * ptype[side][piece] piece can be used directly in nextpos/nextdir when
- * generating moves for pieces that are not white pawns.
- */
-
-const small_short ptype[2][NO_PIECES] =
-{
- {
- ptype_no_piece, ptype_pawn, ptype_lance, ptype_knight,
- ptype_silver, ptype_gold, ptype_bishop, ptype_rook,
- ptype_gold, ptype_gold, ptype_gold, ptype_gold,
- ptype_pbishop, ptype_prook, ptype_king
- },
- {
- ptype_no_piece, ptype_wpawn, ptype_wlance, ptype_wknight,
- ptype_wsilver, ptype_wgold, ptype_bishop, ptype_rook,
- ptype_wgold, ptype_wgold, ptype_wgold, ptype_wgold,
- ptype_pbishop, ptype_prook, ptype_king
- },
-};
-
-const small_short promoted[NO_PIECES] =
-{
- no_piece, ppawn, plance, pknight, psilver, gold, pbishop, prook,
- ppawn, plance, pknight, psilver, pbishop, prook, king
-};
-
-const small_short unpromoted[NO_PIECES] =
-{
- no_piece, pawn, lance, knight, silver, gold, bishop, rook,
- pawn, lance, knight, silver, bishop, rook, king
-};
-
const small_short is_promoted[NO_PIECES] =
{
- false, false, false, false, false, false, false, false,
- true, true, true, true, true, true, false
+ false, false,
+#ifndef MINISHOGI
+ false, false,
+#endif
+ false, false, false, false,
+ true,
+#ifndef MINISHOGI
+ true, true,
+#endif
+ true, true, true, false
};
/* data used to generate nextpos/nextdir */
+#ifndef MINISHOGI
+/* FIXME: use predefined constants ! */
#if !defined SAVE_NEXTPOS
static
#endif
{ -11, 0, 0, 0, 0, 0, 0, 0 }, /* 11 ptype_wlance */
{ -21, -23, 0, 0, 0, 0, 0, 0 }, /* 12 ptype_wknight */
{ -10, -11, -12, 12, 10, 0, 0, 0 }, /* 13 ptype_wsilver */
- { -10, -11, -12, 1, -1, 11, 0, 0 }
-}; /* 14 ptype_wgold */
+ { -10, -11, -12, 1, -1, 11, 0, 0 } /* 14 ptype_wgold */
+};
+#else
+#if !defined SAVE_NEXTPOS
+static
+#endif
+const small_short direc[NO_PTYPE_PIECES][8] =
+{
+ { 7, 0, 0, 0, 0, 0, 0, 0 }, /* 0 ptype_pawn */
+ { 6, 7, 8, -8, -6, 0, 0, 0 }, /* 3 ptype_silver */
+ { 6, 7, 8, -1, 1, -7, 0, 0 }, /* 4 ptype_gold */
+ { 6, 8, -8, -6, 0, 0, 0, 0 }, /* 5 ptype_bishop */
+ { 7, -1, 1, -7, 0, 0, 0, 0 }, /* 6 ptype_rook */
+ { 6, 8, -8, -6, 7, -1, 1, -7 }, /* 7 ptype_pbishop */
+ { 7, -1, 1, -7, 6, 8, -8, -6 }, /* 8 ptype_prook */
+ { 6, 7, 8, -1, 1, -8, -7, -6 }, /* 9 ptype_king */
+ { -7, 0, 0, 0, 0, 0, 0, 0 }, /* 10 ptype_wpawn */
+ { -6, -7, -8, 8, 6, 0, 0, 0 }, /* 13 ptype_wsilver */
+ { -6, -7, -8, 1, -1, 7, 0, 0 } /* 14 ptype_wgold */
+};
+#endif
small_short diagonal(short d)
}
+#ifndef MINISHOGI
+/* FIXME */
static const small_short max_steps[NO_PTYPE_PIECES] =
{
1, 8, 1, 1, 1, 8, 8, 8, 8, 1, 1, 8, 1, 1, 1
};
+#else
+static const small_short max_steps[NO_PTYPE_PIECES] =
+{
+ 1, 1, 1, 4, 4, 4, 4, 1, 1, 1, 1
+};
+#endif
-
+#ifndef MINISHOGI
const small_short nunmap[(NO_COLS + 2)*(NO_ROWS + 4)] =
{
-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
100, 101, 102, 103, 104, 105, 106, 107, 108,
111, 112, 113, 114, 115, 116, 117, 118, 119
};
+#else
+const small_short nunmap[(NO_COLS + 2)*(NO_ROWS + 2)] =
+{
+ -1, -1, -1, -1, -1, -1, -1,
+ -1, 0, 1, 2, 3, 4, -1,
+ -1, 5, 6, 7, 8, 9, -1,
+ -1, 10, 11, 12, 13, 14, -1,
+ -1, 15, 16, 17, 18, 19, -1,
+ -1, 20, 21, 22, 23, 24, -1,
+ -1, -1, -1, -1, -1, -1, -1,
+};
+const small_short inunmap[NO_SQUARES] =
+{
+ 8, 9, 10, 11, 12,
+ 15, 16, 17, 18, 19,
+ 22, 23, 24, 25, 26,
+ 29, 30, 31, 32, 33,
+ 36, 37, 38, 39, 40,
+};
+#endif
+
int InitFlag = false;
short steps[8];
short fpo = inunmap[0], tpo = 1 + inunmap[NO_SQUARES-1];
+ /* pre-fill nextpos and nextdir with source position, probably so
+ * (color[u] == neutral) stops to match once all moves have been seen
+ */
for (ptyp = 0; ptyp < NO_PTYPE_PIECES; ptyp++)
{
for (po = 0; po < NO_SQUARES; po++)
}
ClearCaptured();
- ClearScreen();
+ dsp->ClearScreen();
InitializeStats();
#ifdef HAVE_GETTIMEOFDAY
if (!InitFlag)
{
char sx[256];
- strcpy(sx, CP[169]);
+ strcpy(sx, "level");
if (TCflag)
SetTimeControl();
else if (MaxResponseTime == 0)
- SelectLevel(sx);
+ dsp->SelectLevel(sx);
- UpdateDisplay(0, 0, 1, 0);
+ dsp->UpdateDisplay(0, 0, 1, 0);
GetOpenings();
GetOpeningPatterns(&max_opening_sequence);
-int
-Initialize_data(void)
-{
- size_t n;
- int i;
- char buffer[60];
- int doit = true;
-
- {
- small_short x = -1;
-
- if (x >= 0)
- {
- ShowMessage("datatype 'small_short' is unsigned; "
- "check gnushogi.h\n");
- return 1;
- }
- }
-
- n = sizeof(struct leaf) * (size_t)TREE;
- Tree = malloc(n);
-
- if (!Tree)
- {
- sprintf(buffer, "Cannot allocate %ld bytes for search tree",
- (long)n);
- ShowMessage(buffer);
- return 1;
- }
-
- n = sizeof(hashcode_array);
- hashcode = malloc(n);
-
- if (!hashcode)
- {
- sprintf(buffer, "Cannot allocate %ld bytes for hashcode", (long)n);
- ShowMessage(buffer);
- return 1;
- }
-
- n = sizeof(drop_hashcode_array);
- drop_hashcode = malloc(n);
-
- if (!drop_hashcode)
- {
- sprintf(buffer,
- "Cannot allocate %ld bytes for drop_hashcode",
- (long)n);
- ShowMessage(buffer);
- return 1;
- }
-
- n = sizeof(struct GameRec) * (size_t)(MAXMOVES + MAXDEPTH);
- GameList = malloc(n);
-
- if (!GameList)
- {
- sprintf(buffer,
- "Cannot allocate %ld bytes for game record",
- (long)n);
- ShowMessage(buffer);
- return 1;
- }
-
-#if !defined SAVE_NEXTPOS
- n = sizeof(next_array);
-
- for (i = 0; i < NO_PTYPE_PIECES; i++)
- {
- nextdir[i] = use_nextpos ? malloc(n) : NULL;
-
- if (!nextdir[i])
- {
- if (use_nextpos)
- {
- sprintf(buffer, "cannot allocate %ld space for nextdir %d",
- (long)(n), i);
- ShowMessage(buffer);
- }
-
- nextdir[i] = NULL;
- use_nextpos = false;
- }
-
- nextpos[i] = use_nextpos ? malloc(n) : NULL;
-
- if (!nextpos[i])
- {
- if (use_nextpos)
- {
- sprintf(buffer, "cannot allocate %ld space for nextpos %d",
- (long)(n), i);
- ShowMessage(buffer);
- }
-
- use_nextpos = false;
- }
- }
-
- if (!use_nextpos)
- {
- return 1;
- }
-#endif
-
- n = sizeof(value_array);
- value = malloc(n);
-
- if (!value)
- {
- ShowMessage("cannot allocate value space");
- return 1;
- }
-
- n = sizeof(fscore_array);
- fscore = malloc(n);
-
- if (!fscore)
- {
- ShowMessage("cannot allocate fscore space");
- return 1;
- }
-
-#if defined HISTORY
- n = sizeof_history;
- history = malloc(n);
-
- if (!history)
- {
- sprintf(buffer, "Cannot allocate %ld bytes for history table",
- (long)sizeof_history);
- ShowMessage(buffer);
- use_history = false;
- }
-#endif
-
-#if defined CACHE
- n = sizeof(struct etable) * (size_t)ETABLE;
-
- for (i = 0; i < 2; i++)
- {
- etab[i] = use_etable ? malloc(n) : 0;
-
- if (!etab[i])
- {
- sprintf(buffer, "Cannot allocate %ld bytes for cache table %ld",
- (long)n, (long)i);
- ShowMessage(buffer);
- use_etable = false;
- }
- }
-#endif
-
-#if ttblsz
-
- if (rehash < 0)
- rehash = MAXrehash;
-
- n = sizeof(struct hashentry)*(ttblsize + rehash);
-
- while (doit && ttblsize > MINTTABLE)
- {
- ttable[0] = malloc(n); /* FIXME: cast to the correct type. */
- ttable[1] = ttable[0] ? malloc(n) : NULL;
-
- if (!ttable[0] || !ttable[1])
- {
- if (!ttable[0])
- free(ttable[0]);
-
- if (!ttable[1])
- free(ttable[1]);
-
- ttblsize = ttblsize >> 1;
- n = sizeof(struct hashentry) * (ttblsize + rehash);
- }
- else
- {
- doit = false;
- }
- }
-
- if (ttblsize <= MINTTABLE)
- {
- use_ttable = false;
- }
-
- if (use_ttable)
- {
- /* CHECKME: is the precedence here correct? */
- /* ttbllimit = ttblsize << 1 - ttblsize >> 2; */
- ttbllimit = (ttblsize << 1) - (ttblsize >> 2);
- }
- else
- {
- sprintf(buffer, "Cannot allocate %ld bytes for transposition table",
- (long)(2 * n));
- ShowMessage(buffer);
- ttable[0] = ttable[1] = NULL;
- }
-#endif /* ttblsz */
-
-#if !defined SAVE_DISTDATA
- n = sizeof(distdata_array);
- distdata = malloc(n);
-
- if (!distdata)
- {
- ShowMessage("cannot allocate distdata space...");
- use_distdata = false;
- }
-#endif
-
-#if !defined SAVE_PTYPE_DISTDATA
- n = sizeof(distdata_array);
-
- for (i = 0; i < NO_PTYPE_PIECES; i++)
- {
- ptype_distdata[i] = use_ptype_distdata ? malloc(n) : 0;
-
- if (!ptype_distdata[i])
- {
- sprintf(buffer,
- "cannot allocate %ld bytes for ptype_distdata %d...",
- (long)n, i);
- use_ptype_distdata = false;
- }
- }
-#endif
-
- return 0;
-}
-
-
-#if defined EXTLANGFILE
-
-#ifdef OLDLANGFILE
-
-void
-InitConst(char *lang)
-{
- FILE *constfile;
- char s[256];
- char sl[5];
- char buffer[120];
- int len, entry;
- char *p, *q;
- constfile = fopen(LANGFILE, "r");
-
- if (!constfile)
- {
- ShowMessage("NO LANGFILE");
- exit(1);
- }
-
- while (fgets(s, sizeof(s), constfile))
- {
- if (s[0] == '!')
- continue;
-
- len = strlen(s);
-
- for (q = &s[len]; q > &s[8]; q--)
- if (*q == '}')
- break;
-
- if (q == &s[8])
- {
- ShowMessage("{ error in cinstfile");
- exit(1);
- }
-
- *q = '\0';
-
- if ((s[3] != ':') || (s[7] != ':') || (s[8] != '{'))
- {
- sprintf(buffer, "Langfile format error %s", s);
- ShowMessage(buffer);
- exit(1);
- }
-
- s[3] = s[7] = '\0';
-
- if (lang == NULL)
- {
- lang = sl;
- strcpy(sl, &s[4]);
- }
-
- if (strcmp(&s[4], lang))
- continue;
-
- entry = atoi(s);
-
- if ((entry < 0) || (entry >= CPSIZE))
- {
- ShowMessage("Langfile number error");
- exit(1);
- }
-
- for (q = p = &s[9]; *p; p++)
- {
- if (*p != '\\')
- {
- *q++ = *p;
- }
- else if (*(p + 1) == 'n')
- {
- *q++ = '\n';
- p++;
- }
- }
-
- *q = '\0';
-
- if ((entry < 0) || (entry > 255))
- {
- sprintf(buffer, "Langfile error %d\n", entry);
- ShowMessage(buffer);
- exit(0);
- }
-
- CP[entry] = (char *)GLOBAL_ALLOC((unsigned) strlen(&s[9]) + 1);
-
- if (CP[entry] == NULL)
- {
- char buffer[80];
- sprintf(buffer, "CP MALLOC, entry %d", entry);
- perror(buffer);
- exit(0);
- }
-
- strcpy(CP[entry], &s[9]);
- }
-
- fclose(constfile);
-}
-
-#else
-
-void
-InitConst(char *lang)
-{
- FILE *constfile;
- char s[256];
- char sl[5];
- char buffer[120];
- int len, entry;
- char *p, *q;
- constfile = fopen(LANGFILE, "r");
-
- if (!constfile)
- {
- ShowMessage("NO LANGFILE");
- exit(1);
- }
-
- while (fgets(s, sizeof(s), constfile))
- {
- if (s[0] == '!')
- continue;
-
- len = strlen(s);
-
- if ((len > 3) && (s[3] == ':') || (len > 7) && (s[7] == ':'))
- {
- ShowMessage("old Langfile error");
- exit(1);
- }
-
- if (len <= 15)
- {
- ShowMessage("length error in Langfile");
- exit(1);
- }
-
- for (q = &s[len]; q > &s[15]; q--)
- {
- if (*q == '"')
- break;
- }
-
- if (q == &s[15])
- {
- ShowMessage("\" error in Langfile");
- exit(1);
- }
-
- *q = '\0';
-
- if ((s[6] != ':') || (s[10] != ':') || (s[15] != '"'))
- {
- sprintf(buffer, "Langfile format error %s", s);
- ShowMessage(buffer);
- exit(1);
- }
-
- s[6] = s[10] = '\0';
-
- if (lang == NULL)
- {
- lang = sl;
- strcpy(sl, &s[7]);
- }
-
- if (strcmp(&s[7], lang))
- continue;
-
- entry = atoi(&s[3]);
-
- if ((entry < 0) || (entry >= CPSIZE))
- {
- ShowMessage("Langfile number error");
- exit(1);
- }
-
- for (q = p = &s[16]; *p; p++)
- {
- if (*p != '\\')
- {
- *q++ = *p;
- }
- else if (*(p + 1) == 'n')
- {
- *q++ = '\n';
- p++;
- }
- }
-
- *q = '\0';
-
- if ((entry < 0) || (entry > 255))
- {
- sprintf(buffer, "Langfile error %d\n", entry);
- ShowMessage(buffer);
- exit(0);
- }
-
- CP[entry] = (char *)GLOBAL_ALLOC((unsigned)strlen(&s[16]) + 1);
-
- if (CP[entry] == NULL)
- {
- char buffer[80];
- sprintf(buffer, "CP MALLOC, entry %d", entry);
- perror(buffer);
- exit(0);
- }
-
- strcpy(CP[entry], &s[16]);
- }
-
- fclose(constfile);
-}
-
-#endif
-
-#endif
-
int
InitMain(void)
if (Initialize_data() != 0)
return 1;
-#if defined EXTLANGFILE
- InitConst(Lang);
-#endif
-
- strcpy(ColorStr[0], CP[118]);
- strcpy(ColorStr[1], CP[119]);
+ strcpy(ColorStr[0], "Black");
+ strcpy(ColorStr[1], "White");
XC = 0;
MaxResponseTime = 0;
if (XSHOGI)
{
- signal(SIGUSR1, TerminateSearch);
-
TCmoves = 40;
TCminutes = 5;
TCseconds = 0;
barebones = 0;
}
- Initialize();
+ dsp->Initialize();
Initialize_dist();
Initialize_eval();
#if !defined SAVE_NEXTPOS
#endif /* HASHFILE */
#endif /* ttblsz */
- ExitShogi();
+ dsp->ExitShogi();
}