v13i058: xboard, Part02/06

dbs at Pa.dec.com dbs at Pa.dec.com
Mon Jun 24 23:40:28 AEST 1991


Submitted-by: dbs at Pa.dec.com
Posting-number: Volume 13, Issue 58
Archive-name: xboard/part02

---- Cut Here and feed the following to sh ----
#!/bin/sh
# this is xx.02 (part 2 of a multipart archive)
# do not concatenate these parts, unpack them in order with /bin/sh
# file xboard/xboard.c continued
#
if test ! -r _shar_seq_.tmp; then
	echo 'Please unpack part 1 first!'
	exit 1
fi
(read Scheck
 if test "$Scheck" != 2; then
	echo Please unpack part "$Scheck" next!
	exit 1
 else
	exit 0
 fi
) < _shar_seq_.tmp || exit 1
if test ! -f _shar_wnt_.tmp; then
	echo 'x - still skipping xboard/xboard.c'
else
echo 'x - continuing file xboard/xboard.c'
sed 's/^X//' << 'SHAR_EOF' >> 'xboard/xboard.c' &&
X		boards[currentMove][to_y][to_x] = WhitePawn;
X		boards[currentMove][to_y - 1][to_x] = EmptySquare;
X		DrawSquare(from_y, from_x, boards[currentMove][from_y][from_x]);
X		DrawSquare(to_y, to_x, boards[currentMove][to_y][to_x]);
X		DrawSquare(to_y - 1, to_x, boards[currentMove][to_y - 1][to_x]);
X		if (gameMode == PlayFromGameFile)
X			sprintf(message, "%d. %s", move, yytext);
X		else
X			sprintf(message, "%d. %c%c ep", move, from_x + 'a', to_x + 'a');
X	} else if (from_y == 7 && from_x == 4		/* black king-side castle */
X			&& boards[currentMove][from_y][from_x] == BlackKing
X			&& to_y == 7 && to_x == 6) {
X		*move_type = BlackKingSideCastle;
X		boards[currentMove][7][4] = EmptySquare;
X		boards[currentMove][7][5] = BlackRook;
X		boards[currentMove][7][6] = BlackKing;
X		boards[currentMove][7][7] = EmptySquare;
X		DrawSquare(7, 7, boards[currentMove][7][7]);
X		DrawSquare(7, 6, boards[currentMove][7][6]);
X		DrawSquare(7, 5, boards[currentMove][7][5]);
X		DrawSquare(7, 4, boards[currentMove][7][4]);
X		if (gameMode == PlayFromGameFile)
X			sprintf(message, "%d. ... %s", move, yytext);
X		else
X			sprintf(message, "%d. ... 0-0", move);
X	} else if (from_y == 7 && from_x == 4		/* black queen-side castle */
X			&& boards[currentMove][from_y][from_x] == BlackKing
X			&& to_y == 7 && to_x == 2) {
X		*move_type = BlackQueenSideCastle;
X		boards[currentMove][7][0] = EmptySquare;
X		boards[currentMove][7][2] = BlackKing;
X		boards[currentMove][7][3] = BlackRook;
X		boards[currentMove][7][4] = EmptySquare;
X		DrawSquare(7, 0, boards[currentMove][7][0]);
X		DrawSquare(7, 2, boards[currentMove][7][2]);
X		DrawSquare(7, 3, boards[currentMove][7][3]);
X		DrawSquare(7, 4, boards[currentMove][7][4]);
X		if (gameMode == PlayFromGameFile)
X			sprintf(message, "%d. ... %s", move, yytext);
X		else
X			sprintf(message, "%d. ... 0-0-0", move);
X	} else if (from_y == 1						/* black pawn promotion */
X			&& boards[currentMove][from_y][from_x] == BlackPawn && to_y == 0) {
X		*move_type = BlackPromotionQueen;		/* TODO: gnuchess limitation */
X		boards[currentMove][1][from_x] = EmptySquare;
X		boards[currentMove][0][to_x] = BlackQueen;
X		DrawSquare(1, from_x, boards[currentMove][1][from_x]);
X		DrawSquare(0, to_x, boards[currentMove][0][to_x]);
X		if (gameMode == PlayFromGameFile)
X			sprintf(message, "%d. ... %s", move, yytext);
X		else
X			sprintf(message, "%d. ... %c8(Q)", move, from_x + 'a');
X	} else if ((from_y == 3)					/* black captures en passant */
X			&& (to_x != from_x)
X			&& (boards[currentMove][from_y][from_x] == BlackPawn)
X			&& (boards[currentMove][to_y][to_x] == EmptySquare)) {
X		*move_type = BlackCapturesEnPassant;
X		boards[currentMove][from_y][from_x] = EmptySquare;
X		boards[currentMove][to_y][to_x] = BlackPawn;
X		boards[currentMove][to_y + 1][to_x] = EmptySquare;
X		DrawSquare(from_y, from_x, boards[currentMove][from_y][from_x]);
X		DrawSquare(to_y, to_x, boards[currentMove][to_y][to_x]);
X		DrawSquare(to_y + 1, to_x, boards[currentMove][to_y + 1][to_x]);
X		if (gameMode == PlayFromGameFile)
X			sprintf(message, "%d. ... %s", move, yytext);
X		else
X			sprintf(message, "%d. ... %c%c ep", move, from_x + 'a', to_x + 'a');
X	} else {
X		*move_type = NormalMove;
X		boards[currentMove][to_y][to_x] = boards[currentMove][from_y][from_x];
X		boards[currentMove][from_y][from_x] = EmptySquare;
X		DrawSquare(to_y, to_x, boards[currentMove][to_y][to_x]);
X		DrawSquare(from_y, from_x, boards[currentMove][from_y][from_x]);
X		if (gameMode == PlayFromGameFile)
X			sprintf(message, "%d. %s%s", move,
X				WHITE_ON_MOVE ? "... " : "", yytext);
X		else
X			sprintf(message, "%d. %s%c%c%c%c", move, WHITE_ON_MOVE ? "... "
X				: "", from_x + 'a', from_y + '1', to_x + 'a', to_y + '1');
X	}
X
X	DisplayMessage(message);
X	strcpy(parseList[currentMove - 1], message);
X	XSync(xDisplay, False);
}
X
void
InitChessProgram(host_name, program_name, pid, to, from, xid)
X	char *host_name, *program_name;
X	int *pid;
X	FILE **to, **from;
X	XtIntervalId *xid;
{
X	char time_control[10], moves_per_session[10], time_search[10];
X	int to_prog[2], from_prog[2];
X	FILE *from_fp, *to_fp;
X
#if	SYSTEM_FIVE || SYSV
X	if ((ttyname = PseudoTTY(&to_prog[1])) == NULL) {
X		perror(program_name);
X		exit(1);
X	}
X
X	from_prog[0] = to_prog[1];
X	to_prog[0] = from_prog[1] = open(ttyname, O_RDWR, 0);
#else
X	signal(SIGPIPE, CatchPipeSignal);
X	pipe(to_prog);
X	pipe(from_prog);
#endif
X
X	if ((*pid = fork()) == 0) {
#if	!SYSTEM_FIVE && !SYSV
X		signal(SIGPIPE, CatchPipeSignal);
#ifdef	O_NDELAY
X		fcntl(from_prog[0], F_SETFL, O_NDELAY);
#endif
#endif
X		dup2(to_prog[0], 0);
X		dup2(from_prog[1], 1);
X		close(to_prog[0]);
X		close(to_prog[1]);
X		close(from_prog[0]);
X		close(from_prog[1]);
X		dup2(1, fileno(stderr));	/* force stderr to the pipe */
X		sprintf(time_control, "%d", appData.timeControl);
X		sprintf(time_search, "%d", appData.searchTime);
X		sprintf(moves_per_session, "%d", appData.movesPerSession);
X		if (strcmp(host_name, "localhost") == 0) {
X			if (appData.searchTime <= 0)
X				execlp(program_name, program_name,
X					moves_per_session, time_control, (char *) NULL);
X			else
X				execlp(program_name, program_name, time_search, (char *) NULL);
X		} else {
X			if (appData.searchTime <= 0)
X				execlp(appData.remoteShell, appData.remoteShell,
X					host_name, program_name, moves_per_session,
X					time_control, (char *) NULL);
X			else
X				execlp(appData.remoteShell, appData.remoteShell,
X					host_name, program_name, time_search, (char *) NULL);
X		}
X
X		perror(program_name);
X		exit(1);
X	}
X
X	close(to_prog[0]);
X	close(from_prog[1]);
X
X	*from = from_fp = fdopen(from_prog[0], "r");
X	*to = to_fp = fdopen(to_prog[1], "w");
X	setbuf(from_fp, NULL); setbuf(to_fp, NULL);
X
X	*xid = XtAppAddInput(appContext, fileno(from_fp), XtInputReadMask,
X		ReceiveFromProgram, from_fp);
X
X	SendToProgram(appData.initString, to_fp);
}
X
void
ShutdownChessPrograms(message)
X	char *message;
{
X	lastGameMode = gameMode;
X	gameMode = EndOfGame;
X	DisplayMessage(message);
X
X	if (firstProgramPID != 0) {
X		fclose(fromFirstProgFP);
X		fclose(toFirstProgFP);
X		fromFirstProgFP = toFirstProgFP = NULL;
X		kill(firstProgramPID, SIGTERM);
X	}
X
X	if (secondProgramPID != 0) {
X		fclose(fromSecondProgFP);
X		fclose(toSecondProgFP);
X		fromSecondProgFP = toSecondProgFP = NULL;
X		kill(secondProgramPID, SIGTERM);
X	}
X
X	if (firstProgramXID != NULL)
X		XtRemoveInput(firstProgramXID);
X	if (secondProgramXID != NULL)
X		XtRemoveInput(secondProgramXID);
X	if (readGameXID != NULL)
X		XtRemoveTimeOut(readGameXID);
X
X	firstProgramXID = secondProgramXID = readGameXID = NULL;
X	firstProgramPID = secondProgramPID = 0;
X
X	DisplayClocks(StopTimers);
}
X
void
CommentPopUp(label)
X	char *label;
{
X	Arg args[2];
X	Position x, y;
X	Dimension bw_width, pw_width;
X
X	if (commentUp) {
X		XtPopdown(commentShell);
X		XtDestroyWidget(commentShell);
X		commentUp = False;
X	}
X
X	DisplayMessage("Comment");
X
X	XtSetArg(args[0], XtNwidth, &bw_width);
X	XtGetValues(boardWidget, args, 1);
X
X	XtSetArg(args[0], XtNresizable, True);
X	XtSetArg(args[1], XtNwidth, bw_width);
X
X	commentShell = XtCreatePopupShell("Comment",
X		transientShellWidgetClass, commandsWidget, args, 2);
X
X	XtSetArg(args[0], XtNlabel, label);
X
X	(void) XtCreateManagedWidget("commentLabel", labelWidgetClass,
X		commentShell, args, 1);
X
X	XtRealizeWidget(commentShell);
X
X	XtSetArg(args[0], XtNwidth, &pw_width);
X	XtGetValues(commentShell, args, 1);
X
X	XtTranslateCoords(shellWidget, (bw_width - pw_width) / 2, -50, &x, &y);
X
X	XtSetArg(args[0], XtNx, x);
X	XtSetArg(args[1], XtNy, y);
X	XtSetValues(commentShell, args, 2);
X
X	XtPopup(commentShell, XtGrabNone);
X	commentUp = True;
}
X
void
FileNamePopUp(label, proc)
X	char *label;
X	void (*proc) P((char *name));
{
X	Arg args[2];
X	Widget popup, dialog;
X	Position x, y;
X	Dimension bw_width, pw_width;
X
X	fileProc = (XtCallbackProc) proc;
X
X	XtSetArg(args[0], XtNwidth, &bw_width);
X	XtGetValues(boardWidget, args, 1);
X
X	XtSetArg(args[0], XtNresizable, True);
X	XtSetArg(args[1], XtNwidth, DIALOG_SIZE);
X
X	popup = XtCreatePopupShell("File Name Prompt",
X		transientShellWidgetClass, commandsWidget, args, 2);
X
X	XtSetArg(args[0], XtNlabel, label);
X	XtSetArg(args[1], XtNvalue, "");
X
X	dialog = XtCreateManagedWidget("dialog", dialogWidgetClass,
X		popup, args, 2);
X
X	XawDialogAddButton(dialog, "ok", FileNameCallback, (XtPointer) dialog);
X	XawDialogAddButton(dialog, "cancel", FileNameCallback, (XtPointer) dialog);
X
X	XtRealizeWidget(popup);
X
X	XtSetArg(args[0], XtNwidth, &pw_width);
X	XtGetValues(popup, args, 1);
X
X	XtTranslateCoords(boardWidget, (bw_width - pw_width) / 2, 10, &x, &y);
X
X	XtSetArg(args[0], XtNx, x);
X	XtSetArg(args[1], XtNy, y);
X	XtSetValues(popup, args, 2);
X
X	XtPopup(popup, XtGrabExclusive);
X
X	XtSetKeyboardFocus(shellWidget, popup);
}
X
void
FileNameCallback(w, client_data, call_data)
X	Widget w;
X	XtPointer client_data, call_data;
{
X	String name;
X	Arg args[1];
X
X	XtSetArg(args[0], XtNlabel, &name);
X	XtGetValues(w, args, 1);
X
X	if (strcmp(name, "cancel") == 0) {
X		XtPopdown(w = XtParent(XtParent(w)));
X		XtDestroyWidget(w);
X		return;
X	}
X
X	FileNameAction(w, NULL);
}
X
void
FileNameAction(w, event)
X	Widget w;
X	XEvent *event;
{
X	char buf[MSG_SIZ];
X	String name;
X
X	name = XawDialogGetValueString(w = XtParent(w));
X
X	if ((name != NULL) && (*name != '\0')) {
X		strcpy(buf, name);
X		XtPopdown(w = XtParent(w));
X		XtDestroyWidget(w);
X		(*fileProc)(buf);	/* I can't see a way not to use a global here */
X		return;
X	}
X
X	XtPopdown(w = XtParent(w));
X	XtDestroyWidget(w);
}
X
void
SelectCommand(w, client_data, call_data)
X	Widget w;
X	XtPointer client_data, call_data;
{
X	XawListReturnStruct *list_return = XawListShowCurrent(w);
X
X	fromX = fromY = -1;
X
X	if ((gameMode == PauseGame)
X		&& (list_return->list_index != (int) ButtonPause))
X		PauseProc();
X
X	switch ((Button) list_return->list_index) {
X	case ButtonQuit:
X		QuitProc();
X		break;
X	case ButtonBackward:
X		BackwardProc();
X		break;
X	case ButtonForward:
X		ForwardProc();
X		break;
X	case ButtonFlip:
X		FlipProc();
X		break;
X	case ButtonReset:
X		ResetFileProc();
X		ResetProc();
X		break;
X	case ButtonSaveGame:
X		if (appData.saveGameFile[0] == '\0')
X			FileNamePopUp("Filename for saved game?", SaveGameProc);
X		else
X			SaveGameProc(appData.saveGameFile);
X		break;
X	case ButtonSavePosition:
X		if (appData.savePositionFile[0] == '\0')
X			FileNamePopUp("Filename for saved position?", SavePositionProc);
X		else
X			SaveGameProc(appData.savePositionFile);
X		break;
X	case ButtonHint:
X		HintProc();
X		break;
X	case ButtonSwitch:
X		SwitchProc();
X		break;
X	case ButtonSetupFromFile:
X		if (gameMode != BeginningOfGame)
X			break;
X		if (appData.readPositionFile == NULL)
X			FileNamePopUp("Position file name?",
X				VOID_PROC SetupPositionFromFileProc);
X		else
X			(void) SetupPositionFromFileProc(appData.readPositionFile);
X		break;
X	case ButtonPlayFromFile:
X		GameProc();
X		break;
X	case ButtonMachinePlaysBlack:
X		MachinePlaysBlackProc();
X		break;
X	case ButtonMachinePlaysWhite:
X		MachinePlaysWhiteProc();
X		break;
X	case ButtonTwoMachinesPlay:
X		TwoMachinesPlayProc();
X		break;
X	case ButtonForce:
X		ForceProc();
X		break;
X	case ButtonPause:
X		PauseProc();
X		break;
X	}
X
X	XawListUnhighlight(w);
}
X
/*
X * Button procedures
X */
void
QuitProc()
{
X	ShutdownChessPrograms("Quitting");
X	exit(0);
}
X
int
PlayFromGameFileProc(name)
X	char *name;
{
X	char buf[MSG_SIZ], error_buf[MSG_SIZ];
X	Arg args[1];
X
X	if (gameMode != BeginningOfGame)
X		return (int) False;
X
X	if (appData.readGameFile != name) {
X		if (appData.readGameFile)
X			XtFree(appData.readGameFile);
X		appData.readGameFile = XtMalloc(strlen(name));
X		strcpy(appData.readGameFile, name);
X	}
X
X	if (name[0] == '/')
X		strcpy(buf, name);
X	else {
X		strcpy(buf, chessDir);
X		strcat(buf, "/");
X		strcat(buf, name);
X	}
X
X	if ((gameFileFP = fopen(buf, "r")) == NULL) {
X		strcpy(error_buf, buf);
X		sprintf(buf, "Can't open %s", error_buf);
X		DisplayMessage(buf);
X		return (int) False;
X	}
X
X	lastGameMode = gameMode;
X	gameMode = PlayFromGameFile;
X	InitPosition();
X	DisplayClocks(StopTimers);
X	if (firstProgramXID == NULL)
X		InitChessProgram(appData.firstHost, appData.firstChessProgram,
X			&firstProgramPID, &toFirstProgFP, &fromFirstProgFP,
X			&firstProgramXID);
X	SendToProgram(appData.initString, toFirstProgFP);
X	SendToProgram("force\n", toFirstProgFP);
X
X	/*
X	 * If the file doesn't immediately start with what looks like a game ...
X	 */
X	if (fgetc(gameFileFP) != '1') {
X		fseek(gameFileFP, 0, 0);
X		fgets(buf, MSG_SIZ, gameFileFP);
X		buf[strlen(buf) - 1] = '\0';
X		XtSetArg(args[0], XtNlabel, buf);
X		XtSetValues(nameWidget, args, 1);
X	} else
X		fseek(gameFileFP, 0, 0);
X
X	for (;;)
X		if ((ChessMove) yylex() == StartGame)
X			break;
X
X	ReadGameFile();
X
X	return (int) True;
}
X
void
MachinePlaysBlackProc()
{
X	if ((gameMode == EndOfGame) || (gameMode == PlayFromGameFile)
X		|| (matchMode != MatchFalse) || WHITE_ON_MOVE)
X		return;
X
X	undoMode = False;
X	lastGameMode = gameMode = MachinePlaysBlack;
X	SendToProgram(appData.blackString, toFirstProgFP);
}
X
void
ForwardProc()
{
X	char buf[MSG_SIZ];
X	int i, j;
X
X	if (gameMode == BeginningOfGame) {
X		if (currentMove != 0)
X			return;
X		if (appData.readGameFile != NULL) {
X			if (PlayFromGameFileProc(appData.readGameFile)) {
X				XtRemoveTimeOut(readGameXID);
X				readGameXID = NULL;
X			}
X		}
X		return;
X	}
X
X	if ((gameMode == EndOfGame) || (matchMode != MatchFalse)
X		|| ((currentMove == 0) && (forwardMostMove == 0)))
X		return;
X
X	if (gameMode != PauseGame) {
X		PauseProc();
X		if (readGameXID != NULL) {
X			XtRemoveTimeOut(readGameXID);
X			readGameXID = NULL;
X		}
X	}
X
X	if (currentMove >= forwardMostMove) {
X		ReadGameFileProc();
X		if ((strcmp(parseList[currentMove], "1-0") == 0)
X			|| (strcmp(parseList[currentMove], "0-1") == 0)
X			|| (strcmp(parseList[currentMove], "1/2") == 0)
X			|| (strcmp(parseList[currentMove], "End Of Game") == 0))
X			DisplayMessage(parseList[currentMove]);
X		return;
X	}
X
X	if ((forwardForce == False) && (gameMode != PlayFromGameFile)) {
X		forwardForce = True;
X		SendToProgram("force\n", toFirstProgFP);
X	}
X
X	for (i = 0; i < BOARD_SIZE; i++)
X		for (j = 0; j < BOARD_SIZE; j++)
X			if (boards[currentMove + 1][i][j] != boards[currentMove][i][j])
X				DrawSquare(i, j, boards[currentMove + 1][i][j]);
X
X	DisplayMessage(parseList[currentMove]);
X	strcpy(buf, moveList[currentMove++]);
X	SendToProgram(buf, toFirstProgFP);
}
X
void
ResetFileProc()
{
X	Arg args[1];
X	char *buf = "";
X
X	if (appData.readGameFile);
X		XtFree(appData.readGameFile);
X	if (appData.readPositionFile);
X		XtFree(appData.readPositionFile);
X	appData.readGameFile = appData.readPositionFile = NULL;
X	XtSetArg(args[0], XtNlabel, buf);
X	XtSetValues(nameWidget, args, 1);
X	if (gameFileFP != NULL) {
X		fclose(gameFileFP);
X		gameFileFP = NULL;
X	}
}
X
void
ResetProc()
{
X	twoProgramState = flipView = forwardForce = False;
X	matchMode = MatchFalse;
X	firstMove = True;
X
X	ShutdownChessPrograms("");
X	lastGameMode = gameMode = BeginningOfGame;
X	InitPosition();
X	InitChessProgram(appData.firstHost, appData.firstChessProgram,
X		&firstProgramPID, &toFirstProgFP, &fromFirstProgFP, &firstProgramXID);
X	DisplayClocks(ResetTimers);
}
X
int
SetupPositionFromFileProc(name)
X	char *name;
{
X	char *p, line[MSG_SIZ], buf[MSG_SIZ];
X	Board initial_position;
X	Arg args[1];
X	FILE *fp;
X	int i, j;
X
X	if (gameMode != BeginningOfGame)
X		return (int) False;
X
X	if (appData.readPositionFile != name) {
X		if (appData.readPositionFile)
X			XtFree(appData.readPositionFile);
X		appData.readPositionFile = XtMalloc(strlen(name));
X		strcpy(appData.readPositionFile, name);
X	}
X
X	if (name[0] == '/')
X		strcpy(buf, name);
X	else {
X		strcpy(buf, chessDir);
X		strcat(buf, "/");
X		strcat(buf, name);
X	}
X
X	if ((fp = fopen(buf, "r")) == NULL) {
X		strcpy(line, buf);
X		sprintf(buf, "Can't open %s", line);
X		DisplayMessage(buf);
X		return (int) False;
X	}
X
X	lastGameMode = gameMode = SetupPosition;
X
X	if (firstProgramXID == NULL)
X		InitChessProgram(appData.firstHost, appData.firstChessProgram,
X			&firstProgramPID, &toFirstProgFP, &fromFirstProgFP,
X			&firstProgramXID);
X
X	/*
X	 * skip header information in position file
X	 */
X	fgets(line, MSG_SIZ, fp);
X	line[strlen(line) - 1] = '\0';
X	XtSetArg(args[0], XtNlabel, line);
X	XtSetValues(nameWidget, args, 1);
X	fgets(line, MSG_SIZ, fp);
X	fgets(line, MSG_SIZ, fp);
X
X	for (i = BOARD_SIZE - 1; i >= 0; i--) {
X		fgets(line, MSG_SIZ, fp);
X		for (p = line, j = 0; j < BOARD_SIZE; p++) {
X			if (*p == ' ')
X				continue;
X			initial_position[i][j++] = CharToPiece(*p);
X		}
X	}
X	fclose(fp);
X
X	currentMove = forwardMostMove = 0;
X	CopyBoard(boards[0], initial_position);
X	SendCurrentBoard(toFirstProgFP);
X	DrawPosition(boardWidget, (XExposeEvent *) NULL);
X
X	return (int) True;
}
X
void
MachinePlaysWhiteProc()
{
X	if ((gameMode == EndOfGame) || (gameMode == PlayFromGameFile)
X		|| (matchMode != MatchFalse) || !WHITE_ON_MOVE)
X		return;
X
X	undoMode = False;
X	lastGameMode = gameMode = MachinePlaysWhite;
X	SendToProgram(appData.whiteString, toFirstProgFP);
}
X
void
BackwardProc()
{
X	int i, j;
X
X	if ((currentMove <= 0) || (matchMode != MatchFalse)
X		|| (gameMode == EndOfGame))
X		return;
X
X	if (currentMove == 1) {
X		ResetProc();
X		return;
X	}
X
X	if (gameMode == BeginningOfGame)
X		gameMode = lastGameMode;
X	else
X		SendToProgram("undo\n", toFirstProgFP);
X
X	if (gameMode != PauseGame) {
X		PauseProc();
X		if (readGameXID != NULL) {
X			XtRemoveTimeOut(readGameXID);
X			readGameXID = NULL;
X		}
X	}
X
X	undoMode = True;
X	currentMove--;
X	DisplayMessage(parseList[currentMove - 1]);
X
X	for (i = 0; i < BOARD_SIZE; i++)
X		for (j = 0; j < BOARD_SIZE; j++)
X			if (boards[currentMove][i][j] != boards[currentMove + 1][i][j])
X				DrawSquare(i, j, boards[currentMove][i][j]);
}
X
void
FlipProc()
{
X	flipView = !flipView;
X	DrawPosition(boardWidget, (XExposeEvent *) NULL);
}
X
void
SaveGameProc(name)
X	char *name;
{
X	char buf[MSG_SIZ], white_move[MSG_SIZ], black_move[MSG_SIZ];
X	int i, len, move = 0;
X	time_t tm;
X
X	if ((gameFileFP = fopen(name, "w")) == NULL) {
X		sprintf(buf, "Can't open %s", name);
X		DisplayMessage(buf);
X		return;
X	}
X
X	tm = time((time_t *) NULL);
X	gethostname(buf, MSG_SIZ);
X
X	fprintf(gameFileFP, "%s game file -- %s", programName, ctime(&tm));
X	switch (lastGameMode) {
X	case MachinePlaysWhite:
X		fprintf(gameFileFP, "\t%s@%s vs. %s@%s\n", appData.firstChessProgram,
X			appData.firstHost, getpwuid(getuid())->pw_name, buf);
X		break;
X	case MachinePlaysBlack:
X		fprintf(gameFileFP, "\t%s@%s vs. %s@%s\n", getpwuid(getuid())->pw_name,
X			buf, appData.firstChessProgram, appData.firstHost);
X		break;
X	case TwoMachinesPlay:
X		fprintf(gameFileFP, "\t%s@%s vs. %s@%s\n",
X			appData.secondChessProgram, appData.secondHost,
X			appData.firstChessProgram, appData.firstHost);
X		break;
X	default:
X		fprintf(gameFileFP, "\n");
X		break;
X	}
X	fprintf(gameFileFP, "\talgebraic\n");
X
X	for (i = 0; i < currentMove;) {
X		/*
X		 * get rid of '\n' added to send the move to GNU Chess
X		 */
X		len = strlen(moveList[i]);
X		strcpy(white_move, moveList[i++]);
X		if (white_move[len - 1] == '\n')
X			white_move[len - 1] = NULL;
X		fprintf(gameFileFP, "%d. %s ", ++move, white_move);
X
X		if (i >= currentMove) {
X			fprintf(gameFileFP, "\n");
X			break;
X		}
X
X		if ((len = strlen(moveList[i])) == 0) {
X			fprintf(gameFileFP, "\n");
X			break;
X		}
X		strcpy(black_move, moveList[i++]);
X		if (black_move[len - 1] == '\n')
X			black_move[len - 1] = NULL;
X		fprintf(gameFileFP, "%s\n", black_move);
X	}
X
X	fclose(gameFileFP);
X	gameFileFP = NULL;
}
X
void
SwitchProc()
{
X	switch (gameMode) {
X	default:
X		return;
X	case MachinePlaysWhite:
X		lastGameMode = gameMode = MachinePlaysBlack;
X		break;
X	case BeginningOfGame:
X	case MachinePlaysBlack:
X		if (currentMove == 0) {
X			MachinePlaysWhiteProc();
X			return;
X		}
X		lastGameMode = gameMode = MachinePlaysWhite;
X		break;
X	}
X
X	SendToProgram("switch\n", toFirstProgFP);
}
X
void
ForceProc()
{
X	if ((gameMode == EndOfGame) || (gameMode == PlayFromGameFile))
X		return;
X
X	switch (gameMode) {
X	case MachinePlaysWhite:
X		if (WHITE_ON_MOVE && !undoMode) {
X			DisplayMessage("Wait until your move");
X			return;
X		}
X		break;
X	case MachinePlaysBlack:
X		if (!WHITE_ON_MOVE && !undoMode) {
X			DisplayMessage("Wait until your move");
X			return;
X		}
X	case BeginningOfGame:
X		break;
X	default:
X		return;
X	}
X
X	lastGameMode = gameMode = ForceMoves;
X	DisplayClocks(StopTimers);
X	SendToProgram("force\n", toFirstProgFP);
}
X
void
HintProc()
{
X	switch (gameMode) {
X	case MachinePlaysWhite:
X	case MachinePlaysBlack:
X	case BeginningOfGame:
X		SendToProgram("hint\n", toFirstProgFP);
X	default:
X		return;
X	}
}
X
void
SavePositionProc(name)
X	char *name;
{
X	char buf[MSG_SIZ], host_name[MSG_SIZ];
X	FILE *fp;
X	time_t tm;
X	int i, j;
X
X	if ((fp = fopen(name, "w")) == NULL) {
X		sprintf(buf, "Can't open %s", name);
X		DisplayMessage(buf);
X		return;
X	}
X
X	tm = time((time_t *) NULL);
X	gethostname(host_name, MSG_SIZ);
X
X	fprintf(fp, "%s position file -- %s", programName, ctime(&tm));
X	switch (gameMode) {
X	case MachinePlaysWhite:
X		fprintf(fp, "\t%s@%s vs. %s@%s\n", appData.firstChessProgram,
X			appData.firstHost, getpwuid(getuid())->pw_name, host_name);
X		break;
X	case MachinePlaysBlack:
X		fprintf(fp, "\t%s@%s vs. %s@%s\n", getpwuid(getuid())->pw_name,
X			host_name, appData.firstChessProgram, appData.firstHost);
X		break;
X	case TwoMachinesPlay:
X		fprintf(fp, "\t%s@%s vs. %s@%s\n", appData.secondChessProgram,
X			appData.secondHost, appData.firstChessProgram, appData.firstHost);
X		break;
X	default:
X		fprintf(fp, "\n");
X		break;
X	}
X	fprintf(fp, "\n");
X
X	for (i = BOARD_SIZE - 1; i >= 0; i--) {
X		for (j = 0; j < BOARD_SIZE; j++) {
X			fprintf(fp, "%c", pieceToChar[(int) boards[currentMove][i][j]]);
X			fputc(j == BOARD_SIZE - 1 ? '\n' : ' ', fp);
X		}
X	}
X
X	fclose(fp);
}
X
void
TwoMachinesPlayProc()
{
X	int i;
X
X	if ((gameMode == EndOfGame) || (twoProgramState == True))
X		return;
X
X	if (!WHITE_ON_MOVE) {
X		DisplayMessage("White must be on move");
X		return;
X	}
X
X	twoProgramState = True;
X
X	if (matchMode == MatchFalse) {
X		switch (gameMode) {
X		case MachinePlaysWhite:
X		case MachinePlaysBlack:
X		case PauseGame:
X		case TwoMachinesPlay:
X		case PlayFromGameFile:
X			return;
X		case ForceMoves:
X			matchMode = MatchOpening;
X			break;
X		case SetupPosition:
X			matchMode = MatchPosition;
X			break;
X		case BeginningOfGame:
X		default:
X			matchMode = MatchInit;
X			break;
X		}
X	}
X
X	flipView = forwardForce = False;
X	firstMove = False;
X	DisplayClocks(ResetTimers);
X	DisplayClocks(ReStartTimers);
X
X	switch (matchMode) {
X	case MatchOpening:
X		if (firstProgramXID == NULL) {
X			if (appData.readGameFile == NULL) {
X				DisplayMessage("Select game file first");
X				return;
X			}
X			InitChessProgram(appData.firstHost, appData.firstChessProgram,
X				&firstProgramPID, &toFirstProgFP, &fromFirstProgFP,
X				&firstProgramXID);
X			if (!PlayFromGameFileProc(appData.readGameFile)) {
X				ShutdownChessPrograms("Bad game file");
X				return;
X			}
X			DrawPosition(boardWidget, (XExposeEvent *) NULL);
X		}
X		InitChessProgram(appData.secondHost, appData.secondChessProgram,
X			&secondProgramPID, &toSecondProgFP, &fromSecondProgFP,
X			&secondProgramXID);
X		SendToProgram("force\n", toSecondProgFP);
X		for (i = 0; i < currentMove; i++)
X			SendToProgram(moveList[i], toSecondProgFP);
X		lastGameMode = gameMode = TwoMachinesPlay;
X		firstMove = True;
X		SendToProgram(appData.whiteString, toSecondProgFP);
X		break;
X	case MatchPosition:
X		if (firstProgramXID == NULL) {
X			if (appData.readPositionFile == NULL) {
X				DisplayMessage("Select position file first");
X				return;
X			}
X			InitChessProgram(appData.firstHost, appData.firstChessProgram,
X				&firstProgramPID, &toFirstProgFP, &fromFirstProgFP,
X				&firstProgramXID);
X			if (!SetupPositionFromFileProc(appData.readPositionFile))
X				return;
X		}
X		InitChessProgram(appData.secondHost, appData.secondChessProgram,
X			&secondProgramPID, &toSecondProgFP, &fromSecondProgFP,
X			&secondProgramXID);
X		SendCurrentBoard(toSecondProgFP);
X		lastGameMode = gameMode = TwoMachinesPlay;
X		firstMove = True;
X		SendToProgram(appData.whiteString, toSecondProgFP);
X		break;
X	case MatchInit:
X		InitPosition();
X		if (firstProgramXID == NULL)
X			InitChessProgram(appData.firstHost, appData.firstChessProgram,
X				&firstProgramPID, &toFirstProgFP, &fromFirstProgFP,
X				&firstProgramXID);
X		InitChessProgram(appData.secondHost, appData.secondChessProgram,
X			&secondProgramPID, &toSecondProgFP, &fromSecondProgFP,
X			&secondProgramXID);
X		lastGameMode = gameMode = TwoMachinesPlay;
X		SendToProgram(appData.whiteString, toSecondProgFP);
X	default:
X		break;
X	}
}
X
void
PauseProc()
{
X	static GameMode previous_mode = PauseGame;
X
X	switch (gameMode) {
X	case ForceMoves:
X	case EndOfGame:
X		return;
X	case PauseGame:
X		gameMode = previous_mode;
X		previous_mode = PauseGame;
X		DisplayClocks(ReStartTimers);
X		DisplayMessage("");
X		break;
X	case PlayFromGameFile:
X		if (readGameXID == NULL)
X			readGameXID = XtAppAddTimeOut(appContext,
X				(int) (1000 * appData.timeDelay), ReadGameFile, NULL);
X		else {
X			XtRemoveTimeOut(readGameXID);
X			readGameXID = NULL;
X		}
X		DisplayMessage("Pausing");
X		break;
X	case BeginningOfGame:		/* play game from files end here at the end */
X	case MachinePlaysWhite:
X	case MachinePlaysBlack:
X	case TwoMachinesPlay:
X	case SetupPosition:
X		if (currentMove == 0)	/* don't pause if no one has moved */
X			return;
X		previous_mode = gameMode;
X		gameMode = PauseGame;
X		DisplayClocks(StopTimers);
X		DisplayMessage("Pausing");
X		break;
X	}
}
X
void
GameProc()
{
X	if (gameMode != BeginningOfGame)
X		return;
X	if (appData.readGameFile == NULL)
X		FileNamePopUp("Game file name?", VOID_PROC PlayFromGameFileProc);
X	else
X		(void) PlayFromGameFileProc(appData.readGameFile);
}
X
void
Iconify()
{
X	Arg args[1];
X
X	fromX = fromY = -1;
X
X	XtSetArg(args[0], XtNiconic, True);
X	XtSetValues(shellWidget, args, 1);
}
X
void
SendToProgram(message, fp)
X	char *message;
X	FILE *fp;
{
X	if (xboardDebug)
X		fprintf(stderr, "Sending to %s: %s",
X			fp == toFirstProgFP ? "first" : "second", message);
X	fputs(message, fp);
}
X
void
ReceiveFromProgram(fp)
X	FILE *fp;
{
X	char message[MSG_SIZ], *end_str;
X
X	if (fgets(message, MSG_SIZ, fp) == NULL)
X		return;
X
X	if ((end_str = (char *) strchr(message, '\r')) != NULL)
X		*end_str = '\0';
X	if ((end_str = (char *) strchr(message, '\n')) != NULL)
X		*end_str = '\0';
X
X	if (xboardDebug)
X		fprintf(stderr, "Received from %s: %s\n",
X			fp == fromFirstProgFP ? "first" : "second", message);
X	HandleMachineMove(message);
}
X
void
DisplayMessage(message)
X	char *message;
{
X	Arg arg;
X
X	XtSetArg(arg, XtNlabel, message);
X	XtSetValues(messageWidget, &arg, 1);
}
X
/*
X * DisplayClocks manages the game clocks.
X *
X * In tournament play, black starts the clock and then white makes a move.
X * DisplayClocks starts black's clock when white makes the first move.
X * Also, DisplayClocks doesn't account for network lag so it could get
X * out of sync with GNU Chess's clock -- but then, referees are always right.
X */
void
DisplayClocks(clock_mode)
X	int clock_mode;
{
X	switch (clock_mode) {
X	case ResetTimers:
X		if (timerXID != NULL) {
X			XtRemoveTimeOut(timerXID);
X			timerXID = NULL;
X		}
X
X		whiteTimeRemaining = appData.timeControl * 60;
X		DisplayTimerLabel(whiteTimerWidget, "White", whiteTimeRemaining);
X
X		blackTimeRemaining = appData.timeControl * 60;
X		DisplayTimerLabel(blackTimerWidget, "Black", blackTimeRemaining);
X		break;
X	case DisplayTimers:
X		if (gameMode == PauseGame)
X			return;
X		if (appData.clockMode) {
X			if (WHITE_ON_MOVE) {
X				if ((currentMove > 0) || (gameMode == TwoMachinesPlay))
X					whiteTimeRemaining--;
X				if (whiteTimeRemaining <= 0) {
X					whiteTimeRemaining = 0;
X					DisplayMessage("White's flag dropped");
X				}
X			} else {
X				blackTimeRemaining--;
X				if (blackTimeRemaining <= 0) {
X					blackTimeRemaining = 0;
X					DisplayMessage("Black's flag dropped");
X				}
X			}
X		}
X
X		DisplayTimerLabel(whiteTimerWidget, "White", whiteTimeRemaining);
X		DisplayTimerLabel(blackTimerWidget, "Black", blackTimeRemaining);
X
X		/*
X		 * reset clocks when time control is acheived
X		 */
X		if (appData.clockMode && (currentMove != 0)
X			&& ((currentMove % (appData.movesPerSession * 2)) == 0)
X			&& (whiteTimeRemaining > 0) && (blackTimeRemaining > 0)) {
X			whiteTimeRemaining = appData.timeControl * 60;
X			blackTimeRemaining = appData.timeControl * 60;
X		}
X
X		if (timerXID != NULL) {
X			XtRemoveTimeOut(timerXID);
X			timerXID = NULL;
X		}
X		if (appData.clockMode)
X			timerXID = XtAppAddTimeOut(appContext,
X				1000, DisplayClocks, DisplayTimers);
X		break;
X	case StopTimers:
X		if (timerXID == NULL)
X			return;
X		XtRemoveTimeOut(timerXID);
X		timerXID = NULL;
X		break;
X	case ReStartTimers:
X		if (timerXID != NULL)
X			return;
X
X		DisplayTimerLabel(whiteTimerWidget, "White", whiteTimeRemaining);
X		DisplayTimerLabel(blackTimerWidget, "Black", blackTimeRemaining);
X
X		if (appData.clockMode)
X			timerXID = XtAppAddTimeOut(appContext,
X				1000, DisplayClocks, DisplayTimers);
X		break;
X	}
}
X
void
DisplayTimerLabel(w, color, timer)
X	Widget w;
X	char *color;
X	time_t timer;
{
X	char buf[MSG_SIZ];
X	Arg args[3];
X
X	if (appData.clockMode) {
X		sprintf(buf, "%s: %s", color, TimeString(timer));
X		XtSetArg(args[0], XtNlabel, buf);
X	} else
X		XtSetArg(args[0], XtNlabel, color);
X
X	if (((color[0] == 'B') && WHITE_ON_MOVE)
X		|| ((color[0] == 'W') && !WHITE_ON_MOVE)) {
X		XtSetArg(args[1], XtNbackground, timerForegroundPixel);
X		XtSetArg(args[2], XtNforeground, timerBackgroundPixel);
X	} else {
X		XtSetArg(args[1], XtNbackground, timerBackgroundPixel);
X		XtSetArg(args[2], XtNforeground, timerForegroundPixel);
X	}
X
X	XtSetValues(w, args, 3);
}
X
char *
TimeString(tm)
X	time_t tm;
{
X	int second, minute, hour, day;
X	static char buf[32];
X
X	if (tm >= (60 * 60 * 24)) {
X		day = (int) (tm / (60 * 60 * 24));
X		tm -= day * 60 * 60 * 24;
X	} else
X		day = 0;
X
X	if (tm >= (60 * 60)) {
X		hour = (int) (tm / (60 * 60));
X		tm -= hour * 60 * 60;
X	} else
X		hour = 0;
X
X	if (tm >= 60) {
X		minute = (int) (tm / 60);
X		tm -= minute * 60;
X	} else
X		minute = 0;
X
X	second = tm % 60;
X
X	if (day > 0)
X		sprintf(buf, " %d:%02d:%02d:%02d ", day, hour, minute, second);
X	else if (hour > 0)
X		sprintf(buf, " %d:%02d:%02d ", hour, minute, second);
X	else
X		sprintf(buf, " %2d:%02d ", minute, second);
X
X	return buf;
}
X
void
Usage()
{
X	fprintf(stderr, "Usage %s:\n", programName);
X	fprintf(stderr, "\tstandard Xt options\n");
X	fprintf(stderr, "\t-wpc or -whitePieceColor color\n");
X	fprintf(stderr, "\t-bpc or -blackPieceColor color\n");
X	fprintf(stderr, "\t-lsc or -lightSquareColor color\n");
X	fprintf(stderr, "\t-dsc or -darkSquareColor color\n");
X	fprintf(stderr, "\t-mps or -movesPerSession moves\n");
X	fprintf(stderr, "\t-fcp or -firstChessProgram program_name\n");
X	fprintf(stderr, "\t-scp or -secondChessProgram program_name\n");
X	fprintf(stderr, "\t-fh or -firstHost host_name\n");
X	fprintf(stderr, "\t-sh or -secondHost host_name\n");
X	fprintf(stderr, "\t-spb or -solidPawnBitmap file_name\n");
X	fprintf(stderr, "\t-srb or -solidRookBitmap file_name\n");
X	fprintf(stderr, "\t-sbb or -solidBishopBitmap file_name\n");
X	fprintf(stderr, "\t-skb or -solidKnightBitmap file_name\n");
X	fprintf(stderr, "\t-sqb or -solidQueenBitmap file_name\n");
X	fprintf(stderr, "\t-skb or -solidKingBitmap file_name\n");
X	fprintf(stderr, "\t-opb or -outlinePawnBitmap file_name\n");
X	fprintf(stderr, "\t-orb or -outlineRookBitmap file_name\n");
X	fprintf(stderr, "\t-obb or -outlineBishopBitmap file_name\n");
X	fprintf(stderr, "\t-okb or -outlineKnightBitmap file_name\n");
X	fprintf(stderr, "\t-oqb or -outlineQueenBitmap file_name\n");
X	fprintf(stderr, "\t-okb or -outlineKingBitmap file_name\n");
X	fprintf(stderr, "\t-rsh or -remoteShell shell_name\n");
X	fprintf(stderr, "\t-td or -timeDelay seconds\n");
X	fprintf(stderr, "\t-tc or -timeControl minutes\n");
X	fprintf(stderr, "\t-rgf or -readGameFile file_name\n");
X	fprintf(stderr, "\t-rpf or -readPositionFile file_name\n");
X	fprintf(stderr, "\t-sgf or -saveGameFile file_name\n");
X	fprintf(stderr, "\t-spf or -savePositionFile file_name\n");
X	fprintf(stderr, "\t-mm or -matchMode (False | Init | Position | Opening)\n");
X	fprintf(stderr, "\t-mono or -monoMode (True | False)\n");
X	fprintf(stderr, "\t-debug or -debugMode (True | False)\n");
X	fprintf(stderr, "\t-clock or -clockMode (True | False)\n");
X	fprintf(stderr, "\t-big or -bigSizeMode (True | False)\n");
X	fprintf(stderr, "\t-st or -searchTime seconds\n");
X
X	exit(0);
}
X
/*
X * This is necessary because some C libraries aren't ANSI C compliant yet.
X */
char *
StrStr(string, match)
X	char *string, *match;
{
X	int i, length;
X
X	length = strlen(match);
X
X	for (i = strlen(string) - length; i >= 0; i--, string++)
X		if (!strncmp(match, string, (size_t) length))
X			return string;
X
X	return NULL;
}
X
#if	SYSTEM_FIVE || SYSV
char *
PseudoTTY(ptyv)
X	int *ptyv;
{
X	struct stat stb;
X	int c, i;
X
X	for (c = 'p'; c <= 'z'; c++)
X		for (i = 0; i < 16; i++) {
#ifdef	HPUX
X			sprintf(ptyname, "/dev/ptym/pty%c%x", c, i);
#else
#ifdef	RTU
X			sprintf(ptyname, "/dev/pty%x", i);
#else
X			sprintf(ptyname, "/dev/pty%c%x", c, i);
#endif
#endif
X
#ifdef	IRIS
X			*ptyv = open("/dev/ptc", O_RDWR | O_NDELAY, 0);
X			if (*ptyv < 0)
X				return NULL;
X			if (fstat(*ptyv, &stb) < 0)
X				return NULL;
#else
X			if (stat(ptyname, &stb) < 0)
X				return NULL;
X			*ptyv = open(ptyname, O_RDWR | O_NDELAY, 0);
#endif
X
X			if (*ptyv >= 0) {
#ifdef	HPUX
X				sprintf(ptyname, "/dev/pty/tty%c%x", c, i);
#else
#ifdef	RTU
X				sprintf(ptyname, "/dev/ttyp%x", i);
#else
#ifdef	IRIS
X				sprintf(ptyname, "/dev/ttyq%d", minor(stb.st_rdev));
#else
X				sprintf(ptyname, "/dev/tty%c%x", c, i);
#endif
#endif
#endif
X
#ifndef	UNIPLUS
X				if (access(ptyname, 6) != 0) {
X					close(*ptyv);
#ifdef	IRIS
X					return NULL;
#else
X					continue;
#endif
X				}
#endif
X
#ifdef	FIONBIO
X			{
X				int on = 1;
X				ioctl(*ptyv, FIONBIO, &on);
X			}
#endif
X
#ifdef	IBMRTAIX
X			signal(SIGHUP, SIG_IGN);
#endif
X			return ptyname;
X		}
X	}
X
X	return NULL;
}
X
#else
X
void
CatchPipeSignal()
{
X	/*
X	 * If a game is just being played out and there is no reason for
X	 * gnuchessr to be used, so ignore pipe signals.  This allows people
X	 * to use xboard as a chess board without need for gnuchess.
X	 */
X	switch (gameMode) {
X	case ForceMoves:
X	case PlayFromGameFile:
X	case SetupPosition:
X	case BeginningOfGame:
X		break;
X	default:
X		fprintf(stderr, "Caught pipe signal\n");
X		exit(0);
X	}
}
#endif
SHAR_EOF
echo 'File xboard/xboard.c is complete' &&
chmod 0644 xboard/xboard.c ||
echo 'restore of xboard/xboard.c failed'
Wc_c="`wc -c < 'xboard/xboard.c'`"
test 80472 -eq "$Wc_c" ||
	echo 'xboard/xboard.c: original size 80472, current size' "$Wc_c"
rm -f _shar_wnt_.tmp
fi
# ============= xboard/xboard.h ==============
if test -f 'xboard/xboard.h' -a X"$1" != X"-c"; then
	echo 'x - skipping xboard/xboard.h (File already exists)'
	rm -f _shar_wnt_.tmp
else
> _shar_wnt_.tmp
echo 'x - extracting xboard/xboard.h (Text)'
sed 's/^X//' << 'SHAR_EOF' > 'xboard/xboard.h' &&
/*
X * XBoard -- an Xt/Athena user interface for GNU Chess
X *
X * Dan Sears
X * Chris Sears
X *
X * Copyright 1991 by Digital Equipment Corporation, Maynard, Massachusetts.
X *
X * All Rights Reserved
X *
X * Permission to use, copy, modify, and distribute this software and its
X * documentation for any purpose and without fee is hereby granted,
X * provided that the above copyright notice appear in all copies and that
X * both that copyright notice and this permission notice appear in
X * supporting documentation, and that the name of Digital not be
X * used in advertising or publicity pertaining to distribution of the
X * software without specific, written prior permission.
X *
X * DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
X * ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
X * DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
X * ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
X * WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
X * ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
X * SOFTWARE.
X */
#define BOARD_SIZE				8				/* rarely changed */
#define BIG_SQUARE_SIZE			80
#define SMALL_SQUARE_SIZE		64
#define LINE_GAP				3
#define MAX_MOVES				512
#define MSG_SIZ					256
#define DIALOG_SIZE				250
#define MOVE_LEN				8
#define TIME_CONTROL			5				/* in minutes */
#define TIME_DELAY				"1.0"			/* seconds between moves */
#define TIME_SEARCH				0				/* don't specify search time */
#define MOVES_PER_SESSION		40				/* moves per TIME_CONTROL */
#define WHITE_ON_MOVE			((int) ((currentMove % 2) == 0))
#define FIRST_CHESS_PROGRAM		"gnuchessr"
#define SECOND_CHESS_PROGRAM	"gnuchessr"
#define FIRST_HOST				"localhost"
#define SECOND_HOST				"localhost"
#define MATCH_MODE				"False"
#define INIT_STRING				"new\nbeep\nrandom\n"
#define WHITE_STRING			"white\ngo\n"
#define BLACK_STRING			"black\ngo\n"
#define WHITE_PIECE_COLOR		"#FFFFCC"
#define BLACK_PIECE_COLOR		"#202020"
#define LIGHT_SQUARE_COLOR		"#C8C365"
#define DARK_SQUARE_COLOR		"#77A26D"
X
typedef enum {
X	BeginningOfGame, MachinePlaysWhite, MachinePlaysBlack, TwoMachinesPlay,
X	ForceMoves, PlayFromGameFile, SetupPosition, PauseGame, EndOfGame
} GameMode;
X
typedef enum {
X	MatchFalse, MatchInit, MatchPosition, MatchOpening
} MatchMode;
X
typedef enum {
X	WhitePawn, WhiteRook, WhiteKnight, WhiteBishop, WhiteQueen, WhiteKing,
X	BlackPawn, BlackRook, BlackKnight, BlackBishop, BlackQueen, BlackKing,
X	EmptySquare
} ChessSquare;
X
typedef ChessSquare Board[BOARD_SIZE][BOARD_SIZE];
X
typedef enum {
X	WhiteKingSideCastle = 1, WhiteQueenSideCastle,
X	WhitePromotionKnight, WhitePromotionBishop,
X	WhitePromotionRook, WhitePromotionQueen,
X	BlackPromotionKnight, BlackPromotionBishop,
X	BlackPromotionRook, BlackPromotionQueen,
X	BlackKingSideCastle, BlackQueenSideCastle,
X	WhiteCapturesEnPassant, BlackCapturesEnPassant, NormalMove,
X	WhiteWins, BlackWins, GameIsDrawn, StartGame, BadMove, Comment
} ChessMove;
X
typedef enum {			/* Same order as buttonStrings */
X	ButtonQuit, ButtonPlayFromFile, ButtonMachinePlaysBlack, ButtonForward,
X	ButtonReset, ButtonSetupFromFile, ButtonMachinePlaysWhite, ButtonBackward,
X	ButtonFlip, ButtonSaveGame, ButtonSwitch, ButtonForce,
X	ButtonHint, ButtonSavePosition, ButtonTwoMachinesPlay, ButtonPause
} Button;
X
typedef enum {
X	ResetTimers, DisplayTimers, StopTimers, ReStartTimers
} ClockMode;
X
/*
X * Various compatibility grunge
X */
#ifdef __STDC__
#define	P(args)		args
#define VOID_PROC	(void(*)(char*))
#else
#define P(args)		()
#define VOID_PROC
#endif
SHAR_EOF
chmod 0644 xboard/xboard.h ||
echo 'restore of xboard/xboard.h failed'
Wc_c="`wc -c < 'xboard/xboard.h'`"
test 3583 -eq "$Wc_c" ||
	echo 'xboard/xboard.h: original size 3583, current size' "$Wc_c"
rm -f _shar_wnt_.tmp
fi
# ============= xboard/xboard.man ==============
if test -f 'xboard/xboard.man' -a X"$1" != X"-c"; then
	echo 'x - skipping xboard/xboard.man (File already exists)'
	rm -f _shar_wnt_.tmp
else
> _shar_wnt_.tmp
echo 'x - extracting xboard/xboard.man (Text)'
sed 's/^X//' << 'SHAR_EOF' > 'xboard/xboard.man' &&
..TH XBOARD 1 "June 11, 1991" "X Version 11"
..SH NAME
xboard \- Xt/Athena user interface for GNU Chess, version 1.2
..SH SYNOPSIS
..B xboard
[
..IR "\-wpc or -whitePieceColor color"
]
[
..IR "\-bpc or -blackPieceColor color"
]
[
..IR "\-lsc or -lightSquareColor color"
]
[
..IR "\-dsc or -darkSquareColor color"
]
[
..IR "\-mps or -movesPerSession moves"
]
[
..IR "\-fcp or -firstChessProgram program_name"
]
[
..IR "\-scp or -secondChessProgram program_name"
]
[
..IR "\-fh or -firstHost host_name"
]
[
..IR "\-sh or -secondHost host_name"
]
[
..IR "\-spb or -solidPawnBitmap file_name"
]
[
..IR "\-srb or -solidRookBitmap file_name"
]
[
..IR "\-sbb or -solidBishopBitmap file_name"
]
[
..IR "\-skb or -solidKnightBitmap file_name"
]
[
..IR "\-sqb or -solidQueenBitmap file_name"
]
[
..IR "\-skb or -solidKingBitmap file_name"
]
[
..IR "\-opb or -outlinePawnBitmap file_name"
]
[
..IR "\-orb or -outlineRookBitmap file_name"
]
[
..IR "\-obb or -outlineBishopBitmap file_name"
]
[
..IR "\-okb or -outlineKnightBitmap file_name"
]
[
..IR "\-oqb or -outlineQueenBitmap file_name"
]
[
..IR "\-okb or -outlineKingBitmap file_name"
]
[
..IR "\-rsh or -remoteShell shell_name"
]
[
..IR "\-td or -timeDelay seconds"
]
[
..IR "\-tc or -timeControl minutes"
]
[
..IR "\-rgf or -readGameFile file_name"
]
[
..IR "\-rpf or -readPositionFile file_name"
]
..IR "\-sgf or -saveGameFile file_name"
]
[
..IR "\-spf or -savePositionFile file_name"
]
[
..IR "\-mm or -matchMode (False | Init | Position | Opening)"
]
[
..IR "\-mono or -monoMode (True | False)"
]
[
..IR "\-debug or -debugMode (True | False)"
]
[
..IR "\-clock or -clockMode (True | False)"
]
[
..IR "\-big or -bigSizeMode (True | False)"
]
[
..IR "\-st or -searchTime seconds"
]
..SH DESCRIPTION
..IR xboard
provides an X11/Xt/Athena Widgets user interface for GNU Chess.
With
..IR xboard
you can play GNU Chess,
setup arbitrary positions,
force variations or watch
..IR xboard
manage a game between two chess programs.
..LP
..IR xboard
can also be used as a chessboard to play out games.
It will read through a game file or allow a player to play (force mode)
through a variation manually.
All of the keystroke commands (Backward, Forward, Reset, etc.) work.
A chess program doesn't even need to be present in the program search path
in this case.
This is useful for keeping track of email postal games or browsing games
off the net.
..LP
After starting
..IR xboard
you can make moves by pressing a mouse button
while the cursor is over a square with your piece on it
and dragging the mouse to another square.
If the move is illegal,
..IR gnuchess
will not allow it.
..IR xboard
will then retract the move.
..LP
Alternate bitmaps for piece icons can be specified
either by choosing one of two built-in sets or with
the file name resources described below.
There are two sets of piece bitmaps available:
a large set (the default) and a small set.
It is easiest to select the small set in the .Xdefaults file:
..sp 1
..br
XXBoard*bigSizeMode:	false
..LP
The font used for button labels and comments can be changed in the
..Xdefaults file:
..sp 1
..br
XXBoard*font:	helvetica_oblique14
..LP
If you are using a grayscale monitor, try setting the colors to:
..sp 1
..br
XXBoard*whitePieceColor:     gray100
..br
XXBoard*blackPieceColor:     gray0
..br
XXBoard*lightSquareColor:    gray60
..br
XXBoard*darkSquareColor:     gray40
..SH OPTIONS
The following command line options also correspond to X resources
that you can set in your
..IR \&.Xdefaults
file.
..TP 8
..B standard Xt options
..IR xboard
accepts standard Xt options like
..IR "\-display"
and
..IR "\-geometry" .
..TP 8
..B -wpc or -whitePieceColor color
Color specification for white pieces
suitable for
..IR XParseColor (3X11).
Default: #FFFFCC.
These colors look good on a DEC workstation.
If you need different colors, try using the
..IR xcolors
application.  Source for
..IR xcolors
can be found in the X11/R4 contrib directory.
..TP 8
..B -bpc or -blackPieceColor color
Same for black pieces.
Default: #202020.
..TP 8
..B -lsc or -lightSquareColor color
Same for light squares.
Default: #C8C365.
..TP 8
..B -dsc or -darkSquareColor color
Same for dark squares.
Default: #77A26D.
..TP 8
..B -td or -timeDelay seconds
Time delay between moves during "Play From File".
This doesn't have to be round numbers.
Try -td 0.4.  Default: 1 second.
..TP 8
..B -clock or -clockMode (True | False)
Determines whether or not to use the clock.
Some people aren't interested in having the chess clock be updated.
This allows it to be turned off.  The side that is on move is still
highlighted.
..TP 8
..B -big or -bigSizeMode (True | False)
Determines which set of bitmaps to use, a built-in 80x80 pixel set
or a built-in 64-64 set.
..TP 8
..B -st or -searchTime seconds
Call GNU Chess with only one argument.
Determines the program search time in seconds.
..TP 8
..B -tc or -timeControl minutes
Amount of time for a set of moves determined by
..IR movesPerSession .
If this number of moves is played within the time control period,
..IR xboard
resets the time clocks.
Default: 5 minutes.
..TP 8
..B -mps or -movesPerSession moves
Number of moves in a playing session.
Default: 40 moves.
..TP 8
..B -rgf or -readGameFile file
Name of file to read a game record from.
If the first line does not appear to start with a move,
that is if the first character of the file is not `1',
then the first line is assumed to be a title and is displayed.
Comments either start with [ and end with a matching ]
or they start with a ! and end with the next newline.
Game files are found in the directory named by the CHESSDIR environment
variable.  If this variable is not declared then the current directory is used
unless the file name starts with a /.
..TP 8
..B -rpf or -readPositionFile file
Name of file to read a game position from.
Position files are found in the directory named by the CHESSDIR environment
variable.  If this variable is not declared then the current directory is used
unless the file name starts with a /.
..TP 8
..B -sgf or -saveGameFile file
Name of file to save a game record to.
No default.
..TP 8
..B -spf or -savePositionFile file
Name of file to save a game position to.
No default.
..TP 8
..B -rsh or -remoteShell shell_name
Some systems do not use rsh as the remote shell.
This option allows a user to name the remote shell command.
This should be done in the resource file.
..TP 8
..B -fcp or -firstChessProgram program
Name of first chess program that,
by default,
plays black.
Default: "gnuchessr".
..TP 8
..B -scp or -secondChessProgram program
Name of second chess program that,
by default,
plays white.
Default: "gnuchessr".
..TP 8
..B -fh or -firstHost host
Name of host the white chess program plays on.
Default: "localhost".
..TP 8
..B -sh or -secondHost host
Name of host the black chess program plays on.
Default: "localhost".
..TP 8
..B -s*b or -solid*Bitmap file
Names of the bitmap files for the bitmap piece icons.
Default: solid_pawn.bitmap, solid_rook.bitmap ...
..TP 8
..B -o*b or -outline*Bitmap file
Names of the bitmap files for the outline piece icons.
Default: outline_pawn.bitmap, outline_rook.bitmap ...
..TP 8
..B -mm or -matchMode "(False | Init | Position | Opening)"
Automatically run a game between
..IR firstChessProgram
and
..IR secondChessProgram .
If
..IR matchMode
is set to
..IR Init ,
..IR xboard
will start the game with the initial chess position.
If
..IR matchMode
is set to
..IR Position ,
..IR xboard
will start the game with the position specified by the
..IR readPositionFile
resource.
If
..IR matchMode
is set to
..IR Opening ,
..IR xboard
will play out the opening moves specified by the
..IR -readGameFile
resource.
Default: "False".
..TP 8
..B -mono or -monoMode (False | True)
Determines whether
..IR xboard
displays its pieces and squares with two colors or four.
You shouldn't have to specify monochrome.
..IR xboard
will determine if this is necessary.
..SH RESOURCES
..TP 8
..B initString
The actual string that is sent to initialize the chess program can be
set from .Xdefaults.  It can't be set from the command line because of
syntax problems.
..TP 8
..B whiteString and blackString
These resources control what is sent when the Machine White and Machine Black
buttons are selected.  This is mostly for compatibility with previous versions
of gnuchess.
..TP 8
..B XBoard*font
This is the font that is used by
..IR xboard .
..SH COMMAND BUTTONS AND KEYS
..TP 8
..B Quit
Quits
..IR xboard .
Q or q is a keyboard equivalent.
..TP 8
..B Reset
Resets
..IR xboard
to the beginning of a chess game.
It also deselects any game or position files.
..TP 8
..B Flip View
inverts the view of the chess board.
..TP 8
..B Hint
displays a move hint from GNU Chess.
..TP 8
..B Play From File
plays a game from a record file.
If no file is specified a popup dialog asks for a filename.
Game files are found in the directory named by the CHESSDIR environment
variable.  If this variable is not declared then the current directory is used
unless the file name starts with a /.
G or g is a keyboard equivalent.
..TP 8
..B Setup From File
sets up a position from a position file.
If no file is specified a popup dialog asks for a filename.
Position files are found in the directory named by the CHESSDIR environment
variable.  If this variable is not declared then the current directory is used
unless the file name starts with a /.
..TP 8
..B Save Game
saves a game to a record file.
If no file is specified a popup dialog asks for a filename.
..TP 8
..B Save Position
saves a position to a position file.
If no file is specified a popup dialog asks for a filename.
..TP 8
..B Machine Black
forces GNU Chess to play black.
..TP 8
..B Machine White
forces GNU Chess to play white.
..TP 8
..B Switch Sides
forces GNU Chess to switch sides.
..TP 8
..B Two Machines
plays a game between two computer programs.
..TP 8
..B Forward
moves forward through a series of remembered moves.
F or f is a keyboard equivalent.
..TP 8
..B Backward
moves backward through a series of remembered moves.
B or b is a keyboard equivalent.
..TP 8
..B Force Moves
forces a series of moves.
..TP 8
..B Pause
pauses the game clocks or game replay.
P or p is a keyboard equivalent.
..TP 8
..B Iconify
I, i, C or c iconifies
SHAR_EOF
true || echo 'restore of xboard/xboard.man failed'
fi
echo 'End of  part 2'
echo 'File xboard/xboard.man is continued in part 3'
echo 3 > _shar_seq_.tmp
exit 0

--
Dan Heller
O'Reilly && Associates       Z-Code Software    Comp-sources-x:
Senior Writer                President          comp-sources-x at uunet.uu.net
argv at ora.com                 argv at zipcode.com



More information about the Comp.sources.x mailing list