# include "zippy.h"
#endif
#include "backendz.h"
-#include "gettext.h"
-
-#ifdef ENABLE_NLS
-# define _(s) gettext (s)
-# define N_(s) gettext_noop (s)
+#include "gettext.h"
+
+#ifdef ENABLE_NLS
+# define _(s) gettext (s)
+# define N_(s) gettext_noop (s)
# define T_(s) gettext(s)
-#else
+#else
# ifdef WIN32
# define _(s) T_(s)
# define N_(s) s
# else
-# define _(s) (s)
-# define N_(s) s
+# define _(s) (s)
+# define N_(s) s
# define T_(s) s
# endif
-#endif
+#endif
/* A point in time */
#define TN_SGA 0003
#define TN_PORT 23
-/* [AS] */
-static char * safeStrCpy( char * dst, const char * src, size_t count )
+char*
+safeStrCpy( char *dst, const char *src, size_t count )
{
- assert( dst != NULL );
- assert( src != NULL );
- assert( count > 0 );
+ /* see for example: https://buildsecurityin.us-cert.gov/bsi-rules/home/g1/854-BSI.html
+ *
+ * usage: safeStrCpy( stringA, stringB, sizeof(stringA)/sizeof(stringA[0]);
+ *
+ */
+
+ assert( dst != NULL );
+ assert( src != NULL );
+ assert( count > 0 );
+
+ strncpy( dst, src, count );
+ if( dst[ count-1 ] != '\0' )
+ {
+ if(appData.debugMode)
+ printf("safeStrCpy: copying %s into %s didn't work, not enough space %d\n",src,dst,count);
+ }
+ dst[ count-1 ] = '\0';
- strncpy( dst, src, count );
- dst[ count-1 ] = '\0';
- return dst;
+ return dst;
}
/* Some compiler can't cast u64 to double
case VariantKriegspiel:
flags |= F_KRIEGSPIEL_CAPTURE;
break;
- case VariantCapaRandom:
+ case VariantCapaRandom:
case VariantFischeRandom:
flags |= F_FRC_TYPE_CASTLING; /* [HGM] enable this through flag */
case VariantNoCastle:
FILE *gameFileFP, *debugFP;
-/*
+/*
[AS] Note: sometimes, the sscanf() function is used to parse the input
into a fixed-size buffer. Because of this, we must be prepared to
receive strings as long as the size of the input buffer, which is currently
int nrCastlingRights; // For TwoKings, or to implement castling-unknown status
int initialRulePlies, FENrulePlies;
FILE *serverMoves = NULL; // next two for broadcasting (/serverMoves option)
-int loadFlag = 0;
+int loadFlag = 0;
int shuffleOpenings;
int mute; // mute all sounds
};
ChessSquare CapablancaArray[2][BOARD_FILES] = {
- { WhiteRook, WhiteKnight, WhiteAngel, WhiteBishop, WhiteQueen,
+ { WhiteRook, WhiteKnight, WhiteAngel, WhiteBishop, WhiteQueen,
WhiteKing, WhiteBishop, WhiteMarshall, WhiteKnight, WhiteRook },
- { BlackRook, BlackKnight, BlackAngel, BlackBishop, BlackQueen,
+ { BlackRook, BlackKnight, BlackAngel, BlackBishop, BlackQueen,
BlackKing, BlackBishop, BlackMarshall, BlackKnight, BlackRook }
};
ChessSquare GreatArray[2][BOARD_FILES] = {
- { WhiteDragon, WhiteKnight, WhiteAlfil, WhiteGrasshopper, WhiteKing,
+ { WhiteDragon, WhiteKnight, WhiteAlfil, WhiteGrasshopper, WhiteKing,
WhiteSilver, WhiteCardinal, WhiteAlfil, WhiteKnight, WhiteDragon },
- { BlackDragon, BlackKnight, BlackAlfil, BlackGrasshopper, BlackKing,
+ { BlackDragon, BlackKnight, BlackAlfil, BlackGrasshopper, BlackKing,
BlackSilver, BlackCardinal, BlackAlfil, BlackKnight, BlackDragon },
};
ChessSquare JanusArray[2][BOARD_FILES] = {
- { WhiteRook, WhiteAngel, WhiteKnight, WhiteBishop, WhiteKing,
+ { WhiteRook, WhiteAngel, WhiteKnight, WhiteBishop, WhiteKing,
WhiteQueen, WhiteBishop, WhiteKnight, WhiteAngel, WhiteRook },
- { BlackRook, BlackAngel, BlackKnight, BlackBishop, BlackKing,
+ { BlackRook, BlackAngel, BlackKnight, BlackBishop, BlackKing,
BlackQueen, BlackBishop, BlackKnight, BlackAngel, BlackRook }
};
#ifdef GOTHIC
ChessSquare GothicArray[2][BOARD_FILES] = {
- { WhiteRook, WhiteKnight, WhiteBishop, WhiteQueen, WhiteMarshall,
+ { WhiteRook, WhiteKnight, WhiteBishop, WhiteQueen, WhiteMarshall,
WhiteKing, WhiteAngel, WhiteBishop, WhiteKnight, WhiteRook },
- { BlackRook, BlackKnight, BlackBishop, BlackQueen, BlackMarshall,
+ { BlackRook, BlackKnight, BlackBishop, BlackQueen, BlackMarshall,
BlackKing, BlackAngel, BlackBishop, BlackKnight, BlackRook }
};
#else // !GOTHIC
#ifdef FALCON
ChessSquare FalconArray[2][BOARD_FILES] = {
- { WhiteRook, WhiteKnight, WhiteBishop, WhiteLance, WhiteQueen,
+ { WhiteRook, WhiteKnight, WhiteBishop, WhiteLance, WhiteQueen,
WhiteKing, WhiteLance, WhiteBishop, WhiteKnight, WhiteRook },
- { BlackRook, BlackKnight, BlackBishop, BlackLance, BlackQueen,
+ { BlackRook, BlackKnight, BlackBishop, BlackLance, BlackQueen,
BlackKing, BlackLance, BlackBishop, BlackKnight, BlackRook }
};
#else // !FALCON
if (appData.icsActive) {
appData.matchMode = FALSE;
appData.matchGames = 0;
-#if ZIPPY
+#if ZIPPY
appData.noChessProgram = !appData.zippyPlay;
#else
appData.zippyPlay = FALSE;
/* [AS] Adjudication threshold */
adjudicateLossThreshold = appData.adjudicateLossThreshold;
-
+
first.which = _("first");
second.which = _("second");
first.maybeThinking = second.maybeThinking = FALSE;
TidyProgramName(first.program, first.host, first.tidy);
TidyProgramName(second.program, second.host, second.tidy);
first.matchWins = second.matchWins = 0;
- strcpy(first.variants, appData.variant);
- strcpy(second.variants, appData.variant);
+ safeStrCpy(first.variants, appData.variant, sizeof(first.variants)/sizeof(first.variants[0]));
+ safeStrCpy(second.variants, appData.variant,sizeof(second.variants)/sizeof(second.variants[0]));
first.analysisSupport = second.analysisSupport = 2; /* detect */
first.analyzing = second.analyzing = FALSE;
first.initDone = second.initDone = FALSE;
appData.clockMode = FALSE;
first.sendTime = second.sendTime = 0;
}
-
+
#if ZIPPY
/* Override some settings from environment variables, for backward
compatibility. Unfortunately it's not feasible to have the env
ZippyInit();
}
#endif
-
+
if (appData.noChessProgram) {
programVersion = (char*) malloc(5 + strlen(PACKAGE_STRING));
sprintf(programVersion, "%s", PACKAGE_STRING);
if( NextTimeControlFromString( &tc, &tc1 ) != 0 ) {
return FALSE;
}
-
+
if( *tc == '/' ) {
/* Parse second time control */
tc++;
-
+
if( NextTimeControlFromString( &tc, &tc2 ) != 0 ) {
return FALSE;
}
-
+
if( tc2 == 0 ) {
return FALSE;
}
-
+
timeControl_2 = tc2 * 1000;
}
else {
timeControl_2 = 0;
}
-
+
if( tc1 == 0 ) {
return FALSE;
}
-
+
timeControl = tc1 * 1000;
-
+
if (ti >= 0) {
timeIncrement = ti * 1000; /* convert to ms */
movesPerSession = 0;
if (appData.icsActive) {
#ifdef WIN32
/* [DM] Make a console window if needed [HGM] merged ifs */
- ConsoleCreate();
+ ConsoleCreate();
#endif
err = establish();
if (err != 0) {
if (*appData.icsCommPort != NULLCHAR) {
- sprintf(buf, _("Could not open comm port %s"),
+ sprintf(buf, _("Could not open comm port %s"),
appData.icsCommPort);
} else {
- snprintf(buf, sizeof(buf), _("Could not connect to host %s, port %s"),
+ snprintf(buf, sizeof(buf), _("Could not connect to host %s, port %s"),
appData.icsHost, appData.icsPort);
}
DisplayFatalError(buf, err, 1);
cmailISR =
AddInputSource(cmailPR, FALSE, CmailSigHandlerCallBack, &cmailISR);
}
-
+
ThawUI();
DisplayMessage("", "");
if (StrCaseCmp(appData.initialMode, "") == 0) {
} else if (StrCaseCmp(appData.initialMode, "TwoMachines") == 0) {
initialMode = TwoMachinesPlay;
} else if (StrCaseCmp(appData.initialMode, "AnalyzeFile") == 0) {
- initialMode = AnalyzeFile;
+ initialMode = AnalyzeFile;
} else if (StrCaseCmp(appData.initialMode, "Analysis") == 0) {
initialMode = AnalyzeMode;
} else if (StrCaseCmp(appData.initialMode, "MachineWhite") == 0) {
appData.icsHost, appData.icsPort);
} else {
snprintf(buf, sizeof(buf), "%s %s -l %s %s %s %s",
- appData.remoteShell, appData.gateway,
+ appData.remoteShell, appData.gateway,
appData.remoteUser, appData.telnetProgram,
appData.icsHost, appData.icsPort);
}
/* Remove all highlighting escape sequences in s
- Also deletes any suffix starting with '('
+ Also deletes any suffix starting with '('
*/
char *
StripHighlightAndTitle(s)
if (!found) {
if ((StrCaseStr(e, "fischer") && StrCaseStr(e, "random"))
- || StrCaseStr(e, "wild/fr")
+ || StrCaseStr(e, "wild/fr")
|| StrCaseStr(e, "frc") || StrCaseStr(e, "960")) {
v = VariantFischeRandom;
} else if ((i = 4, p = StrCaseStr(e, "wild")) ||
v = VariantShatranj;
break;
- /* Temporary names for future ICC types. The name *will* change in
+ /* Temporary names for future ICC types. The name *will* change in
the next xboard/WinBoard release after ICC defines it. */
case 29:
v = Variant29;
char *bufp = &buf[*index], *patternp = pattern;
int star_count = 0;
char *matchp = star_match[0];
-
+
for (;;) {
if (*patternp == NULLCHAR) {
*index = leftover_start = bufp - buf;
* case we want to add those holdings to the already received position.
*/
-
+
if (appData.debugMode) {
fprintf(debugFP, "Switch board from %s to %s\n",
VariantName(gameInfo.variant), VariantName(newVariant));
}
shuffleOpenings = 0; /* [HGM] shuffle */
gameInfo.holdingsSize = 5; /* [HGM] prepare holdings */
- switch(newVariant)
+ switch(newVariant)
{
case VariantShogi:
newWidth = 9; newHeight = 9;
default:
newHoldingsWidth = gameInfo.holdingsSize = 0;
};
-
+
if(newWidth != gameInfo.boardWidth ||
newHeight != gameInfo.boardHeight ||
newHoldingsWidth != gameInfo.holdingsWidth ) {
-
+
/* shift position to new playing area, if needed */
if(newHoldingsWidth > gameInfo.holdingsWidth) {
- for(i=0; i<BOARD_HEIGHT; i++)
+ for(i=0; i<BOARD_HEIGHT; i++)
for(j=BOARD_RGHT-1; j>=BOARD_LEFT; j--)
board[i][j+newHoldingsWidth-gameInfo.holdingsWidth] =
board[i][j];
#define STARTED_CHATTER 5
#define STARTED_COMMENT 6
#define STARTED_MOVES_NOHIDE 7
-
+
static int started = STARTED_NONE;
static char parse[20000];
static int parse_pos = 0;
static int savingComment = FALSE;
static int cmatch = 0; // continuation sequence match
char *bp;
- char str[500];
+ char str[MSG_SIZ];
int i, oldi;
int buf_len;
int next_out;
// next_out = leftover_len; // [HGM] should we set this to 0, and not print it in advance?
next_out = 0;
leftover_start = 0;
-
+
i = 0;
while (i < buf_len) {
/* Deal with part of the TELNET option negotiation
next_out = i;
continue;
}
-
+
/* OK, this at least will *usually* work */
if (!loggedOn && looking_at(buf, &i, "ics%")) {
loggedOn = TRUE;
}
-
+
if (loggedOn && !intfSet) {
if (ics_type == ICS_ICC) {
sprintf(str,
} else if (ics_type == ICS_CHESSNET) {
sprintf(str, "/style 12\n");
} else {
- strcpy(str, "alias $ @\n$set interface ");
+ safeStrCpy(str, "alias $ @\n$set interface ", sizeof(str)/sizeof(str[0]));
strcat(str, programVersion);
strcat(str, "\n$iset startpos 1\n$iset ms 1\n");
if(appData.seekGraph && appData.autoRefresh) // [HGM] seekgraph
(looking_at(buf, &i, "\"*\" is *a registered name") ||
looking_at(buf, &i, "Logging you in as \"*\"") ||
looking_at(buf, &i, "will be \"*\""))) {
- strcpy(ics_handle, star_match[0]);
+ safeStrCpy(ics_handle, star_match[0], sizeof(ics_handle)/sizeof(ics_handle[0]));
continue;
}
if(looking_at(buf, &i, "* (*) seeking * * * * *\"play *\" to respond)\n")) {
int s = (ics_type == ICS_ICC); // ICC format differs
if(seekGraphUp)
- AddAd(star_match[0], star_match[1], atoi(star_match[2+s]), atoi(star_match[3+s]),
+ AddAd(star_match[0], star_match[1], atoi(star_match[2+s]), atoi(star_match[3+s]),
star_match[4+s][0], star_match[5-3*s], atoi(star_match[7]), TRUE);
looking_at(buf, &i, "*% "); // eat prompt
if(oldi > 0 && buf[oldi-1] == '\n') oldi--; // suppress preceding LF, if any
}
// [HGM] kibitz: try to recognize opponent engine-score kibitzes, to divert them to engine-output window
- if (appData.autoKibitz && started == STARTED_NONE &&
+ if (appData.autoKibitz && started == STARTED_NONE &&
!appData.icsEngineAnalyze && // [HGM] [DM] ICS analyze
(gameMode == IcsPlayingWhite || gameMode == IcsPlayingBlack || gameMode == IcsObserving)) {
if((looking_at(buf, &i, "* kibitzes: ") || looking_at(buf, &i, "* whispers: ")) &&
- (StrStr(star_match[0], gameInfo.white) == star_match[0] ||
+ (StrStr(star_match[0], gameInfo.white) == star_match[0] ||
StrStr(star_match[0], gameInfo.black) == star_match[0] )) { // kibitz of self or opponent
suppressKibitz = TRUE;
if (oldi > next_out) SendToPlayer(&buf[next_out], oldi - next_out);
savingComment = TRUE;
suppressKibitz = gameMode != IcsObserving ? 2 :
(StrStr(star_match[0], gameInfo.white) == NULL) + 1;
- }
+ }
continue;
} else
if((looking_at(buf, &i, "\nkibitzed to *\n") || looking_at(buf, &i, "kibitzed to *\n") ||
// [HGM] chat: intercept tells by users for which we have an open chat window
channel = -1;
- if(started == STARTED_NONE && (looking_at(buf, &i, "* tells you:") || looking_at(buf, &i, "* says:") ||
+ if(started == STARTED_NONE && (looking_at(buf, &i, "* tells you:") || looking_at(buf, &i, "* says:") ||
looking_at(buf, &i, "* whispers:") ||
looking_at(buf, &i, "* kibitzes:") ||
looking_at(buf, &i, "* shouts:") ||
SendToICS("refresh\n");
continue;
}
-
+
if (!have_sent_ICS_logon && looking_at(buf, &i, "login:")) {
ICSInitScript();
have_sent_ICS_logon = 1;
continue;
}
-
- if (ics_getting_history != H_GETTING_MOVES /*smpos kludge*/ &&
+
+ if (ics_getting_history != H_GETTING_MOVES /*smpos kludge*/ &&
(looking_at(buf, &i, "\n<12> ") ||
looking_at(buf, &i, "<12> "))) {
loggedOn = TRUE;
gameInfo.whiteRating = string_to_rating(star_match[1]);
gameInfo.blackRating = string_to_rating(star_match[3]);
if (appData.debugMode)
- fprintf(debugFP, _("Ratings from header: W %d, B %d\n"),
+ fprintf(debugFP, _("Ratings from header: W %d, B %d\n"),
gameInfo.whiteRating, gameInfo.blackRating);
}
continue;
break;
}
continue;
- }
-
+ }
+
if (looking_at(buf, &i, "% ") ||
((started == STARTED_MOVES || started == STARTED_MOVES_NOHIDE)
&& looking_at(buf, &i, "}*"))) { char *bookHit = NULL; // [HGM] book
if (WhiteOnMove(forwardMostMove)) {
if (first.sendTime) {
if (first.useColors) {
- SendToProgram("black\n", &first);
+ SendToProgram("black\n", &first);
}
SendTimeRemaining(&first, TRUE);
}
firstMove = TRUE;
}
}
- }
+ }
}
#endif
if (gameMode == IcsObserving && ics_gamenum == -1) {
if(bookHit) { // [HGM] book: simulate book reply
static char bookMove[MSG_SIZ]; // a bit generous?
- programStats.nodes = programStats.depth = programStats.time =
+ programStats.nodes = programStats.depth = programStats.time =
programStats.score = programStats.got_only_move = 0;
sprintf(programStats.movelist, "%s (xbook)", bookHit);
- strcpy(bookMove, "move ");
+ safeStrCpy(bookMove, "move ", sizeof(bookMove)/sizeof(bookMove[0]));
strcat(bookMove, bookHit);
HandleMachineMove(bookMove, &first);
}
continue;
}
-
+
if ((started == STARTED_MOVES || started == STARTED_BOARD ||
started == STARTED_HOLDINGS ||
started == STARTED_MOVES_NOHIDE) && i >= leftover_len) {
/* Accumulate characters in move list or board */
parse[parse_pos++] = buf[i];
}
-
+
/* Start of game messages. Mostly we detect start of game
when the first board image arrives. On some versions
of the ICS, though, we need to do a "refresh" after starting
SendToICS(str);
/* Save ratings from notify string */
- strcpy(player1Name, star_match[0]);
+ safeStrCpy(player1Name, star_match[0], sizeof(player1Name)/sizeof(player1Name[0]));
player1Rating = string_to_rating(star_match[1]);
- strcpy(player2Name, star_match[2]);
+ safeStrCpy(player2Name, star_match[2], sizeof(player2Name)/sizeof(player2Name[0]));
player2Rating = string_to_rating(star_match[3]);
if (appData.debugMode)
- fprintf(debugFP,
+ fprintf(debugFP,
"Ratings from 'Game notification:' %s %d, %s %d\n",
player1Name, player1Rating,
player2Name, player2Rating);
SendToICS("refresh\n");
}
continue;
- }
-
+ }
+
/* Error messages */
// if (ics_user_moved) {
if (1) { // [HGM] old way ignored error after move type in; ics_user_moved is not set then!
2 empty, white, or black (IGNORED)
3 player 2 name (not necessarily black)
4 player 2 rating
-
+
The names/ratings are sorted out when the game
actually starts (below).
*/
- strcpy(player1Name, StripHighlightAndTitle(star_match[0]));
- player1Rating = string_to_rating(star_match[1]);
- strcpy(player2Name, StripHighlightAndTitle(star_match[3]));
- player2Rating = string_to_rating(star_match[4]);
+ safeStrCpy(player1Name, StripHighlightAndTitle(star_match[0]), sizeof(player1Name)/sizeof(player1Name[0]));
+ player1Rating = string_to_rating(star_match[1]);
+ safeStrCpy(player2Name, StripHighlightAndTitle(star_match[3]), sizeof(player2Name)/sizeof(player2Name[0]));
+ player2Rating = string_to_rating(star_match[4]);
if (appData.debugMode)
- fprintf(debugFP,
+ fprintf(debugFP,
"Ratings from 'Creating:' %s %d, %s %d\n",
player1Name, player1Rating,
player2Name, player2Rating);
continue;
}
-
+
/* Improved generic start/end-of-game messages */
if ((tkind=0, looking_at(buf, &i, "{Game * (* vs. *) *}*")) ||
(tkind=1, looking_at(buf, &i, "{Game * (*(*) vs. *(*)) *}*"))){
if (strncmp(why, "Creating ", 9) == 0 ||
strncmp(why, "Continuing ", 11) == 0) {
gs_gamenum = gamenum;
- strcpy(gs_kind, strchr(why, ' ') + 1);
+ safeStrCpy(gs_kind, strchr(why, ' ') + 1,sizeof(gs_kind)/sizeof(gs_kind[0]));
VariantSwitch(boards[currentMove], StringToVariant(gs_kind)); // [HGM] variantswitch: even before we get first board
#if ZIPPY
if (appData.zippyPlay) {
ClearPremoveHighlights();
if (appData.debugMode)
fprintf(debugFP, "Sending premove:\n");
- UserMoveEvent(premoveFromX, premoveFromY,
- premoveToX, premoveToY,
+ UserMoveEvent(premoveFromX, premoveFromY,
+ premoveToX, premoveToY,
premovePromoChar);
}
}
i++; /* skip unparsed character and loop back */
}
-
+
if (started != STARTED_MOVES && started != STARTED_BOARD && !suppressKibitz && // [HGM] kibitz
// started != STARTED_HOLDINGS && i > next_out) { // [HGM] should we compare to leftover_start in stead of i?
// SendToPlayer(&buf[next_out], i - next_out);
SendToPlayer(&buf[next_out], leftover_start - next_out);
next_out = i;
}
-
+
leftover_len = buf_len - leftover_start;
/* if buffer ends with something we couldn't parse,
reparse it after appending the next read */
-
+
} else if (count == 0) {
RemoveInputSource(isr);
DisplayFatalError(_("Connection closed by ICS"), 0, 0);
/* Board style 12 looks like this:
-
+
<12> r-b---k- pp----pp ---bP--- ---p---- q------- ------P- P--Q--BP -----R-K W -1 0 0 0 0 0 0 paf MaxII 0 2 12 21 25 234 174 24 Q/d7-a4 (0:06) Qxa4 0 0
-
+
* The "<12> " is stripped before it gets to this routine. The two
* trailing 0's (flip state and clock ticking) are later addition, and
* some chess servers may not have them, or may have only the first.
- * Additional trailing fields may be added in the future.
+ * Additional trailing fields may be added in the future.
*/
#define PATTERN "%c%d%d%d%d%d%d%d%s%s%d%d%d%d%d%d%d%d%s%s%s%d%d"
void
ParseBoard12(string)
char *string;
-{
+{
GameMode newGameMode;
int gamenum, newGame, newMove, relation, basetime, increment, ics_flip = 0, i;
int j, k, n, moveNum, white_stren, black_stren, white_time, black_time, takeback;
Boolean weird = FALSE, reqFlag = FALSE;
fromX = fromY = toX = toY = -1;
-
+
newGame = FALSE;
if (appData.debugMode)
0, 1);
return;
}
-
+
switch (relation) {
case RELATION_OBSERVING_PLAYED:
case RELATION_OBSERVING_STATIC:
case RELATION_ISOLATED_BOARD:
default:
/* Just display this board. If user was doing something else,
- we will forget about it until the next board comes. */
+ we will forget about it until the next board comes. */
newGameMode = IcsIdle;
break;
case RELATION_STARTING_POSITION:
newGameMode = gameMode;
break;
}
-
+
if((gameMode == IcsPlayingWhite || gameMode == IcsPlayingBlack)
&& newGameMode == IcsObserving && gamenum != ics_gamenum && appData.bgObserve) {
// [HGM] bughouse: don't act on alien boards while we play. Just parse the board and save it */
return;
}
- if (gameInfo.boardHeight != ranks || gameInfo.boardWidth != files ||
+ if (gameInfo.boardHeight != ranks || gameInfo.boardWidth != files ||
weird && (int)gameInfo.variant <= (int)VariantShogi) {
/* [HGM] We seem to have switched variant unexpectedly
* Try to guess new variant from board size
SendToICS(str);
}
}
-
+
/* Take action if this is the first board of a new game, or of a
different game than is currently being displayed. */
if (gamenum != ics_gamenum || newGameMode != gameMode ||
relation == RELATION_ISOLATED_BOARD) {
-
+
/* Forget the old game and get the history (if any) of the new one */
if (gameMode != BeginningOfGame) {
Reset(TRUE, TRUE);
sprintf(str, "%smoves %d\n", ics_prefix, gamenum);
SendToICS(str);
}
-
+
/* Initially flip the board to have black on the bottom if playing
black or if the ICS flip flag is set, but let the user change
it with the Flip View button. */
- flipView = appData.autoFlipView ?
+ flipView = appData.autoFlipView ?
(newGameMode == IcsPlayingBlack) || ics_flip :
appData.flipView;
-
+
/* Done with values from previous mode; copy in new ones */
gameMode = newGameMode;
ModeHighlight();
}
gameInfo.outOfBook = NULL;
-
+
/* Do we have the ratings? */
if (strcmp(player1Name, white) == 0 &&
strcmp(player2Name, black) == 0) {
SendToICS("set shout 0\n");
}
}
-
+
/* Deal with midgame name changes */
if (!newGame) {
if (!gameInfo.white || strcmp(gameInfo.white, white) != 0) {
gameInfo.black = StrSave(black);
}
}
-
+
/* Throw away game result if anything actually changes in examine mode */
if (gameMode == IcsExamining && !newGame) {
gameInfo.result = GameUnfinished;
gameInfo.resultDetails = NULL;
}
}
-
+
/* In pausing && IcsExamining mode, we ignore boards coming
in if they are in a different variation than we are. */
if (pauseExamInvalid) return;
return;
}
}
-
+
if (appData.debugMode) {
fprintf(debugFP, "load %dx%d board\n", files, ranks);
}
/* [HGM] e.p. rights. Assume that ICS sends file number here? */
boards[moveNum][EP_STATUS] = double_push == -1 ? EP_NONE : double_push + BOARD_LEFT;
-
+
if (ics_getting_history == H_GOT_REQ_HEADER ||
ics_getting_history == H_GOT_UNREQ_HEADER) {
/* This was an initial position from a move list, not
the current position */
return;
}
-
+
/* Update currentMove and known move number limits */
newMove = newGame || moveNum > forwardMostMove;
if (!pausing || currentMove > forwardMostMove)
currentMove = forwardMostMove;
} else {
- /* New part of history that is not contiguous with old part */
+ /* New part of history that is not contiguous with old part */
if (pausing && gameMode == IcsExamining) {
pauseExamInvalid = TRUE;
forwardMostMove = pauseExamForwardMostMove;
}
forwardMostMove = backwardMostMove = currentMove = moveNum;
}
-
+
/* Update the clocks */
if (strchr(elapsed_time, '.')) {
/* Time is in ms */
timeRemaining[0][moveNum] = whiteTimeRemaining = white_time * 1000;
timeRemaining[1][moveNum] = blackTimeRemaining = black_time * 1000;
}
-
+
#if ZIPPY
if (appData.zippyPlay && newGame &&
gameMode != IcsExamining)
ZippyFirstBoard(moveNum, basetime, increment);
#endif
-
+
/* Put the move on the move list, first converting
to canonical algebraic form. */
if (moveNum > 0) {
if (moveNum <= backwardMostMove) {
/* We don't know what the board looked like before
this move. Punt. */
- strcpy(parseList[moveNum - 1], move_str);
+ safeStrCpy(parseList[moveNum - 1], move_str, sizeof(parseList[moveNum - 1])/sizeof(parseList[moveNum - 1][0]));
strcat(parseList[moveNum - 1], " ");
strcat(parseList[moveNum - 1], elapsed_time);
moveList[moveNum - 1][0] = NULLCHAR;
startedFromSetupPosition = TRUE;
fromX = fromY = toX = toY = -1;
} else {
- // [HGM] long SAN: if legality-testing is off, disambiguation might not work or give wrong move.
+ // [HGM] long SAN: if legality-testing is off, disambiguation might not work or give wrong move.
// So we parse the long-algebraic move string in stead of the SAN move
int valid; char buf[MSG_SIZ], *prom;
// str looks something like "Q/a1-a2"; kill the slash
- if(str[1] == '/')
+ if(str[1] == '/')
sprintf(buf, "%c%s", str[0], str+2);
- else strcpy(buf, str); // might be castling
- if((prom = strstr(move_str, "=")) && !strstr(buf, "="))
+ else safeStrCpy(buf, str, sizeof(buf)/sizeof(buf[0])); // might be castling
+ if((prom = strstr(move_str, "=")) && !strstr(buf, "="))
strcat(buf, prom); // long move lacks promo specification!
if(!appData.testLegality && move_str[1] != '@') { // drops never ambiguous (parser chokes on long form!)
- if(appData.debugMode)
+ if(appData.debugMode)
fprintf(debugFP, "replaced ICS move '%s' by '%s'\n", move_str, buf);
- strcpy(move_str, buf);
+ safeStrCpy(move_str, buf, sizeof(move_str)/sizeof(move_str[0]));
}
valid = ParseOneMove(move_str, moveNum - 1, &moveType,
&fromX, &fromY, &toX, &toY, &promoChar)
strcat(parseList[moveNum - 1], " ");
strcat(parseList[moveNum - 1], elapsed_time);
/* currentMoveString is set as a side-effect of ParseOneMove */
- strcpy(moveList[moveNum - 1], currentMoveString);
+ safeStrCpy(moveList[moveNum - 1], currentMoveString, sizeof(moveList[moveNum - 1])/sizeof(moveList[moveNum - 1][0]));
strcat(moveList[moveNum - 1], "\n");
} else {
/* Move from ICS was illegal!? Punt. */
- if (appData.debugMode) {
- fprintf(debugFP, "Illegal move from ICS '%s'\n", move_str);
- fprintf(debugFP, "board L=%d, R=%d, H=%d, holdings=%d\n", BOARD_LEFT, BOARD_RGHT, BOARD_HEIGHT, gameInfo.holdingsWidth);
- }
- strcpy(parseList[moveNum - 1], move_str);
+ if (appData.debugMode) {
+ fprintf(debugFP, "Illegal move from ICS '%s'\n", move_str);
+ fprintf(debugFP, "board L=%d, R=%d, H=%d, holdings=%d\n", BOARD_LEFT, BOARD_RGHT, BOARD_HEIGHT, gameInfo.holdingsWidth);
+ }
+ safeStrCpy(parseList[moveNum - 1], move_str, sizeof(parseList[moveNum - 1])/sizeof(parseList[moveNum - 1][0]));
strcat(parseList[moveNum - 1], " ");
strcat(parseList[moveNum - 1], elapsed_time);
moveList[moveNum - 1][0] = NULLCHAR;
#if ZIPPY
/* Send move to chess program (BEFORE animating it). */
- if (appData.zippyPlay && !newGame && newMove &&
+ if (appData.zippyPlay && !newGame && newMove &&
(!appData.getMoveList || backwardMostMove == 0) && first.initDone) {
if ((gameMode == IcsPlayingWhite && WhiteOnMove(moveNum)) ||
SetHighlights(fromX, fromY, toX, toY);
}
}
-
+
/* Start the clocks */
whiteFlag = blackFlag = FALSE;
appData.clockMode = !(basetime == 0 && increment == 0);
DisplayBothClocks();
else
StartClocks();
-
+
/* Display opponents and material strengths */
if (gameInfo.variant != VariantBughouse &&
gameInfo.variant != VariantCrazyhouse && !appData.noGUI) {
if (tinyLayout || smallLayout) {
if(gameInfo.variant == VariantNormal)
- sprintf(str, "%s(%d) %s(%d) {%d %d}",
+ sprintf(str, "%s(%d) %s(%d) {%d %d}",
gameInfo.white, white_stren, gameInfo.black, black_stren,
basetime, increment);
else
- sprintf(str, "%s(%d) %s(%d) {%d %d w%d}",
+ sprintf(str, "%s(%d) %s(%d) {%d %d w%d}",
gameInfo.white, white_stren, gameInfo.black, black_stren,
basetime, increment, (int) gameInfo.variant);
} else {
if(gameInfo.variant == VariantNormal)
- sprintf(str, "%s (%d) vs. %s (%d) {%d %d}",
+ sprintf(str, "%s (%d) vs. %s (%d) {%d %d}",
gameInfo.white, white_stren, gameInfo.black, black_stren,
basetime, increment);
else
- sprintf(str, "%s (%d) vs. %s (%d) {%d %d %s}",
+ sprintf(str, "%s (%d) vs. %s (%d) {%d %d %s}",
gameInfo.white, white_stren, gameInfo.black, black_stren,
basetime, increment, VariantName(gameInfo.variant));
}
/* Display the board */
if (!pausing && !appData.noGUI) {
-
+
if (appData.premove)
- if (!gotPremove ||
+ if (!gotPremove ||
((gameMode == IcsPlayingWhite) && (WhiteOnMove(currentMove))) ||
((gameMode == IcsPlayingBlack) && (!WhiteOnMove(currentMove))))
ClearPremoveHighlights();
if(bookHit) { // [HGM] book: simulate book reply
static char bookMove[MSG_SIZ]; // a bit generous?
- programStats.nodes = programStats.depth = programStats.time =
+ programStats.nodes = programStats.depth = programStats.time =
programStats.score = programStats.got_only_move = 0;
sprintf(programStats.movelist, "%s (xbook)", bookHit);
- strcpy(bookMove, "move ");
+ safeStrCpy(bookMove, "move ", sizeof(bookMove)/sizeof(bookMove[0]));
strcat(bookMove, bookHit);
HandleMachineMove(bookMove, &first);
}
AlphaRank(moveList[moveNum], 4); // and back
} else
/* Added by Tord: Send castle moves in "O-O" in FRC games if required by
- * the engine. It would be nice to have a better way to identify castle
+ * the engine. It would be nice to have a better way to identify castle
* moves here. */
if((gameInfo.variant == VariantFischeRandom || gameInfo.variant == VariantCapaRandom)
&& cps->useOOCastle) {
- int fromX = moveList[moveNum][0] - AAA;
+ int fromX = moveList[moveNum][0] - AAA;
int fromY = moveList[moveNum][1] - ONE;
- int toX = moveList[moveNum][2] - AAA;
+ int toX = moveList[moveNum][2] - AAA;
int toY = moveList[moveNum][3] - ONE;
- if((boards[moveNum][fromY][fromX] == WhiteKing
+ if((boards[moveNum][fromY][fromX] == WhiteKing
&& boards[moveNum][toY][toX] == WhiteRook)
- || (boards[moveNum][fromY][fromX] == BlackKing
+ || (boards[moveNum][fromY][fromX] == BlackKing
&& boards[moveNum][toY][toX] == BlackRook)) {
if(toX > fromX) SendToProgram("O-O\n", cps);
else SendToProgram("O-O-O\n", cps);
if(ics_type == ICS_ICC) { // on ICC match ourselves in applicable variant
sprintf(command, "match %s", ics_handle);
} else { // on FICS we must first go to general examine mode
- strcpy(command, "examine\nbsetup"); // and specify variant within it with bsetups
+ safeStrCpy(command, "examine\nbsetup", sizeof(command)/sizeof(command[0])); // and specify variant within it with bsetups
}
if(gameInfo.variant != VariantNormal) {
// try figure out wild number, as xboard names are not always valid on ICS
fprintf(debugFP, "alphaRank(%s,%d)\n", move, n);
}
- if(move[1]=='*' &&
+ if(move[1]=='*' &&
move[2]>='0' && move[2]<='9' &&
move[3]>='a' && move[3]<='x' ) {
move[1] = '@';
ChessMove *moveType;
int *fromX, *fromY, *toX, *toY;
char *promoChar;
-{
+{
if (appData.debugMode) {
fprintf(debugFP, "move to parse: %s\n", move);
}
if (appData.testLegality) {
return (*moveType != IllegalMove);
} else {
- return !(*fromX == *toX && *fromY == *toY) && boards[moveNum][*fromY][*fromX] != EmptySquare &&
+ return !(*fromX == *toX && *fromY == *toY) && boards[moveNum][*fromY][*fromX] != EmptySquare &&
WhiteOnMove(moveNum) == (boards[moveNum][*fromY][*fromX] < BlackPawn);
}
fprintf(debugFP,"parsePV: %d %c%c%c%c yy='%s'\nPV = '%s'\n", valid, fromX+AAA, fromY+ONE, toX+AAA, toY+ONE, yy_textstr, pv);
}
if(!valid && nr == 0 &&
- ParseOneMove(pv, endPV-1, &moveType, &fromX, &fromY, &toX, &toY, &promoChar)){
+ ParseOneMove(pv, endPV-1, &moveType, &fromX, &fromY, &toX, &toY, &promoChar)){
nr++; moveType = Comment; // First move has been played; kludge to make sure we continue
// Hande case where played move is different from leading PV move
CopyBoard(boards[endPV+1], boards[endPV-1]); // tentatively unplay last game move
moveList[endPV-1][2] = toX + AAA;
moveList[endPV-1][3] = toY + ONE;
parseList[endPV-1][0] = NULLCHAR;
- strcpy(moveList[endPV-2], "_0_0"); // suppress premove highlight on takeback move
+ safeStrCpy(moveList[endPV-2], "_0_0", sizeof(moveList[endPV-2])/sizeof(moveList[endPV-2][0])); // suppress premove highlight on takeback move
}
}
pv = strstr(pv, yy_textstr) + strlen(yy_textstr); // skip what we parsed
board[rank][i] = (ChessSquare) pieceType;
squaresLeft[((i-BOARD_LEFT)&1) + 1]--;
squaresLeft[ANY]--;
- piecesLeft[pieceType]--;
+ piecesLeft[pieceType]--;
return i;
}
}
{
int result = FALSE; int NrPieces;
- if( map != NULL && (NrPieces=strlen(map)) <= (int) EmptySquare
+ if( map != NULL && (NrPieces=strlen(map)) <= (int) EmptySquare
&& NrPieces >= 12 && !(NrPieces&1)) {
int i; /* [HGM] Accept even length from 12 to 34 */
void Prelude(Board board)
{ // [HGM] superchess: random selection of exo-pieces
- int i, j, k; ChessSquare p;
+ int i, j, k; ChessSquare p;
static ChessSquare exoPieces[4] = { WhiteAngel, WhiteMarshall, WhiteSilver, WhiteLance };
GetPositionNumber(); // use FRC position number
if(appData.pieceToCharTable != NULL) { // select pieces to participate from given char table
SetCharTable(pieceToChar, appData.pieceToCharTable);
- for(i=(int)WhiteQueen+1, j=0; i<(int)WhiteKing && j<4; i++)
+ for(i=(int)WhiteQueen+1, j=0; i<(int)WhiteKing && j<4; i++)
if(PieceToChar((ChessSquare)i) != '.') exoPieces[j++] = (ChessSquare) i;
}
- j = seed%4; seed /= 4;
+ j = seed%4; seed /= 4;
p = board[0][BOARD_LEFT+j]; board[0][BOARD_LEFT+j] = EmptySquare; k = PieceToNumber(p);
board[k][BOARD_WIDTH-1] = p; board[k][BOARD_WIDTH-2]++;
board[BOARD_HEIGHT-1-k][0] = WHITE_TO_BLACK p; board[BOARD_HEIGHT-1-k][1]++;
- j = seed%3 + (seed%3 >= j); seed /= 3;
+ j = seed%3 + (seed%3 >= j); seed /= 3;
p = board[0][BOARD_LEFT+j]; board[0][BOARD_LEFT+j] = EmptySquare; k = PieceToNumber(p);
board[k][BOARD_WIDTH-1] = p; board[k][BOARD_WIDTH-2]++;
board[BOARD_HEIGHT-1-k][0] = WHITE_TO_BLACK p; board[BOARD_HEIGHT-1-k][1]++;
- j = seed%3; seed /= 3;
+ j = seed%3; seed /= 3;
p = board[0][BOARD_LEFT+j+5]; board[0][BOARD_LEFT+j+5] = EmptySquare; k = PieceToNumber(p);
board[k][BOARD_WIDTH-1] = p; board[k][BOARD_WIDTH-2]++;
board[BOARD_HEIGHT-1-k][0] = WHITE_TO_BLACK p; board[BOARD_HEIGHT-1-k][1]++;
- j = seed%2 + (seed%2 >= j); seed /= 2;
+ j = seed%2 + (seed%2 >= j); seed /= 2;
p = board[0][BOARD_LEFT+j+5]; board[0][BOARD_LEFT+j+5] = EmptySquare; k = PieceToNumber(p);
board[k][BOARD_WIDTH-1] = p; board[k][BOARD_WIDTH-2]++;
board[BOARD_HEIGHT-1-k][0] = WHITE_TO_BLACK p; board[BOARD_HEIGHT-1-k][1]++;
castlingRank[3] = castlingRank[4] = castlingRank[5] = BOARD_HEIGHT-1;
}
-
+
/* [HGM] logic here is completely changed. In stead of full positions */
/* the initialized data only consist of the two backranks. The switch */
/* selects which one we will use, which is than copied to the Board */
case VariantShatranj:
pieces = ShatranjArray;
nrCastlingRights = 0;
- SetCharTable(pieceToChar, "PN.R.QB...Kpn.r.qb...k");
+ SetCharTable(pieceToChar, "PN.R.QB...Kpn.r.qb...k");
break;
case VariantMakruk:
pieces = makrukArray;
nrCastlingRights = 0;
startedFromSetupPosition = TRUE;
- SetCharTable(pieceToChar, "PN.R.M....SKpn.r.m....sk");
+ SetCharTable(pieceToChar, "PN.R.M....SKpn.r.m....sk");
break;
case VariantTwoKings:
pieces = twoKingsArray;
case VariantCapablanca:
pieces = CapablancaArray;
gameInfo.boardWidth = 10;
- SetCharTable(pieceToChar, "PNBRQ..ACKpnbrq..ack");
+ SetCharTable(pieceToChar, "PNBRQ..ACKpnbrq..ack");
break;
case VariantGothic:
pieces = GothicArray;
gameInfo.boardWidth = 10;
- SetCharTable(pieceToChar, "PNBRQ..ACKpnbrq..ack");
+ SetCharTable(pieceToChar, "PNBRQ..ACKpnbrq..ack");
break;
case VariantJanus:
pieces = JanusArray;
gameInfo.boardWidth = 10;
- SetCharTable(pieceToChar, "PNBRQ..JKpnbrq..jk");
+ SetCharTable(pieceToChar, "PNBRQ..JKpnbrq..jk");
nrCastlingRights = 6;
initialPosition[CASTLING][0] = initialRights[0] = BOARD_RGHT-1;
initialPosition[CASTLING][1] = initialRights[1] = BOARD_LEFT;
case VariantFalcon:
pieces = FalconArray;
gameInfo.boardWidth = 10;
- SetCharTable(pieceToChar, "PNBRQ.............FKpnbrq.............fk");
+ SetCharTable(pieceToChar, "PNBRQ.............FKpnbrq.............fk");
break;
case VariantXiangqi:
pieces = XiangqiArray;
gameInfo.boardWidth = 9;
gameInfo.boardHeight = 10;
nrCastlingRights = 0;
- SetCharTable(pieceToChar, "PH.R.AE..K.C.ph.r.ae..k.c.");
+ SetCharTable(pieceToChar, "PH.R.AE..K.C.ph.r.ae..k.c.");
break;
case VariantShogi:
pieces = ShogiArray;
gameInfo.boardHeight = 9;
gameInfo.holdingsSize = 7;
nrCastlingRights = 0;
- SetCharTable(pieceToChar, "PNBRLS...G.++++++Kpnbrls...g.++++++k");
+ SetCharTable(pieceToChar, "PNBRLS...G.++++++Kpnbrls...g.++++++k");
break;
case VariantCourier:
pieces = CourierArray;
gameInfo.boardWidth = 12;
nrCastlingRights = 0;
- SetCharTable(pieceToChar, "PNBR.FE..WMKpnbr.fe..wmk");
+ SetCharTable(pieceToChar, "PNBR.FE..WMKpnbr.fe..wmk");
break;
case VariantKnightmate:
pieces = KnightmateArray;
- SetCharTable(pieceToChar, "P.BRQ.....M.........K.p.brq.....m.........k.");
+ SetCharTable(pieceToChar, "P.BRQ.....M.........K.p.brq.....m.........k.");
break;
case VariantFairy:
pieces = fairyArray;
- SetCharTable(pieceToChar, "PNBRQFEACWMOHIJGDVLSUKpnbrqfeacwmohijgdvlsuk");
+ SetCharTable(pieceToChar, "PNBRQFEACWMOHIJGDVLSUKpnbrqfeacwmohijgdvlsuk");
break;
case VariantGreat:
pieces = GreatArray;
case VariantCrazyhouse:
case VariantBughouse:
pieces = FIDEArray;
- SetCharTable(pieceToChar, "PNBRQ.......~~~~Kpnbrq.......~~~~k");
+ SetCharTable(pieceToChar, "PNBRQ.......~~~~Kpnbrq.......~~~~k");
gameInfo.holdingsSize = 5;
break;
case VariantWildCastle:
initialPosition[BOARD_HEIGHT-pawnRow-1][j] = BlackPawn;
if(gameInfo.variant == VariantXiangqi) {
if(j&1) {
- initialPosition[pawnRow][j] =
+ initialPosition[pawnRow][j] =
initialPosition[BOARD_HEIGHT-pawnRow-1][j] = EmptySquare;
if(j==BOARD_LEFT+1 || j>=BOARD_RGHT-2) {
initialPosition[2][j] = WhiteCannon;
/* This sets default castling rights from none to normal corners */
/* Variants with other castling rights must set them themselves above */
nrCastlingRights = 6;
-
+
initialPosition[CASTLING][0] = initialRights[0] = BOARD_RGHT-1;
initialPosition[CASTLING][1] = initialRights[1] = BOARD_LEFT;
initialPosition[CASTLING][2] = initialRights[2] = BOARD_WIDTH>>1;
int moveNum;
{
char message[MSG_SIZ];
-
+
if (cps->useSetboard) {
char* fen = PositionToFEN(moveNum, cps->fenOverride);
sprintf(message, "setboard %s\n", fen);
bp = &boards[moveNum][i][BOARD_LEFT];
for (j = BOARD_LEFT; j < BOARD_RGHT; j++, bp++) {
if ((int) *bp < (int) BlackPawn) {
- sprintf(message, "%c%c%c\n", PieceToChar(*bp),
+ sprintf(message, "%c%c%c\n", PieceToChar(*bp),
AAA + j, ONE + i);
if(message[0] == '+' || message[0] == '~') {
sprintf(message, "%c%c%c+\n",
}
}
}
-
+
SendToProgram("c\n", cps);
for (i = BOARD_HEIGHT - 1; i >= 0; i--) {
bp = &boards[moveNum][i][BOARD_LEFT];
}
}
}
-
+
SendToProgram(".\n", cps);
}
setboardSpoiledMachineBlack = 0; /* [HGM] assume WB 4.2.7 already solves this after sending setboard */
if (!white_piece && WhiteOnMove(currentMove)) {
DisplayMoveError(_("It is White's turn"));
return FALSE;
- }
+ }
if (white_piece && !WhiteOnMove(currentMove)) {
DisplayMoveError(_("It is Black's turn"));
return FALSE;
- }
+ }
if (cmailMsgLoaded && (currentMove < cmailOldMove)) {
/* Editing correspondence game history */
/* Could disallow this or prompt for confirmation */
}
}
break;
-
+
case Training:
if (!white_piece && WhiteOnMove(currentMove)) {
DisplayMoveError(_("It is White's turn"));
return FALSE;
- }
+ }
if (white_piece && !WhiteOnMove(currentMove)) {
DisplayMoveError(_("It is Black's turn"));
return FALSE;
- }
+ }
break;
default:
default:
return FALSE;
}
- cl.pieceIn = EmptySquare;
+ cl.pieceIn = EmptySquare;
cl.rfIn = *y;
cl.ffIn = *x;
cl.rtIn = -1;
premoveFromY = fromY;
premovePromoChar = promoChar;
gotPremove = 1;
- if (appData.debugMode)
+ if (appData.debugMode)
fprintf(debugFP, "Got premove: fromX %d,"
"fromY %d, toX %d, toY %d\n",
fromX, fromY, toX, toY);
premoveFromY = fromY;
premovePromoChar = promoChar;
gotPremove = 1;
- if (appData.debugMode)
+ if (appData.debugMode)
fprintf(debugFP, "Got premove: fromX %d,"
"fromY %d, toX %d, toY %d\n",
fromX, fromY, toX, toY);
if(fromX == BOARD_LEFT-2) { // handle 'moves' out of holdings
if(boards[0][fromY][0] != EmptySquare) {
if(boards[0][fromY][1]) boards[0][fromY][1]--;
- if(boards[0][fromY][1] == 0) boards[0][fromY][0] = EmptySquare;
+ if(boards[0][fromY][1] == 0) boards[0][fromY][0] = EmptySquare;
}
} else
if(fromX == BOARD_RGHT+1) {
if(boards[0][fromY][BOARD_WIDTH-1] != EmptySquare) {
if(boards[0][fromY][BOARD_WIDTH-2]) boards[0][fromY][BOARD_WIDTH-2]--;
- if(boards[0][fromY][BOARD_WIDTH-2] == 0) boards[0][fromY][BOARD_WIDTH-1] = EmptySquare;
+ if(boards[0][fromY][BOARD_WIDTH-2] == 0) boards[0][fromY][BOARD_WIDTH-1] = EmptySquare;
}
} else
boards[0][fromY][fromX] = EmptySquare;
{
char *bookHit = 0;
- if((gameInfo.variant == VariantSuper || gameInfo.variant == VariantGreat) && promoChar != NULLCHAR) {
+ if((gameInfo.variant == VariantSuper || gameInfo.variant == VariantGreat) && promoChar != NULLCHAR) {
// [HGM] superchess: suppress promotions to non-available piece
int k = PieceToNumber(CharToPiece(ToUpper(promoChar)));
if(WhiteOnMove(currentMove)) {
performed after it is known to what we promote. */
if (gameMode == Training) {
/* compare the move played on the board to the next move in the
- * game. If they match, display the move and the opponent's response.
+ * game. If they match, display the move and the opponent's response.
* If they don't match, display an error message.
*/
int saveAnimate;
/* Ok, now we know that the move is good, so we can kill
the previous line in Analysis Mode */
- if ((gameMode == AnalyzeMode || gameMode == EditGame)
+ if ((gameMode == AnalyzeMode || gameMode == EditGame)
&& currentMove < forwardMostMove) {
PushTail(currentMove, forwardMostMove); // [HGM] vari: save tail of game
}
break;
}
break;
-
+
case MachinePlaysBlack:
case MachinePlaysWhite:
/* disable certain menu options while machine is thinking */
}
userOfferedDraw = FALSE; // [HGM] drawclaim: after move made, and tested for claimable draw
-
+
if(bookHit) { // [HGM] book: simulate book reply
static char bookMove[MSG_SIZ]; // a bit generous?
- programStats.nodes = programStats.depth = programStats.time =
+ programStats.nodes = programStats.depth = programStats.time =
programStats.score = programStats.got_only_move = 0;
sprintf(programStats.movelist, "%s (xbook)", bookHit);
- strcpy(bookMove, "move ");
+ safeStrCpy(bookMove, "move ", sizeof(bookMove)/sizeof(bookMove[0]));
strcat(bookMove, bookHit);
HandleMachineMove(bookMove, &first);
}
MarkTargetSquares(int clear)
{
int x, y;
- if(!appData.markers || !appData.highlightDragging ||
+ if(!appData.markers || !appData.highlightDragging ||
!appData.testLegality || gameMode == EditPosition) return;
if(clear) {
for(x=0; x<BOARD_WIDTH; x++) for(y=0; y<BOARD_HEIGHT; y++) marker[y][x] = 0;
if(clickType == Release) return; // ignore upclick of click-click destination
promotionChoice = FALSE; // only one chance: if click not OK it is interpreted as cancel
if(appData.debugMode) fprintf(debugFP, "promotion click, x=%d, y=%d\n", x, y);
- if(gameInfo.holdingsWidth &&
- (WhiteOnMove(currentMove)
+ if(gameInfo.holdingsWidth &&
+ (WhiteOnMove(currentMove)
? x == BOARD_WIDTH-1 && y < gameInfo.holdingsSize && y > 0
: x == 0 && y >= BOARD_HEIGHT - gameInfo.holdingsSize && y < BOARD_HEIGHT-1) ) {
// click in right holdings, for determining promotion piece
WhitePawn <= toP && toP <= WhiteKing &&
!(fromP == WhiteKing && toP == WhiteRook && frc) &&
!(fromP == WhiteRook && toP == WhiteKing && frc)) ||
- (BlackPawn <= fromP && fromP <= BlackKing &&
+ (BlackPawn <= fromP && fromP <= BlackKing &&
BlackPawn <= toP && toP <= BlackKing &&
!(fromP == BlackRook && toP == BlackKing && frc) && // allow also RxK as FRC castling
!(fromP == BlackKing && toP == BlackRook && frc))) {
if(gameMode == EditPosition && piece != EmptySquare &&
fromX >= BOARD_LEFT && fromX < BOARD_RGHT) {
int n;
-
+
if(x == BOARD_LEFT-2 && piece >= BlackPawn) {
n = PieceToNumber(piece - (int)BlackPawn);
if(n >= gameInfo.holdingsSize) { n = 0; piece = BlackPawn; }
stats.an_move_count = cpstats->nr_moves;
}
- if(stats.pv && stats.pv[0]) strcpy(lastPV[stats.which], stats.pv); // [HGM] pv: remember last PV of each
+ if(stats.pv && stats.pv[0]) safeStrCpy(lastPV[stats.which], stats.pv, sizeof(lastPV[stats.which])/sizeof(lastPV[stats.which][0])); // [HGM] pv: remember last PV of each
SetProgramStats( &stats );
}
{
int myPawns = pCnt[WhitePawn+side]; // my total Pawn count;
int majorDefense = pCnt[BlackRook-side] + pCnt[BlackCannon-side] + pCnt[BlackKnight-side];
-
+
nMine -= pCnt[WhiteFerz+side] + pCnt[WhiteAlfil+side]; // discount defenders
if(nMine - myPawns > 2) return FALSE; // no trivial draws with more than 1 major
if(myPawns == 2 && nMine == 3) // KPP
return majorDefense || pCnt[BlackFerz-side] + pCnt[BlackAlfil-side]*2 >= 5;
if(myPawns) return FALSE;
if(pCnt[WhiteRook+side])
- return pCnt[BlackRook-side] ||
+ return pCnt[BlackRook-side] ||
pCnt[BlackCannon-side] && (pCnt[BlackFerz-side] >= 2 || pCnt[BlackAlfil-side] >= 2) ||
pCnt[BlackKnight-side] && pCnt[BlackFerz-side] + pCnt[BlackAlfil-side] > 2 ||
pCnt[BlackFerz-side] + pCnt[BlackAlfil-side] >= 4;
} else if(pCnt[WhiteKing] == 1 && pCnt[BlackKing] == 1) { // other variants with orthodox Kings
int nBishops = pCnt[WhiteBishop+side] + pCnt[WhiteFerz+side];
-
+
if(nMine == 1) return FALSE; // bare King
if(nBishops && bisColor == 3) return TRUE; // There must be a second B/A/F, which can either block (his) or attack (mine) the escape square
nMine += (nBishops > 0) - nBishops; // By now all Bishops (and Ferz) on like-colored squares, so count as one
if(nMine > 2 && nMine != pCnt[WhiteAlfil+side] + 1) return TRUE; // At least two pieces, not all Alfils
// by now we have King + 1 piece (or multiple Bishops on the same color)
if(pCnt[WhiteKnight+side])
- return (pCnt[BlackKnight-side] + pCnt[BlackBishop-side] + pCnt[BlackMan-side] +
+ return (pCnt[BlackKnight-side] + pCnt[BlackBishop-side] + pCnt[BlackMan-side] +
pCnt[BlackWazir-side] + pCnt[BlackSilver-side] + bisColor // KNKN, KNKB, KNKF, KNKE, KNKW, KNKM, KNKS
|| nHis > 3); // be sure to cover suffocation mates in corner (e.g. KNKQCA)
if(nBishops)
if(engineOpponent)
SendMoveToProgram(forwardMostMove-1, engineOpponent); // make sure opponent gets move
ShowMove(fromX, fromY, toX, toY); /*updates currentMove*/
- GameEnds( WhiteOnMove(forwardMostMove) ? BlackWins : WhiteWins,
+ GameEnds( WhiteOnMove(forwardMostMove) ? BlackWins : WhiteWins,
"Xboard adjudication: King destroyed", GE_XBOARD );
return 1;
}
if(engineOpponent)
SendMoveToProgram(forwardMostMove-1, engineOpponent); // make sure opponent gets to see move
ShowMove(fromX, fromY, toX, toY); /*updates currentMove*/
- GameEnds( WhiteOnMove(forwardMostMove) ? WhiteWins : BlackWins,
+ GameEnds( WhiteOnMove(forwardMostMove) ? WhiteWins : BlackWins,
"Xboard adjudication: Bare king", GE_XBOARD );
return 1;
}
if(engineOpponent)
SendMoveToProgram(forwardMostMove-1, engineOpponent); // make sure opponent gets move
ShowMove(fromX, fromY, toX, toY); /*updates currentMove*/
- GameEnds( nrW > 1 ? WhiteWins : nrB > 1 ? BlackWins : GameIsDrawn,
+ GameEnds( nrW > 1 ? WhiteWins : nrB > 1 ? BlackWins : GameIsDrawn,
"Xboard adjudication: Bare king", GE_XBOARD );
return 1;
}
/* Then some trivial draws (only adjudicate, cannot be claimed) */
if(gameInfo.variant == VariantXiangqi ?
SufficientDefence(nr, WhitePawn, nrW, nrB) && SufficientDefence(nr, BlackPawn, nrB, nrW)
- : nrW + nrB == 4 &&
+ : nrW + nrB == 4 &&
( nr[WhiteRook] == 1 && nr[BlackRook] == 1 /* KRKR */
|| nr[WhiteQueen] && nr[BlackQueen]==1 /* KQKQ */
|| nr[WhiteKnight]==2 || nr[BlackKnight]==2 /* KNNK */
}
} else moveCount = 6;
}
-
if (appData.debugMode) { int i;
fprintf(debugFP, "repeat test fmm=%d bmm=%d ep=%d, reps=%d\n",
forwardMostMove, backwardMostMove, boards[backwardMostMove][EP_STATUS],
appData.drawRepeats);
for( i=forwardMostMove; i>=backwardMostMove; i-- )
fprintf(debugFP, "%d ep=%d\n", i, (signed char)boards[i][EP_STATUS]);
-
+
}
// Repetition draws and 50-move rule can be applied independently of legality testing
}
if( boards[forwardMostMove][CASTLING][5] != boards[k][CASTLING][5] &&
(boards[k][CASTLING][3] != NoRights || boards[k][CASTLING][4] != NoRights) )
- rights++;
+ rights++;
if( boards[forwardMostMove][CASTLING][5] != NoRights ) {
if( boards[forwardMostMove][CASTLING][3] != boards[k][CASTLING][3] ||
boards[forwardMostMove][CASTLING][4] != boards[k][CASTLING][4] )
/* adjudicate after user-specified nr of repeats */
int result = GameIsDrawn;
char *details = "XBoard adjudication: repetition draw";
- if(gameInfo.variant == VariantXiangqi && appData.testLegality) {
+ if(gameInfo.variant == VariantXiangqi && appData.testLegality) {
// [HGM] xiangqi: check for forbidden perpetuals
int m, ourPerpetual = 1, hisPerpetual = 1;
for(m=forwardMostMove; m>k; m-=2) {
/* if we hit starting position, add initial plies */
if( count == backwardMostMove )
count -= initialRulePlies;
- count = forwardMostMove - count;
+ count = forwardMostMove - count;
if(gameInfo.variant == VariantXiangqi && ( count >= 100 || count >= 2*appData.ruleMoves ) ) {
// adjust reversible move counter for checks in Xiangqi
int i = forwardMostMove - count, inCheck = 0, lastCheck;
cps->bookSuspend = FALSE; // after a 'go' we are never suspended
} else { // 'go' might be sent based on 'firstMove' after this routine returns
if(cps->bookSuspend && !firstMove) // 'go' needed, and it will not be done after we return
- SendToProgram("go\n", cps);
+ SendToProgram("go\n", cps);
cps->bookSuspend = FALSE; // anyhow, we will not be suspended after a miss
}
return bookHit; // notify caller of hit, so it can take action to send move to opponent
* Look for machine move.
*/
if ((sscanf(message, "%s %s %s", buf1, buf2, machineMove) == 3 && strcmp(buf2, "...") == 0) ||
- (sscanf(message, "%s %s", buf1, machineMove) == 2 && strcmp(buf1, "move") == 0))
+ (sscanf(message, "%s %s", buf1, machineMove) == 2 && strcmp(buf1, "move") == 0))
{
/* This method is only useful on engines that support ping */
if (cps->lastPing != cps->lastPong) {
if (cps->offeredDraw) cps->offeredDraw--;
/* currentMoveString is set as a side-effect of ParseOneMove */
- strcpy(machineMove, currentMoveString);
+ safeStrCpy(machineMove, currentMoveString, sizeof(machineMove)/sizeof(machineMove[0]));
strcat(machineMove, "\n");
- strcpy(moveList[forwardMostMove], machineMove);
+ safeStrCpy(moveList[forwardMostMove], machineMove, sizeof(moveList[forwardMostMove])/sizeof(moveList[forwardMostMove][0]));
/* [AS] Save move info*/
pvInfoList[ forwardMostMove ].score = programStats.score;
if( count >= adjudicateLossPlies ) {
ShowMove(fromX, fromY, toX, toY); /*updates currentMove*/
- GameEnds( WhiteOnMove(forwardMostMove) ? WhiteWins : BlackWins,
- "Xboard adjudication",
+ GameEnds( WhiteOnMove(forwardMostMove) ? WhiteWins : BlackWins,
+ "Xboard adjudication",
GE_XBOARD );
return;
}
ShowMove(fromX, fromY, toX, toY); /*updates currentMove*/
-
+
if (!pausing && appData.ringBellAfterMoves) {
RingBell();
}
- /*
+ /*
* Reenable menu items that were disabled while
* machine was thinking
*/
if(bookHit) {
static char bookMove[MSG_SIZ]; // a bit generous?
- strcpy(bookMove, "move ");
+ safeStrCpy(bookMove, "move ", sizeof(bookMove)/sizeof(bookMove[0]));
strcat(bookMove, bookHit);
message = bookMove;
cps = cps->other;
- programStats.nodes = programStats.depth = programStats.time =
+ programStats.nodes = programStats.depth = programStats.time =
programStats.score = programStats.got_only_move = 0;
sprintf(programStats.movelist, "%s (xbook)", bookHit);
CopyBoard(boards[0], initial_position);
initialRulePlies = FENrulePlies;
if(blackPlaysFirst) gameMode = MachinePlaysWhite;
- else gameMode = MachinePlaysBlack;
+ else gameMode = MachinePlaysBlack;
DrawPosition(FALSE, boards[currentMove]);
}
return;
return;
}
if (sscanf(message, "askuser %s %[^\n]", buf1, buf2) == 2) {
- strcpy(realname, cps->tidy);
+ safeStrCpy(realname, cps->tidy, sizeof(realname)/sizeof(realname[0]));
strcat(realname, " query");
AskQuestion(realname, buf2, buf1, cps->pr);
return;
}
- /* Commands from the engine directly to ICS. We don't allow these to be
- * sent until we are logged on. Crafty kibitzes have been known to
+ /* Commands from the engine directly to ICS. We don't allow these to be
+ * sent until we are logged on. Crafty kibitzes have been known to
* interfere with the login process.
*/
if (loggedOn) {
*/
if (strncmp(message + 1, "llegal move", 11) == 0 ||
strncmp(message, "Error", 5) == 0) {
- if (StrStr(message, "name") ||
+ if (StrStr(message, "name") ||
StrStr(message, "rating") || StrStr(message, "?") ||
StrStr(message, "result") || StrStr(message, "board") ||
StrStr(message, "bk") || StrStr(message, "computer") ||
Don't use it. */
cps->sendTime = 0;
}
-
+
/*
* If chess program startup fails, exit with an error message.
* Attempts to recover here are futile.
DisplayFatalError(buf1, 0, 1);
return;
}
-
- /*
+
+ /*
* Look for hint output
*/
if (sscanf(message, "Hint: %s", buf1) == 1) {
DisplayError(buf2, 0);
}
} else {
- strcpy(lastHint, buf1);
+ safeStrCpy(lastHint, buf1, sizeof(lastHint)/sizeof(lastHint[0]));
}
return;
}
r = p + 1;
}
}
-
+
GameEnds(GameIsDrawn, r, GE_ENGINE1 + (cps != &first));
return;
}
}
-
+
/*
* Look for thinking output
*/
}
/* [AS] Negate score if machine is playing black and reporting absolute scores */
- if( cps->scoreIsAbsolute &&
+ if( cps->scoreIsAbsolute &&
( gameMode == MachinePlaysBlack ||
gameMode == TwoMachinesPlay && cps->twoMachinesColor[0] == 'b' ||
gameMode == IcsPlayingBlack || // [HGM] also add other situations where engine should report black POV
if(cps->nps == 0) ticklen = 10*time; // use engine reported time
else ticklen = (1000. * u64ToDouble(nodes)) / cps->nps; // convert node count to time
if(WhiteOnMove(forwardMostMove) && (gameMode == MachinePlaysWhite ||
- gameMode == TwoMachinesPlay && cps->twoMachinesColor[0] == 'w'))
+ gameMode == TwoMachinesPlay && cps->twoMachinesColor[0] == 'w'))
whiteTimeRemaining = timeRemaining[0][forwardMostMove] - ticklen;
if(!WhiteOnMove(forwardMostMove) && (gameMode == MachinePlaysBlack ||
- gameMode == TwoMachinesPlay && cps->twoMachinesColor[0] == 'b'))
+ gameMode == TwoMachinesPlay && cps->twoMachinesColor[0] == 'b'))
blackTimeRemaining = timeRemaining[1][forwardMostMove] - ticklen;
}
(unsigned) sizeof(tempStats.movelist) - 1);
}
- safeStrCpy( tempStats.movelist, buf1, sizeof(tempStats.movelist) );
+ safeStrCpy( tempStats.movelist, buf1, sizeof(tempStats.movelist)/sizeof(tempStats.movelist[0]) );
} else {
sprintf(tempStats.movelist, " no PV\n");
}
SendProgramStatsToFrontend( cps, &tempStats );
- /*
+ /*
[AS] Protect the thinkOutput buffer from overflow... this
is only useful if buf1 hasn't overflowed first!
*/
sprintf(thinkOutput, "[%d]%c%+.2f %s%s",
- plylev,
+ plylev,
(gameMode == TwoMachinesPlay ?
ToUpper(cps->twoMachinesColor[0]) : ' '),
((double) curscore) / 100.0,
programStats.line_is_book = 1;
SendProgramStatsToFrontend( cps, &programStats );
-
- if (currentMove == forwardMostMove || gameMode==AnalyzeMode ||
+
+ if (currentMove == forwardMostMove || gameMode==AnalyzeMode ||
gameMode == AnalyzeFile || appData.icsEngineAnalyze) {
DisplayMove(currentMove - 1);
}
programStats.nodes = nodes;
programStats.moves_left = mvleft;
programStats.nr_moves = mvtot;
- strcpy(programStats.move_name, mvname);
+ safeStrCpy(programStats.move_name, mvname, sizeof(programStats.move_name)/sizeof(programStats.move_name[0]));
programStats.ok_to_send = 1;
programStats.movelist[0] = '\0';
buf1[0] = NULLCHAR;
if (sscanf(message, "%d%c %d %d " u64Display " %[^\n]\n",
- &plylev, &plyext, &curscore, &time, &nodes, buf1) >= 5)
+ &plylev, &plyext, &curscore, &time, &nodes, buf1) >= 5)
{
ChessProgramStats cpstats;
cpstats.movelist[0] = '\0';
if (buf1[0] != NULLCHAR) {
- safeStrCpy( cpstats.movelist, buf1, sizeof(cpstats.movelist) );
+ safeStrCpy( cpstats.movelist, buf1, sizeof(cpstats.movelist)/sizeof(cpstats.movelist[0]) );
}
cpstats.ok_to_send = 0;
/* Parse a game score from the character string "game", and
record it as the history of the current game. The game
- score is NOT assumed to start from the standard position.
+ score is NOT assumed to start from the standard position.
The display is not updated in any way.
*/
void
parseList[boardIndex]);
CopyBoard(boards[boardIndex + 1], boards[boardIndex]);
/* currentMoveString is set as a side-effect of yylex */
- strcpy(moveList[boardIndex], currentMoveString);
+ safeStrCpy(moveList[boardIndex], currentMoveString, sizeof(moveList[boardIndex])/sizeof(moveList[boardIndex][0]));
strcat(moveList[boardIndex], "\n");
boardIndex++;
ApplyMove(fromX, fromY, toX, toY, promoChar, boards[boardIndex]);
oldEP = (signed char)board[EP_STATUS];
board[EP_STATUS] = EP_NONE;
- if( board[toY][toX] != EmptySquare )
- board[EP_STATUS] = EP_CAPTURE;
+ if( board[toY][toX] != EmptySquare )
+ board[EP_STATUS] = EP_CAPTURE;
/* [HGM] In Shatranj and Courier all promotions are to Ferz */
if((gameInfo.variant==VariantShatranj || gameInfo.variant==VariantCourier || gameInfo.variant == VariantMakruk)
gameInfo.variant != VariantBerolina || toX < fromX)
board[EP_STATUS] = toX | berolina;
if(toX<BOARD_RGHT-1 && board[toY][toX+1] == BlackPawn &&
- gameInfo.variant != VariantBerolina || toX > fromX)
+ gameInfo.variant != VariantBerolina || toX > fromX)
board[EP_STATUS] = toX;
}
- } else
+ } else
if( board[fromY][fromX] == BlackPawn ) {
if(fromY != toY) // [HGM] Xiangqi sideway Pawn moves should not count as 50-move breakers
- board[EP_STATUS] = EP_PAWN_MOVE;
+ board[EP_STATUS] = EP_PAWN_MOVE;
if( toY-fromY== -2) {
if(toX>BOARD_LEFT && board[toY][toX-1] == WhitePawn &&
gameInfo.variant != VariantBerolina || toX < fromX)
board[EP_STATUS] = toX | berolina;
if(toX<BOARD_RGHT-1 && board[toY][toX+1] == WhitePawn &&
- gameInfo.variant != VariantBerolina || toX > fromX)
+ gameInfo.variant != VariantBerolina || toX > fromX)
board[EP_STATUS] = toX;
}
}
for(i=0; i<nrCastlingRights; i++) {
if(board[CASTLING][i] == fromX && castlingRank[i] == fromY ||
- board[CASTLING][i] == toX && castlingRank[i] == toY
+ board[CASTLING][i] == toX && castlingRank[i] == toY
) board[CASTLING][i] = NoRights; // revoke for moved or captured piece
}
if (captured != EmptySquare && gameInfo.holdingsSize > 0
&& gameInfo.variant != VariantBughouse ) {
/* [HGM] holdings: Add to holdings, if holdings exist */
- if(gameInfo.variant == VariantSuper || gameInfo.variant == VariantGreat) {
+ if(gameInfo.variant == VariantSuper || gameInfo.variant == VariantGreat) {
// [HGM] superchess: suppress flipping color of captured pieces by reverse pre-flip
captured = (int) captured >= (int) BlackPawn ? BLACK_TO_WHITE captured : WHITE_TO_BLACK captured;
}
if(gameInfo.variant == VariantKnightmate)
king += (int) WhiteUnicorn - (int) WhiteKing;
if(forwardMostMove == 0) {
- if(blackPlaysFirst)
+ if(blackPlaysFirst)
fprintf(serverMoves, "%s;", second.tidy);
fprintf(serverMoves, "%s;", first.tidy);
- if(!blackPlaysFirst)
+ if(!blackPlaysFirst)
fprintf(serverMoves, "%s;", second.tidy);
} else fprintf(serverMoves, loadFlag|lastLoadFlag ? ":" : ";");
lastLoadFlag = loadFlag;
name[0] = ','; // extract next format name from feature and copy with prefixed ','
while(*p && *p != ',') *q++ = *p++;
*q++ = ':'; *q = 0;
- if( appData.defaultPathEGTB && appData.defaultPathEGTB[0] &&
+ if( appData.defaultPathEGTB && appData.defaultPathEGTB[0] &&
strcmp(name, ",nalimov:") == 0 ) {
// take nalimov path from the menu-changeable option first, if it is defined
sprintf(buf, "egtpath nalimov %s\n", appData.defaultPathEGTB);
overruled = gameInfo.boardWidth != 9 || gameInfo.boardHeight != 9 || gameInfo.holdingsSize != 7;
if( gameInfo.variant == VariantBughouse || gameInfo.variant == VariantCrazyhouse )
overruled = gameInfo.boardWidth != 8 || gameInfo.boardHeight != 8 || gameInfo.holdingsSize != 5;
- if( gameInfo.variant == VariantCapablanca || gameInfo.variant == VariantCapaRandom ||
+ if( gameInfo.variant == VariantCapablanca || gameInfo.variant == VariantCapaRandom ||
gameInfo.variant == VariantGothic || gameInfo.variant == VariantFalcon )
overruled = gameInfo.boardWidth != 10 || gameInfo.boardHeight != 8 || gameInfo.holdingsSize != 0;
if( gameInfo.variant == VariantCourier )
overruled = gameInfo.boardWidth != 10 || gameInfo.boardHeight != 8 || gameInfo.holdingsSize != 8;
if(overruled) {
- sprintf(b, "%dx%d+%d_%s", gameInfo.boardWidth, gameInfo.boardHeight,
+ sprintf(b, "%dx%d+%d_%s", gameInfo.boardWidth, gameInfo.boardHeight,
gameInfo.holdingsSize, VariantName(gameInfo.variant)); // cook up sized variant name
/* [HGM] varsize: try first if this defiant size variant is specifically known */
- if(StrStr(cps->variants, b) == NULL) {
+ if(StrStr(cps->variants, b) == NULL) {
// specific sized variant not known, check if general sizing allowed
if (cps->protocolVersion != 1) { // for protocol 1 we cannot check and hope for the best
if(StrStr(cps->variants, "boardsize") == NULL) {
timeIncrement, appData.searchDepth,
searchTime);
}
- if (appData.showThinking
+ if (appData.showThinking
// [HGM] thinking: four options require thinking output to be sent
|| !appData.hideThinkingFromHuman || appData.adjudicateLossThreshold != 0 || EngineOutputIsUp()
) {
SendToProgram(buf, cps);
}
cps->initDone = TRUE;
-}
+}
void
}
err = StartChildProcess(buf, "", &cps->pr);
}
-
+
if (err != 0) {
sprintf(buf, _("Startup failure on '%s'"), cps->program);
DisplayFatalError(buf, err, 1);
cps->isr = NULL;
return;
}
-
+
cps->isr = AddInputSource(cps->pr, TRUE, ReceiveFromProgram, cps);
if (cps->protocolVersion > 1) {
sprintf(buf, "xboard\nprotover %d\n", cps->protocolVersion);
if(index < 0) { // [HGM] autoinc
lastIndex = index = (index == -2 && first.twoMachinesColor[0] == 'b') ? lastIndex : lastIndex+1;
if(appData.rewindIndex > 0 && index > appData.rewindIndex) lastIndex = index = 1;
- }
+ }
LoadGameFromFile(appData.loadGameFile,
index,
appData.loadGameFile, FALSE);
if(index < 0) { // [HGM] autoinc
lastIndex = index = (index == -2 && first.twoMachinesColor[0] == 'b') ? lastIndex : lastIndex+1;
if(appData.rewindIndex > 0 && index > appData.rewindIndex) lastIndex = index = 1;
- }
+ }
LoadPositionFromFile(appData.loadPositionFile,
index,
appData.loadPositionFile);
if (appData.icsActive && (whosays == GE_ENGINE || whosays >= GE_ENGINE1)) {
/* If we are playing on ICS, the server decides when the
- game is over, but the engine can offer to draw, claim
- a draw, or resign.
+ game is over, but the engine can offer to draw, claim
+ a draw, or resign.
*/
#if ZIPPY
if (appData.zippyPlay && first.initDone) {
/* If this is an ICS game, only ICS can really say it's done;
if not, anyone can. */
- isIcsGame = (gameMode == IcsPlayingWhite ||
- gameMode == IcsPlayingBlack ||
- gameMode == IcsObserving ||
+ isIcsGame = (gameMode == IcsPlayingWhite ||
+ gameMode == IcsPlayingBlack ||
+ gameMode == IcsObserving ||
gameMode == IcsExamining);
if (!isIcsGame || whosays == GE_ICS) {
/* OK -- not an ICS game, or ICS said it was done */
StopClocks();
- if (!isIcsGame && !appData.noChessProgram)
+ if (!isIcsGame && !appData.noChessProgram)
SetUserThinkingEnables();
-
+
/* [HGM] if a machine claims the game end we verify this claim */
if(gameMode == TwoMachinesPlay && appData.testClaims) {
if(appData.testLegality && whosays >= GE_ENGINE1 ) {
}
/* [HGM] bare: don't allow bare King to win */
if((gameInfo.holdingsWidth == 0 || gameInfo.variant == VariantSuper || gameInfo.variant == VariantGreat)
- && gameInfo.variant != VariantLosers && gameInfo.variant != VariantGiveaway
+ && gameInfo.variant != VariantLosers && gameInfo.variant != VariantGiveaway
&& gameInfo.variant != VariantSuicide // [HGM] losers: except in losers, of course...
&& result != GameIsDrawn)
{ int i, j, k=0, color = (result==WhiteWins ? (int)WhitePawn : (int)BlackPawn);
/* display last move only if game was not loaded from file */
if ((whosays != GE_FILE) && (currentMove == forwardMostMove))
DisplayMove(currentMove - 1);
-
+
if (forwardMostMove != 0) {
if (gameMode != PlayFromGameFile && gameMode != EditGame
&& lastSavedGame != GameCheckSum() // [HGM] save: suppress duplicates
}
}
} else if (gameMode == EditGame ||
- gameMode == PlayFromGameFile ||
- gameMode == AnalyzeMode ||
+ gameMode == PlayFromGameFile ||
+ gameMode == AnalyzeMode ||
gameMode == AnalyzeFile) {
nextGameMode = gameMode;
} else {
if (first.isr != NULL)
RemoveInputSource(first.isr);
first.isr = NULL;
-
+
if (first.pr != NoProc) {
ExitAnalyzeMode();
DoSleep( appData.delayBeforeQuit );
if (second.isr != NULL)
RemoveInputSource(second.isr);
second.isr = NULL;
-
+
if (second.pr != NoProc) {
DoSleep( appData.delayBeforeQuit );
SendToProgram("quit\n", &second);
/* Assumes program was just initialized (initString sent).
Leaves program in force mode. */
void
-FeedMovesToProgram(cps, upto)
+FeedMovesToProgram(cps, upto)
ChessProgramState *cps;
int upto;
{
int i;
-
+
if (appData.debugMode)
fprintf(debugFP, "Feeding %smoves %d through %d to %s chess program\n",
startedFromSetupPosition ? "position and " : "",
If so, restart it and feed it all the moves made so far. */
if (appData.noChessProgram || first.pr != NoProc) return;
-
+
StartChessProgram(&first);
InitChessProgram(&first, FALSE);
FeedMovesToProgram(&first, currentMove);
white_holding[0] = black_holding[0] = NULLCHAR;
ClearProgramStats();
opponentKibitzes = FALSE; // [HGM] kibitz: do not reserve space in engine-output window in zippy mode
-
+
ResetFrontEnd();
ClearHighlights();
flipView = appData.flipView;
return FALSE;
}
-
+
toX = moveList[currentMove][2] - AAA;
toY = moveList[currentMove][3] - ONE;
ChessMove moveType;
char move[MSG_SIZ];
char *p, *q;
-
- if (gameMode != PlayFromGameFile && gameMode != AnalyzeFile &&
+
+ if (gameMode != PlayFromGameFile && gameMode != AnalyzeFile &&
gameMode != AnalyzeMode && gameMode != Training) {
gameFileFP = NULL;
return FALSE;
}
-
+
yyboardindex = forwardMostMove;
if (readAhead != (ChessMove)0) {
moveType = readAhead;
return FALSE;
moveType = (ChessMove) yylex();
}
-
+
done = FALSE;
switch (moveType) {
case Comment:
- if (appData.debugMode)
+ if (appData.debugMode)
fprintf(debugFP, "Parsed Comment: %s\n", yy_text);
p = yy_text;
} else {
/* currentMoveString is set as a side-effect of yylex */
strcat(currentMoveString, "\n");
- strcpy(moveList[forwardMostMove], currentMoveString);
-
+ safeStrCpy(moveList[forwardMostMove], currentMoveString, sizeof(moveList[forwardMostMove])/sizeof(moveList[forwardMostMove][0]));
+
thinkOutput[0] = NULLCHAR;
MakeMove(fromX, fromY, toX, toY, promoChar);
currentMove = forwardMostMove;
if (appData.debugMode)
fprintf(debugFP, "Restoring %s for game %d\n",
cmailMove[lastLoadGameNumber - 1], lastLoadGameNumber);
-
+
thinkOutput[0] = NULLCHAR;
- strcpy(moveList[currentMove], cmailMove[lastLoadGameNumber - 1]);
+ safeStrCpy(moveList[currentMove], cmailMove[lastLoadGameNumber - 1], sizeof(moveList[currentMove])/sizeof(moveList[currentMove][0]));
fromX = cmailMove[lastLoadGameNumber - 1][0] - AAA;
fromY = cmailMove[lastLoadGameNumber - 1][1] - ONE;
toX = cmailMove[lastLoadGameNumber - 1][2] - AAA;
promoChar = cmailMove[lastLoadGameNumber - 1][4];
MakeMove(fromX, fromY, toX, toY, promoChar);
ShowMove(fromX, fromY, toX, toY);
-
+
switch (MateTest(boards[currentMove], PosFlags(currentMove)) ) {
case MT_NONE:
case MT_CHECK:
break;
-
+
case MT_CHECKMATE:
case MT_STAINMATE:
if (WhiteOnMove(currentMove)) {
GameEnds(WhiteWins, "White mates", GE_PLAYER);
}
break;
-
+
case MT_STALEMATE:
GameEnds(GameIsDrawn, "Stalemate", GE_PLAYER);
break;
}
break;
-
+
case CMAIL_RESIGN:
if (WhiteOnMove(currentMove)) {
GameEnds(BlackWins, "White resigns", GE_PLAYER);
GameEnds(WhiteWins, "Black resigns", GE_PLAYER);
}
break;
-
+
case CMAIL_ACCEPT:
GameEnds(GameIsDrawn, "Draw agreed", GE_PLAYER);
break;
-
+
default:
break;
}
GameMode oldGameMode;
VariantClass oldVariant = gameInfo.variant; /* [HGM] PGNvariant */
- if (appData.debugMode)
+ if (appData.debugMode)
fprintf(debugFP, "LoadGame(): on entry, gameMode %d\n", gameMode);
if (gameMode == Training )
if (useList) {
lg = (ListGame *) ListElem(&gameList, gameNumber-1);
-
+
if (lg) {
fseek(f, lg->offset, 0);
GameListHighlight(gameNumber);
}
lastLoadGameFP = f;
lastLoadGameNumber = gameNumber;
- strcpy(lastLoadGameTitle, title);
+ safeStrCpy(lastLoadGameTitle, title, sizeof(lastLoadGameTitle)/sizeof(lastLoadGameTitle[0]));
lastLoadGameUseList = useList;
yynewfile(f);
/*
* Skip the first gn-1 games in the file.
- * Also skip over anything that precedes an identifiable
- * start of game marker, to avoid being confused by
- * garbage at the start of the file. Currently
+ * Also skip over anything that precedes an identifiable
+ * start of game marker, to avoid being confused by
+ * garbage at the start of the file. Currently
* recognized start of game markers are the move number "1",
* the pattern "gnuchess .* game", the pattern
- * "^[#;%] [^ ]* game file", and a PGN tag block.
+ * "^[#;%] [^ ]* game file", and a PGN tag block.
* A game that starts with one of the latter two patterns
* will also have a move number 1, possibly
* following a position diagram.
gn--;
lastLoadGameStart = cm;
break;
-
+
case MoveNumberOne:
switch (lastLoadGameStart) {
case GNUChessGame:
break;
}
}
-
+
if (appData.debugMode)
fprintf(debugFP, "Parsed game start '%s' (%d)\n", yy_text, (int) cm);
free(gameInfo.event);
}
gameInfo.event = StrSave(yy_text);
- }
+ }
startedFromSetupPosition = FALSE;
while (cm == PGNTag) {
- if (appData.debugMode)
+ if (appData.debugMode)
fprintf(debugFP, "Parsed PGNTag: %s\n", yy_text);
err = ParsePGNTag(yy_text, &gameInfo);
if (!err) numPGNTags++;
ResetFrontEnd(); // [HGM] might need other bitmaps. Cannot use Reset() because it clears gameInfo :-(
InitPosition(TRUE);
oldVariant = gameInfo.variant;
- if (appData.debugMode)
+ if (appData.debugMode)
fprintf(debugFP, "New variant %d\n", (int) oldVariant);
}
if (blackPlaysFirst) {
currentMove = forwardMostMove = backwardMostMove = 1;
CopyBoard(boards[1], initial_position);
- strcpy(moveList[0], "");
- strcpy(parseList[0], "");
+ safeStrCpy(moveList[0], "", sizeof(moveList[0])/sizeof(moveList[0][0]));
+ safeStrCpy(parseList[0], "", sizeof(parseList[0])/sizeof(parseList[0][0]));
timeRemaining[0][1] = whiteTimeRemaining;
timeRemaining[1][1] = blackTimeRemaining;
if (commentList[0] != NULL) {
/* Handle comments interspersed among the tags */
while (cm == Comment) {
char *p;
- if (appData.debugMode)
+ if (appData.debugMode)
fprintf(debugFP, "Parsed Comment: %s\n", yy_text);
p = yy_text;
AppendComment(currentMove, p, FALSE);
}
while (*p == ' ' || *p == '\t' ||
*p == '\n' || *p == '\r') p++;
-
+
if (strncmp(p, "black", strlen("black"))==0)
blackPlaysFirst = TRUE;
else
blackPlaysFirst = FALSE;
startedFromSetupPosition = TRUE;
-
+
CopyBoard(boards[0], initial_position);
if (blackPlaysFirst) {
currentMove = forwardMostMove = backwardMostMove = 1;
CopyBoard(boards[1], initial_position);
- strcpy(moveList[0], "");
- strcpy(parseList[0], "");
+ safeStrCpy(moveList[0], "", sizeof(moveList[0])/sizeof(moveList[0][0]));
+ safeStrCpy(parseList[0], "", sizeof(parseList[0])/sizeof(parseList[0][0]));
timeRemaining[0][1] = whiteTimeRemaining;
timeRemaining[1][1] = blackTimeRemaining;
if (commentList[0] != NULL) {
fprintf(debugFP, "Load Game\n");
}
DisplayBothClocks();
- }
+ }
/* [HGM] server: flag to write setup moves in broadcast file as one */
loadFlag = appData.suppressLoadMoves;
while (cm == Comment) {
char *p;
- if (appData.debugMode)
+ if (appData.debugMode)
fprintf(debugFP, "Parsed Comment: %s\n", yy_text);
p = yy_text;
AppendComment(currentMove, p, FALSE);
if (!matchMode && (pausing || appData.timeDelay != 0)) {
DisplayComment(currentMove - 1, commentList[currentMove]);
}
- if (!matchMode && appData.timeDelay != 0)
+ if (!matchMode && appData.timeDelay != 0)
DrawPosition(FALSE, boards[currentMove]);
if (gameMode == AnalyzeFile || gameMode == AnalyzeMode) {
}
/* if the first token after the PGN tags is a move
- * and not move number 1, retrieve it from the parser
+ * and not move number 1, retrieve it from the parser
*/
if (cm != MoveNumberOne)
LoadGameOneMove(cm);
AutoPlayGameLoop();
}
- if (appData.debugMode)
+ if (appData.debugMode)
fprintf(debugFP, "LoadGame(): on exit, gameMode %d\n", gameMode);
loadFlag = 0; /* [HGM] true game starts */
char *p, line[MSG_SIZ];
Board initial_position;
int i, j, fenMode, pn;
-
+
if (gameMode == Training )
SetTrainingModeOff();
if (positionNumber == 0) positionNumber = 1;
lastLoadPositionFP = f;
lastLoadPositionNumber = positionNumber;
- strcpy(lastLoadPositionTitle, title);
+ safeStrCpy(lastLoadPositionTitle, title, sizeof(lastLoadPositionTitle)/sizeof(lastLoadPositionTitle[0]));
if (first.pr == NoProc) {
StartChessProgram(&first);
InitChessProgram(&first, FALSE);
- }
+ }
pn = positionNumber;
if (positionNumber < 0) {
/* Negative position number means to seek to that byte offset */
} else {
(void) fgets(line, MSG_SIZ, f);
(void) fgets(line, MSG_SIZ, f);
-
+
for (i = BOARD_HEIGHT - 1; i >= 0; i--) {
(void) fgets(line, MSG_SIZ, f);
for (p = line, j = BOARD_LEFT; j < BOARD_RGHT; p++) {
initial_position[i][j++] = CharToPiece(*p);
}
}
-
+
blackPlaysFirst = FALSE;
if (!feof(f)) {
(void) fgets(line, MSG_SIZ, f);
}
}
startedFromSetupPosition = TRUE;
-
+
SendToProgram("force\n", &first);
CopyBoard(boards[0], initial_position);
if (blackPlaysFirst) {
currentMove = forwardMostMove = backwardMostMove = 1;
- strcpy(moveList[0], "");
- strcpy(parseList[0], "");
+ safeStrCpy(moveList[0], "", sizeof(moveList[0])/sizeof(moveList[0][0]));
+ safeStrCpy(parseList[0], "", sizeof(parseList[0])/sizeof(parseList[0][0]));
CopyBoard(boards[1], initial_position);
DisplayMessage("", _("Black to play"));
} else {
timeRemaining[0][1] = whiteTimeRemaining;
timeRemaining[1][1] = blackTimeRemaining;
DrawPosition(FALSE, boards[currentMove]);
-
+
return TRUE;
}
*p++ = '-';
CopyPlayerNameIntoFileName(&p, gameInfo.black);
*p++ = '.';
- strcpy(p, ext);
+ safeStrCpy(p, ext, MSG_SIZ-2-strlen(gameInfo.white)-strlen(gameInfo.black));
} else {
def[0] = NULLCHAR;
}
{
static char buf[MSG_SIZ];
char *p;
-
+
p = strchr(str, ' ');
if (p == NULL) return str;
strncpy(buf, str, p - str);
}
sprintf( buf+strlen(buf), "%d%s. ", (idx - offset)/2 + 1, idx & 1 ? ".." : "" );
- sprintf( buf+strlen(buf), "%s%.2f",
+ sprintf( buf+strlen(buf), "%s%.2f",
pvInfoList[idx].score >= 0 ? "+" : "",
pvInfoList[idx].score / 100.0 );
}
char move_buffer[100]; /* [AS] Buffer for move+PV info */
offset = backwardMostMove & (~1L); /* output move numbers start at 1 */
-
+
tm = time((time_t *) NULL);
-
+
PrintPGNTags(f, &gameInfo);
-
+
if (backwardMostMove > 0 || startedFromSetupPosition) {
char *fen = PositionToFEN(backwardMostMove, NULL);
fprintf(f, "[FEN \"%s\"]\n[SetUp \"1\"]\n", fen);
GetOutOfBookInfo( buf );
if( buf[0] != '\0' ) {
- fprintf( f, "[%s \"%s\"]\n", PGN_OUT_OF_BOOK, buf );
+ fprintf( f, "[%s \"%s\"]\n", PGN_OUT_OF_BOOK, buf );
}
}
linelen += numlen;
/* Get move */
- strcpy(move_buffer, SavePart(parseList[i])); // [HGM] pgn: print move via buffer, so it can be edited
+ safeStrCpy(move_buffer, SavePart(parseList[i]), sizeof(move_buffer)/sizeof(move_buffer[0])); // [HGM] pgn: print move via buffer, so it can be edited
movelen = strlen(move_buffer); /* [HGM] pgn: line-break point before move */
/* Print move */
sprintf(buf, " %d:%02d%c", seconds/60, seconds%60, 0);
}
- sprintf( move_buffer, "{%s%.2f/%d%s}",
+ sprintf( move_buffer, "{%s%.2f/%d%s}",
pvInfoList[i].score >= 0 ? "+" : "",
pvInfoList[i].score / 100.0,
pvInfoList[i].depth,
i++;
}
-
+
/* Start a new line */
if (linelen > 0) fprintf(f, "\n");
{
int i, offset;
time_t tm;
-
+
tm = time((time_t *) NULL);
-
+
fprintf(f, "# %s game file -- %s", programName, ctime(&tm));
PrintOpponents(f);
-
+
if (backwardMostMove > 0 || startedFromSetupPosition) {
fprintf(f, "\n[--------------\n");
PrintPosition(f, backwardMostMove);
i++;
}
}
-
+
if (commentList[i] != NULL) {
fprintf(f, "[%s]\n", commentList[i]);
}
{
time_t tm;
char *fen;
-
+
if (gameMode == EditPosition) EditPositionDone(TRUE);
if (appData.oldSaveStyle) {
tm = time((time_t *) NULL);
-
+
fprintf(f, "# %s position file -- %s", programName, ctime(&tm));
PrintOpponents(f);
fprintf(f, "[--------------\n");
int i;
struct stat inbuf, outbuf;
int status;
-
+
/* Any registered moves are unregistered if unregister is set, */
/* i.e. invoked by the signal handler */
if (unregister) {
outFilename = (char *) malloc(strlen(appData.cmailGameName) + 5);
sprintf(outFilename, "%s.out", appData.cmailGameName);
}
-
+
status = stat(outFilename, &outbuf);
if (status < 0) {
cmailMailedMove = FALSE;
status = stat(inFilename, &inbuf);
cmailMailedMove = (inbuf.st_mtime < outbuf.st_mtime);
}
-
+
/* LoadGameFromFile(CMAIL_MAX_GAMES) with cmailMsgLoaded == TRUE
counts the games, notes how each one terminated, etc.
-
+
It would be nice to remove this kludge and instead gather all
the information while building the game list. (And to keep it
in the game list nodes instead of having a bunch of fixed-size
*/
cmailMsgLoaded = TRUE;
LoadGameFromFile(inFilename, CMAIL_MAX_GAMES, "", FALSE);
-
+
/* Load first game in the file or popup game menu */
LoadGameFromFile(inFilename, 0, appData.cmailGameName, TRUE);
cmailMoveRegistered[lastLoadGameNumber - 1] = FALSE;
nCmailMovesRegistered --;
- if (cmailCommentList[lastLoadGameNumber - 1] != NULL)
+ if (cmailCommentList[lastLoadGameNumber - 1] != NULL)
{
free(cmailCommentList[lastLoadGameNumber - 1]);
cmailCommentList[lastLoadGameNumber - 1] = NULL;
cmailCommentList[lastLoadGameNumber - 1]
= StrSave(commentList[currentMove]);
}
- strcpy(cmailMove[lastLoadGameNumber - 1], moveList[currentMove - 1]);
+ safeStrCpy(cmailMove[lastLoadGameNumber - 1], moveList[currentMove - 1], sizeof(cmailMove[lastLoadGameNumber - 1])/sizeof(cmailMove[lastLoadGameNumber - 1][0]));
if (appData.debugMode)
fprintf(debugFP, "Saving %s for game %d\n",
sprintf(string,
"%s.game.out.%d", appData.cmailGameName, lastLoadGameNumber);
-
+
f = fopen(string, "w");
if (appData.oldSaveStyle) {
SaveGameOldStyle(f); /* also closes the file */
-
+
sprintf(string, "%s.pos.out", appData.cmailGameName);
f = fopen(string, "w");
SavePosition(f, 0, NULL); /* also closes the file */
fprintf(f, "{--------------\n");
PrintPosition(f, currentMove);
fprintf(f, "--------------}\n\n");
-
+
SaveGame(f, 0, NULL); /* also closes the file*/
}
-
+
cmailMoveRegistered[lastLoadGameNumber - 1] = TRUE;
nCmailMovesRegistered ++;
} else if (nCmailGames == 1) {
#endif
if (! (cmailMailedMove || RegisterMove())) return;
-
+
if ( cmailMailedMove
|| (nCmailMovesRegistered + nCmailResults == nCmailGames)) {
sprintf(string, partCommandString,
char number[5];
char string[MSG_SIZ]; /* Space for game-list */
int i;
-
+
if (!cmailMsgLoaded) return "";
if (cmailMailedMove) {
sprintf(number, "%d", i + 1);
prependComma = 1;
}
-
+
strcat(string, number);
}
}
sprintf(cmailMsg,
_("Still need to make move for game\n"));
break;
-
+
case 2:
sprintf(cmailMsg,
_("Still need to make moves for both games\n"));
break;
-
+
default:
sprintf(cmailMsg,
_("Still need to make moves for all %d games\n"),
_("Still need to make a move for game %s\n"),
string);
break;
-
+
case 0:
if (nCmailResults == nCmailGames) {
sprintf(cmailMsg, _("No unfinished games\n"));
sprintf(cmailMsg, _("Ready to send mail\n"));
}
break;
-
+
default:
sprintf(cmailMsg,
_("Still need to make moves for games %s\n"),
/* Kill off chess programs */
if (first.pr != NoProc) {
ExitAnalyzeMode();
-
+
DoSleep( appData.delayBeforeQuit );
SendToProgram("quit\n", &first);
DoSleep( appData.delayAfterQuit );
DisplayBothClocks();
}
if (gameMode == PlayFromGameFile) {
- if (appData.timeDelay >= 0)
+ if (appData.timeDelay >= 0)
AutoPlayGameLoop();
} else if (gameMode == IcsExamining && pauseExamInvalid) {
Reset(FALSE, TRUE);
char title[MSG_SIZ];
if (currentMove < 1 || parseList[currentMove - 1][0] == NULLCHAR) {
- strcpy(title, _("Edit comment"));
+ safeStrCpy(title, _("Edit comment"), sizeof(title)/sizeof(title[0]));
} else {
- sprintf(title, _("Edit comment on %d.%s%s"), (currentMove - 1) / 2 + 1,
- WhiteOnMove(currentMove - 1) ? " " : ".. ",
- parseList[currentMove - 1]);
+ sprintf(title, _("Edit comment on %d.%s%s"), (currentMove - 1) / 2 + 1,
+ WhiteOnMove(currentMove - 1) ? " " : ".. ",
+ parseList[currentMove - 1]);
}
EditCommentPopUp(currentMove, title, commentList[currentMove]);
return;
- if (gameMode == PlayFromGameFile ||
- gameMode == TwoMachinesPlay ||
- gameMode == Training ||
- gameMode == AnalyzeMode ||
+ if (gameMode == PlayFromGameFile ||
+ gameMode == TwoMachinesPlay ||
+ gameMode == Training ||
+ gameMode == AnalyzeMode ||
gameMode == EndOfGame)
EditGameEvent();
- if (gameMode == EditPosition)
+ if (gameMode == EditPosition)
EditPositionDone(TRUE);
if (!WhiteOnMove(currentMove)) {
DisplayError(_("It is not White's turn"), 0);
return;
}
-
+
if (gameMode == AnalyzeMode || gameMode == AnalyzeFile)
ExitAnalyzeMode();
- if (gameMode == EditGame || gameMode == AnalyzeMode ||
+ if (gameMode == EditGame || gameMode == AnalyzeMode ||
gameMode == AnalyzeFile)
TruncateGame();
if(bookHit) { // [HGM] book: simulate book reply
static char bookMove[MSG_SIZ]; // a bit generous?
- programStats.nodes = programStats.depth = programStats.time =
+ programStats.nodes = programStats.depth = programStats.time =
programStats.score = programStats.got_only_move = 0;
sprintf(programStats.movelist, "%s (xbook)", bookHit);
- strcpy(bookMove, "move ");
+ safeStrCpy(bookMove, "move ", sizeof(bookMove)/sizeof(bookMove[0]));
strcat(bookMove, bookHit);
HandleMachineMove(bookMove, &first);
}
return;
- if (gameMode == PlayFromGameFile ||
- gameMode == TwoMachinesPlay ||
- gameMode == Training ||
- gameMode == AnalyzeMode ||
+ if (gameMode == PlayFromGameFile ||
+ gameMode == TwoMachinesPlay ||
+ gameMode == Training ||
+ gameMode == AnalyzeMode ||
gameMode == EndOfGame)
EditGameEvent();
- if (gameMode == EditPosition)
+ if (gameMode == EditPosition)
EditPositionDone(TRUE);
if (WhiteOnMove(currentMove)) {
DisplayError(_("It is not Black's turn"), 0);
return;
}
-
+
if (gameMode == AnalyzeMode || gameMode == AnalyzeFile)
ExitAnalyzeMode();
- if (gameMode == EditGame || gameMode == AnalyzeMode ||
+ if (gameMode == EditGame || gameMode == AnalyzeMode ||
gameMode == AnalyzeFile)
TruncateGame();
if(bookHit) { // [HGM] book: simulate book reply
static char bookMove[MSG_SIZ]; // a bit generous?
- programStats.nodes = programStats.depth = programStats.time =
+ programStats.nodes = programStats.depth = programStats.time =
programStats.score = programStats.got_only_move = 0;
sprintf(programStats.movelist, "%s (xbook)", bookHit);
- strcpy(bookMove, "move ");
+ safeStrCpy(bookMove, "move ", sizeof(bookMove)/sizeof(bookMove[0]));
strcat(bookMove, bookHit);
HandleMachineMove(bookMove, &first);
}
char buf[MSG_SIZ];
ChessProgramState *onmove;
char *bookHit = NULL;
-
+
if (appData.noChessProgram) return;
switch (gameMode) {
if(bookHit) { // [HGM] book: simulate book reply
static char bookMove[MSG_SIZ]; // a bit generous?
- programStats.nodes = programStats.depth = programStats.time =
+ programStats.nodes = programStats.depth = programStats.time =
programStats.score = programStats.got_only_move = 0;
sprintf(programStats.movelist, "%s (xbook)", bookHit);
- strcpy(bookMove, "move ");
+ safeStrCpy(bookMove, "move ", sizeof(bookMove)/sizeof(bookMove[0]));
strcat(bookMove, bookHit);
savedMessage = bookMove; // args for deferred call
savedState = onmove;
case AnalyzeFile:
ExitAnalyzeMode();
break;
-
+
default:
EditGameEvent();
break;
default:
return;
}
-
+
pausing = FALSE;
StopClocks();
first.offeredDraw = second.offeredDraw = 0;
whiteFlag = blackFlag = 0;
}
DisplayTitle("");
- }
-
+ }
+
gameMode = EditGame;
ModeHighlight();
SetGameInfo();
EditGameEvent();
return;
}
-
+
EditGameEvent();
if (gameMode != EditGame) return;
-
+
gameMode = EditPosition;
ModeHighlight();
SetGameInfo();
if (currentMove > 0)
CopyBoard(boards[0], boards[currentMove]);
-
+
blackPlaysFirst = !WhiteOnMove(currentMove);
ResetClocks();
currentMove = forwardMostMove = backwardMostMove = 0;
}
SendToProgram("force\n", &first);
if (blackPlaysFirst) {
- strcpy(moveList[0], "");
- strcpy(parseList[0], "");
+ safeStrCpy(moveList[0], "", sizeof(moveList[0])/sizeof(moveList[0][0]));
+ safeStrCpy(parseList[0], "", sizeof(parseList[0])/sizeof(parseList[0][0]));
currentMove = forwardMostMove = backwardMostMove = 1;
CopyBoard(boards[1], boards[0]);
} else {
len = strlen(buf);
if (len > MSG_SIZ)
len = MSG_SIZ;
-
+
strncpy(temp, buf, len);
temp[len] = 0;
piece > (int)BlackMan && piece <= (int)BlackKing ) {
selection = (ChessSquare) (DEMOTED piece);
} else if(piece == EmptySquare) selection = BlackSilver;
- else selection = (ChessSquare)((int)piece + 1);
+ else selection = (ChessSquare)((int)piece + 1);
goto defaultlabel;
case WhiteQueen:
AcceptEvent()
{
/* Accept a pending offer of any kind from opponent */
-
+
if (appData.icsActive) {
SendToICS(ics_prefix);
SendToICS("accept\n");
DeclineEvent()
{
/* Decline a pending offer of any kind from opponent */
-
+
if (appData.icsActive) {
SendToICS(ics_prefix);
SendToICS("decline\n");
DrawEvent()
{
/* Offer draw or accept pending draw offer from opponent */
-
+
if (appData.icsActive) {
/* Note: tournament rules require draw offers to be
made after you make your move but before you punch
your clock. Currently ICS doesn't let you do that;
instead, you immediately punch your clock after making
a move, but you can offer a draw at any time. */
-
+
SendToICS(ics_prefix);
SendToICS("draw\n");
userOfferedDraw = TRUE; // [HGM] drawclaim: also set flag in ICS play
AdjournEvent()
{
/* Offer Adjourn or accept pending Adjourn offer from opponent */
-
+
if (appData.icsActive) {
SendToICS(ics_prefix);
SendToICS("adjourn\n");
AbortEvent()
{
/* Offer Abort or accept pending Abort offer from opponent */
-
+
if (appData.icsActive) {
SendToICS(ics_prefix);
SendToICS("abort\n");
ResignEvent()
{
/* Resign. You can do this even if it's not your turn. */
-
+
if (appData.icsActive) {
SendToICS(ics_prefix);
SendToICS("resign\n");
if (gameMode == PlayFromGameFile && !pausing)
PauseEvent();
-
+
if (gameMode == IcsExamining && pausing)
limit = pauseExamForwardMostMove;
else
limit = forwardMostMove;
-
+
if (target > limit) target = limit;
if (target > 0 && moveList[target - 1][0]) {
}
}
}
- if (gameMode == EditGame || gameMode == AnalyzeMode ||
- gameMode == Training || gameMode == PlayFromGameFile ||
+ if (gameMode == EditGame || gameMode == AnalyzeMode ||
+ gameMode == Training || gameMode == PlayFromGameFile ||
gameMode == AnalyzeFile) {
while (currentMove < target) {
SendMoveToProgram(currentMove++, &first);
} else {
currentMove = target;
}
-
+
if (gameMode == EditGame || gameMode == EndOfGame) {
whiteTimeRemaining = timeRemaining[0][currentMove];
blackTimeRemaining = timeRemaining[1][currentMove];
/* to optimze, we temporarily turn off analysis mode while we feed
* the remaining moves to the engine. Otherwise we get analysis output
* after each move.
- */
+ */
if (first.analysisSupport) {
SendToProgram("exit\nforce\n", &first);
first.analyzing = FALSE;
}
}
-
+
if (gameMode == IcsExamining && !pausing) {
SendToICS(ics_prefix);
SendToICS("forward 999999\n");
}
if (gameMode == PlayFromGameFile && !pausing)
PauseEvent();
-
+
if (moveList[target][0]) {
int fromX, fromY, toX, toY;
toX = moveList[target][2] - AAA;
} else {
currentMove = target;
}
-
+
if (gameMode == EditGame || gameMode == EndOfGame) {
whiteTimeRemaining = timeRemaining[0][currentMove];
blackTimeRemaining = timeRemaining[1][currentMove];
if (gameMode == AnalyzeMode || gameMode == AnalyzeFile) {
/* to optimize, we temporarily turn off analysis mode while we undo
* all the moves. Otherwise we get analysis output after each undo.
- */
+ */
if (first.analysisSupport) {
SendToProgram("exit\nforce\n", &first);
first.analyzing = FALSE;
int move;
{
int i, j;
-
+
for (i = BOARD_HEIGHT - 1; i >= 0; i--) {
for (j = BOARD_LEFT; j < BOARD_RGHT; j++) {
char c = PieceToChar(boards[move][i][j]);
{
char buf[MSG_SIZ];
if (!appData.clockMode) {
- strcpy(buf, "-");
+ safeStrCpy(buf, "-", sizeof(buf)/sizeof(buf[0]));
} else if (movesPerSession > 0) {
- sprintf(buf, "%d/%ld", movesPerSession, timeControl/1000);
+ sprintf(buf, "%d/%ld", movesPerSession, timeControl/1000);
} else if (timeIncrement == 0) {
- sprintf(buf, "%ld", timeControl/1000);
+ sprintf(buf, "%ld", timeControl/1000);
} else {
- sprintf(buf, "%ld+%ld", timeControl/1000, timeIncrement/1000);
+ sprintf(buf, "%ld+%ld", timeControl/1000, timeIncrement/1000);
}
return StrSave(buf);
}
char *p = NULL;
if(gameMode == EditGame) { // [HGM] vari: do not erase result on EditGame
- r = gameInfo.result;
- p = gameInfo.resultDetails;
+ r = gameInfo.result;
+ p = gameInfo.resultDetails;
gameInfo.resultDetails = NULL;
}
ClearGameInfo(&gameInfo);
strncpy(commentList[index], text, len);
commentList[index][len] = '\n';
commentList[index][len + 1] = NULLCHAR;
- } else {
+ } else {
// [HGM] braces: if text does not start with known OK delimiter, put braces around it.
char *p;
- commentList[index] = (char *) malloc(len + 6);
- strcpy(commentList[index], "{\n");
- strncpy(commentList[index]+2, text, len);
+ commentList[index] = (char *) malloc(len + 7);
+ safeStrCpy(commentList[index], "{\n", 3);
+ safeStrCpy(commentList[index]+2, text, len+1);
commentList[index][len+2] = NULLCHAR;
while(p = strchr(commentList[index], '}')) *p = ')'; // kill all } to make it one comment
strcat(commentList[index], "\n}\n");
while(commentList[index][oldlen-1] == '\n')
commentList[index][--oldlen] = NULLCHAR;
commentList[index] = (char *) malloc(oldlen + len + 6); // might waste 4
- strcpy(commentList[index], old);
+ safeStrCpy(commentList[index], old, oldlen);
free(old);
// [HGM] braces: join "{A\n}\n" + "{\nB}" as "{A\nB\n}"
if(commentList[index][oldlen-1] == '}' && (text[0] == '{' || addBraces)) {
} else {
commentList[index] = (char *) malloc(len + 6); // perhaps wastes 4...
if(addBraces)
- strcpy(commentList[index], "{\n");
+ safeStrCpy(commentList[index], "{\n", sizeof(commentList[index])/sizeof(commentList[index][0]));
else commentList[index][0] = NULLCHAR;
strcat(commentList[index], text);
strcat(commentList[index], "\n");
if (cps->pr == NULL) return;
Attention(cps);
-
+
if (appData.debugMode) {
TimeMark now;
GetTimeMark(&now);
- fprintf(debugFP, "%ld >%-6s: %s",
+ fprintf(debugFP, "%ld >%-6s: %s",
SubtractTimeMarks(&now, &programStartTime),
cps->which, message);
}
-
+
count = strlen(message);
outCount = OutputToProcess(cps->pr, message, count, &error);
- if (outCount < count && !exiting
+ if (outCount < count && !exiting
&& !endingGame) { /* [HGM] crash: to not hang GameEnds() writing to deceased engines */
sprintf(buf, _("Error writing to %s chess program"), cps->which);
if(gameInfo.resultDetails==NULL) { /* [HGM] crash: if game in progress, give reason for abort */
}
return;
}
-
+
if ((end_str = strchr(message, '\r')) != NULL)
*end_str = NULLCHAR;
if ((end_str = strchr(message, '\n')) != NULL)
*end_str = NULLCHAR;
-
+
if (appData.debugMode) {
TimeMark now; int print = 1;
char *quote = ""; char c; int i;
if(appData.engineComments != 1) { /* [HGM] debug: decide if protocol-violating output is written */
char start = message[0];
if(start >='A' && start <= 'Z') start += 'a' - 'A'; // be tolerant to capitalizing
- if(sscanf(message, "%d%c%d%d%d", &i, &c, &i, &i, &i) != 5 &&
+ if(sscanf(message, "%d%c%d%d%d", &i, &c, &i, &i, &i) != 5 &&
sscanf(message, "move %c", &c)!=1 && sscanf(message, "offer%c", &c)!=1 &&
sscanf(message, "resign%c", &c)!=1 && sscanf(message, "feature %c", &c)!=1 &&
sscanf(message, "error %c", &c)!=1 && sscanf(message, "illegal %c", &c)!=1 &&
}
if(print) {
GetTimeMark(&now);
- fprintf(debugFP, "%ld <%-6s: %s%s\n",
- SubtractTimeMarks(&now, &programStartTime), cps->which,
+ fprintf(debugFP, "%ld <%-6s: %s%s\n",
+ SubtractTimeMarks(&now, &programStartTime), cps->which,
quote,
message);
}
/* [DM] if icsEngineAnalyze is active we block all whisper and kibitz output, because nobody want to see this */
if (appData.icsEngineAnalyze) {
if (strstr(message, "whisper") != NULL ||
- strstr(message, "kibitz") != NULL ||
+ strstr(message, "kibitz") != NULL ||
strstr(message, "tellics") != NULL) return;
}
ChessProgramState *WhitePlayer()
/* [HGM] return pointer to 'first' or 'second', depending on who plays white */
{
- if(gameMode == TwoMachinesPlay && first.twoMachinesColor[0] == 'b' ||
+ if(gameMode == TwoMachinesPlay && first.twoMachinesColor[0] == 'b' ||
gameMode == BeginningOfGame || gameMode == MachinePlaysBlack)
return &second;
return &first;
if (time <= 0) time = 1;
if (otime <= 0) otime = 1;
-
+
sprintf(message, "time %ld\n", time);
SendToProgram(message, cps);
return FALSE;
}
-int
+int
ParseOption(Option *opt, ChessProgramState *cps)
// [HGM] options: process the string that defines an engine option, and determine
// name, type, default value, and allowed value range
void
ParseFeatures(args, cps)
char* args;
- ChessProgramState *cps;
+ ChessProgramState *cps;
{
char *p = args;
char *q;
if (*p == NULLCHAR) return;
if (BoolFeature(&p, "setboard", &cps->useSetboard, cps)) continue;
- if (BoolFeature(&p, "time", &cps->sendTime, cps)) continue;
- if (BoolFeature(&p, "draw", &cps->sendDrawOffers, cps)) continue;
- if (BoolFeature(&p, "sigint", &cps->useSigint, cps)) continue;
- if (BoolFeature(&p, "sigterm", &cps->useSigterm, cps)) continue;
+ if (BoolFeature(&p, "time", &cps->sendTime, cps)) continue;
+ if (BoolFeature(&p, "draw", &cps->sendDrawOffers, cps)) continue;
+ if (BoolFeature(&p, "sigint", &cps->useSigint, cps)) continue;
+ if (BoolFeature(&p, "sigterm", &cps->useSigterm, cps)) continue;
if (BoolFeature(&p, "reuse", &val, cps)) {
/* Engine can disable reuse, but can't enable it if user said no */
if (!val) cps->reuse = FALSE;
int newState = appData.showThinking
// [HGM] thinking: other features now need thinking output as well
|| !appData.hideThinkingFromHuman || appData.adjudicateLossThreshold != 0 || EngineOutputIsUp();
-
+
if (oldState == newState) return;
oldState = newState;
if (gameMode == EditPosition) EditPositionDone(TRUE);
char cpThinkOutput[MSG_SIZ];
if(appData.noGUI) return; // [HGM] fast: suppress display of moves
-
- if (moveNumber == forwardMostMove - 1 ||
+
+ if (moveNumber == forwardMostMove - 1 ||
gameMode == AnalyzeMode || gameMode == AnalyzeFile) {
- safeStrCpy(cpThinkOutput, thinkOutput, sizeof(cpThinkOutput));
+ safeStrCpy(cpThinkOutput, thinkOutput, sizeof(cpThinkOutput)/sizeof(cpThinkOutput[0]));
if (strchr(cpThinkOutput, '\n')) {
*strchr(cpThinkOutput, '\n') = NULLCHAR;
char title[MSG_SIZ];
char buf[8000]; // comment can be long!
int score, depth;
-
+
if (moveNumber < 0 || parseList[moveNumber][0] == NULLCHAR) {
- strcpy(title, "Comment");
+ safeStrCpy(title, "Comment", sizeof(title)/sizeof(title[0]));
} else {
sprintf(title, "Comment on %d.%s%s", moveNumber / 2 + 1,
WhiteOnMove(moveNumber) ? " " : ".. ",
}
// [HGM] PV info: display PV info together with (or as) comment
if(moveNumber >= 0 && (depth = pvInfoList[moveNumber].depth) > 0) {
- if(text == NULL) text = "";
+ if(text == NULL) text = "";
score = pvInfoList[moveNumber].score;
sprintf(buf, "%s%.2f/%d %d\n%s", score>0 ? "+" : "", score/100.,
depth, (pvInfoList[moveNumber].time+50)/100, text);
struct timezone timeZone;
gettimeofday(&timeVal, &timeZone);
- tm->sec = (long) timeVal.tv_sec;
+ tm->sec = (long) timeVal.tv_sec;
tm->ms = (int) (timeVal.tv_usec / 1000L);
#else /*!HAVE_GETTIMEOFDAY*/
* We give the human user a slight advantage if he is playing white---the
* clocks don't run until he makes his first move, so it takes zero time.
* Also, we don't account for network lag, so we could get out of sync
- * with GNU Chess's clock -- but then, referees are always right.
+ * with GNU Chess's clock -- but then, referees are always right.
*/
static TimeMark tickStartTM;
/* Stop clocks and reset to a fresh time control */
void
-ResetClocks()
+ResetClocks()
{
(void) StopClockTimer();
if (appData.icsActive) {
if (!appData.clockMode) return;
if (gameMode==AnalyzeMode || gameMode == AnalyzeFile) return;
-
+
GetTimeMark(&now);
lastTickLength = SubtractTimeMarks(&now, &tickStartTM);
!WhiteOnMove(currentMove < forwardMostMove ? currentMove : forwardMostMove));
}
if (CheckFlags()) return;
-
+
tickStartTM = now;
intendedTickLength = NextTickLength(timeRemaining - fudge) + fudge;
StartClockTimer(intendedTickLength);
/* if the time remaining has fallen below the alarm threshold, sound the
* alarm. if the alarm has sounded and (due to a takeback or time control
* with increment) the time remaining has increased to a level above the
- * threshold, reset the alarm so it can sound again.
+ * threshold, reset the alarm so it can sound again.
*/
-
+
if (appData.icsActive && appData.icsAlarm) {
/* make sure we are dealing with the user's clock */
if (alarmSounded && (timeRemaining > appData.icsAlarmTime)) {
alarmSounded = FALSE;
- } else if (!alarmSounded && (timeRemaining <= appData.icsAlarmTime)) {
+ } else if (!alarmSounded && (timeRemaining <= appData.icsAlarmTime)) {
PlayAlarmSound();
alarmSounded = TRUE;
}
whiteTimeRemaining -= lastTickLength;
/* [HGM] PGNtime: save time for PGN file if engine did not give it */
// if(pvInfoList[forwardMostMove-1].time == -1)
- pvInfoList[forwardMostMove-1].time =
+ pvInfoList[forwardMostMove-1].time =
(timeRemaining[0][forwardMostMove-1] - whiteTimeRemaining)/10;
}
flagged = CheckFlags();
whiteTimeRemaining : blackTimeRemaining);
StartClockTimer(intendedTickLength);
}
-
+
/* Stop both clocks */
void
StopClocks()
-{
+{
long lastTickLength;
TimeMark now;
}
CheckFlags();
}
-
+
/* Start clock of player on move. Time may have been reset, so
if clock is already running, stop and restart it. */
void
whiteTimeRemaining : blackTimeRemaining);
/* [HGM] nps: figure out nps factors, by determining which engine plays white and/or black once and for all */
- whiteNPS = blackNPS = -1;
+ whiteNPS = blackNPS = -1;
if(gameMode == MachinePlaysWhite || gameMode == TwoMachinesPlay && first.twoMachinesColor[0] == 'w'
|| appData.zippyPlay && gameMode == IcsPlayingBlack) // first (perhaps only) engine has white
whiteNPS = first.nps;
long second, minute, hour, day;
char *sign = "";
static char buf[32];
-
+
if (ms > 0 && ms <= 9900) {
/* convert milliseconds to tenths, rounding up */
double tenths = floor( ((double)(ms + 99L)) / 100.00 );
sign = "-";
second = -second;
}
-
+
day = second / (60 * 60 * 24);
second = second % (60 * 60 * 24);
hour = second / (60 * 60);
second = second % (60 * 60);
minute = second / 60;
second = second % 60;
-
+
if (day > 0)
sprintf(buf, " %s%ld:%02ld:%02ld:%02ld ",
sign, day, hour, minute, second);
sprintf(buf, " %s%ld:%02ld:%02ld ", sign, hour, minute, second);
else
sprintf(buf, " %s%2ld:%02ld ", sign, minute, second);
-
+
return buf;
}
char *string, *match;
{
int i, length;
-
+
length = strlen(match);
-
+
for (i = strlen(string) - length; i >= 0; i--, string++)
if (!strncmp(match, string, length))
return string;
-
+
return NULL;
}
char *string, *match;
{
int i, j, length;
-
+
length = strlen(match);
-
+
for (i = strlen(string) - length; i >= 0; i--, string++) {
for (j = 0; j < length; j++) {
if (ToLower(match[j]) != ToLower(string[j]))
char *s1, *s2;
{
char c1, c2;
-
+
for (;;) {
c1 = ToLower(*s1++);
c2 = ToLower(*s2++);
StrSave(s)
char *s;
{
- char *ret;
+ char *ret;
- if ((ret = (char *) malloc(strlen(s) + 1))) {
- strcpy(ret, s);
+ if ((ret = (char *) malloc(strlen(s) + 1)))
+ {
+ safeStrCpy(ret, s, strlen(s)+1);
}
- return ret;
+ return ret;
}
char *
free(*savePtr);
}
if ((*savePtr = (char *) malloc(strlen(s) + 1))) {
- strcpy(*savePtr, s);
+ safeStrCpy(*savePtr, s, strlen(s)+1);
}
return(*savePtr);
}
/* [HGM] write promoted pieces as '+<unpromoted>' (Shogi) */
*p++ = '+';
piece = (ChessSquare)(DEMOTED piece);
- }
+ }
*p++ = PieceToChar(piece);
if(p[-1] == '~') {
/* [HGM] flag promoted pieces as '<promoted>~' (Crazyhouse) */
}
if(gameInfo.variant != VariantShogi && gameInfo.variant != VariantXiangqi &&
- gameInfo.variant != VariantShatranj && gameInfo.variant != VariantCourier && gameInfo.variant != VariantMakruk ) {
+ gameInfo.variant != VariantShatranj && gameInfo.variant != VariantCourier && gameInfo.variant != VariantMakruk ) {
/* En passant target square */
if (move > backwardMostMove) {
fromX = moveList[move - 1][0] - AAA;
}
/* Fullmove number */
sprintf(p, "%d", (move / 2) + 1);
-
+
return StrSave(buf);
}
case 'w':
*blackPlaysFirst = FALSE;
break;
- case 'b':
+ case 'b':
*blackPlaysFirst = TRUE;
break;
default:
/* read e.p. field in games that know e.p. capture */
if(gameInfo.variant != VariantShogi && gameInfo.variant != VariantXiangqi &&
- gameInfo.variant != VariantShatranj && gameInfo.variant != VariantCourier && gameInfo.variant != VariantMakruk ) {
+ gameInfo.variant != VariantShatranj && gameInfo.variant != VariantCourier && gameInfo.variant != VariantMakruk ) {
if(*p=='-') {
p++; board[EP_STATUS] = EP_NONE;
} else {
return TRUE;
}
-
+
void
EditPositionPasteFEN(char *fen)
{
len = strlen(new_seq);
ret = (len > 0) && (len < sizeof(cseq));
if (ret)
- strcpy(cseq, new_seq);
+ safeStrCpy(cseq, new_seq, sizeof(cseq)/sizeof(cseq[0]));
else if (appData.debugMode)
- fprintf(debugFP, "Invalid continuation sequence \"%s\" (maximum length is: %u)\n", new_seq, (unsigned) sizeof(cseq)-1);
+ fprintf(debugFP, "Invalid continuation sequence \"%s\" (maximum length is: %u)\n", new_seq, (unsigned) sizeof(cseq)-1);
return ret;
}
// [HGM] vari: routines for shelving variations
-void
+void
PushTail(int firstMove, int lastMove)
{
int i, j, nrMoves = lastMove - firstMove;
if(annotate) {
int cnt = 10;
if(!WhiteOnMove(currentMove)) sprintf(buf, "(%d...", currentMove+2>>1);
- else strcpy(buf, "(");
+ else safeStrCpy(buf, "(", sizeof(buf)/sizeof(buf[0]));
for(i=currentMove; i<forwardMostMove; i++) {
if(WhiteOnMove(i))
sprintf(moveBuf, " %d. %s", i+2>>1, SavePart(parseList[i]));
return TRUE;
}
-void
+void
CleanupTail()
{ // remove all shelved variations
int i;