Radix cross Linux

The main Radix cross Linux repository contains the build scripts of packages, which have the most complete and common functionality for desktop machines

452 Commits   2 Branches   1 Tag
Index: bdisp.c
===================================================================
--- bdisp.c	(nonexistent)
+++ bdisp.c	(revision 5)
@@ -0,0 +1,288 @@
+/*	$NetBSD: bdisp.c,v 1.8 2003/08/07 09:37:16 agc Exp $	*/
+
+/*
+ * Copyright (c) 1994
+ *	The Regents of the University of California.  All rights reserved.
+ *
+ * This code is derived from software contributed to Berkeley by
+ * Ralph Campbell.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the University nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <sys/cdefs.h>
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)bdisp.c	8.2 (Berkeley) 5/3/95";
+#else
+__RCSID("$NetBSD: bdisp.c,v 1.8 2003/08/07 09:37:16 agc Exp $");
+#endif
+#endif /* not lint */
+
+#include <curses.h>
+#include <string.h>
+#include "gomoku.h"
+
+#define	SCRNH		24		/* assume 24 lines for the moment */
+#define	SCRNW		80		/* assume 80 chars for the moment */
+
+static	int	lastline;
+static	char	pcolor[] = "*O.?";
+
+extern int interactive;
+extern char *plyr[];
+
+/*
+ * Initialize screen display.
+ */
+void
+cursinit()
+{
+
+	initscr();
+	noecho();
+	cbreak();
+	leaveok(stdscr, TRUE);
+}
+
+/*
+ * Restore screen display.
+ */
+void
+cursfini()
+{
+
+	leaveok(stdscr, FALSE);
+	move(23, 0);
+	clrtoeol();
+	refresh();
+	endwin();
+}
+
+/*
+ * Initialize board display.
+ */
+void
+bdisp_init()
+{
+	int i, j;
+
+	/* top border */
+	for (i = 1; i < BSZ1; i++) {
+		move(0, 2 * i + 1);
+		addch(letters[i]);
+	}
+	/* left and right edges */
+	for (j = BSZ1; --j > 0; ) {
+		move(20 - j, 0);
+		printw("%2d ", j);
+		move(20 - j, 2 * BSZ1 + 1);
+		printw("%d ", j);
+	}
+	/* bottom border */
+	for (i = 1; i < BSZ1; i++) {
+		move(20, 2 * i + 1);
+		addch(letters[i]);
+	}
+	bdwho(0);
+	move(0, 47);
+	addstr("#  black  white");
+	lastline = 0;
+	bdisp();
+}
+
+/*
+ * Update who is playing whom.
+ */
+void
+bdwho(update)
+	int update;
+{
+	int i;
+
+	move(21, 0);
+	clrtoeol();
+	i = 6 - strlen(plyr[BLACK]) / 2;
+	move(21, i > 0 ? i : 0);
+	printw("BLACK/%s", plyr[BLACK]);
+	i = 30 - strlen(plyr[WHITE]) / 2;
+	move(21, i);
+	printw("WHITE/%s", plyr[WHITE]);
+	move(21, 19);
+	addstr(" vs. ");
+	if (update)
+		refresh();
+}
+
+/*
+ * Update the board display after a move.
+ */
+void
+bdisp()
+{
+	int i, j, c;
+	struct spotstr *sp;
+
+	for (j = BSZ1; --j > 0; ) {
+		for (i = 1; i < BSZ1; i++) {
+			move(BSZ1 - j, 2 * i + 1);
+			sp = &board[i + j * BSZ1];
+			if (debug > 1 && sp->s_occ == EMPTY) {
+				if (sp->s_flg & IFLAGALL)
+					c = '+';
+				else if (sp->s_flg & CFLAGALL)
+					c = '-';
+				else
+					c = '.';
+			} else
+				c = pcolor[sp->s_occ];
+			addch(c);
+		}
+	}
+	refresh();
+}
+
+#ifdef DEBUG
+/*
+ * Dump board display to a file.
+ */
+void
+bdump(fp)
+	FILE *fp;
+{
+	int i, j, c;
+	struct spotstr *sp;
+
+	/* top border */
+	fprintf(fp, "   A B C D E F G H J K L M N O P Q R S T\n");
+
+	for (j = BSZ1; --j > 0; ) {
+		/* left edge */
+		fprintf(fp, "%2d ", j);
+		for (i = 1; i < BSZ1; i++) {
+			sp = &board[i + j * BSZ1];
+			if (debug > 1 && sp->s_occ == EMPTY) {
+				if (sp->s_flg & IFLAGALL)
+					c = '+';
+				else if (sp->s_flg & CFLAGALL)
+					c = '-';
+				else
+					c = '.';
+			} else
+				c = pcolor[sp->s_occ];
+			putc(c, fp);
+			putc(' ', fp);
+		}
+		/* right edge */
+		fprintf(fp, "%d\n", j);
+	}
+
+	/* bottom border */
+	fprintf(fp, "   A B C D E F G H J K L M N O P Q R S T\n");
+}
+#endif /* DEBUG */
+
+/*
+ * Display a transcript entry
+ */
+void
+dislog(str)
+	const char *str;
+{
+
+	if (++lastline >= SCRNH - 1) {
+		/* move 'em up */
+		lastline = 1;
+	}
+	move(lastline, 46);
+	addnstr(str, SCRNW - 46 - 1);
+	clrtoeol();
+	move(lastline + 1, 46);
+	clrtoeol();
+}
+
+/*
+ * Display a question.
+ */
+
+void
+ask(str)
+	const char *str;
+{
+	int len = strlen(str);
+
+	move(23, 0);
+	addstr(str);
+	clrtoeol();
+	move(23, len);
+	refresh();
+}
+
+int
+g_getline(buf, size)
+	char *buf;
+	int size;
+{
+	char *cp, *end;
+	int c;
+
+	c = 0;
+	cp = buf;
+	end = buf + size - 1;	/* save room for the '\0' */
+	while (cp < end && (c = getchar()) != EOF && c != '\n' && c != '\r') {
+		*cp++ = c;
+		if (interactive) {
+			switch (c) {
+			case 0x0c: /* ^L */
+				wrefresh(curscr);
+				cp--;
+				continue;
+			case 0x15: /* ^U */
+			case 0x18: /* ^X */
+				while (cp > buf) {
+					cp--;
+					addch('\b');
+				}
+				clrtoeol();
+				break;
+			case '\b':
+			case 0x7f: /* DEL */
+				if (cp == buf + 1) {
+					cp--;
+					continue;
+				}
+				cp -= 2;
+				addch('\b');
+				c = ' ';
+				/* FALLTHROUGH */
+			default:
+				addch(c);
+			}
+			refresh();
+		}
+	}
+	*cp = '\0';
+	return(c != EOF);
+}
Index: gomoku.h
===================================================================
--- gomoku.h	(nonexistent)
+++ gomoku.h	(revision 5)
@@ -0,0 +1,302 @@
+/*	$NetBSD: gomoku.h,v 1.10 2004/01/27 20:30:29 jsm Exp $	*/
+
+/*
+ * Copyright (c) 1994
+ *	The Regents of the University of California.  All rights reserved.
+ *
+ * This code is derived from software contributed to Berkeley by
+ * Ralph Campbell.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the University nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ *	@(#)gomoku.h	8.2 (Berkeley) 5/3/95
+ */
+
+#include <sys/types.h>
+#include <sys/endian.h>
+#include <stdio.h>
+
+/* board dimensions */
+#define BSZ	19
+#define BSZ1	(BSZ+1)
+#define BSZ2	(BSZ+2)
+#define BAREA	(BSZ2*BSZ1+1)
+
+/* frame dimentions (based on 5 in a row) */
+#define FSZ1	BSZ
+#define FSZ2	(BSZ-4)
+#define FAREA	(FSZ1*FSZ2 + FSZ2*FSZ2 + FSZ1*FSZ2 + FSZ2*FSZ2)
+
+#define MUP	(BSZ1)
+#define MDOWN	(-BSZ1)
+#define MLEFT	(-1)
+#define MRIGHT	(1)
+
+/* values for s_occ */
+#define BLACK	0
+#define WHITE	1
+#define EMPTY	2
+#define BORDER	3
+
+/* return values for makemove() */
+#define MOVEOK	0
+#define RESIGN	1
+#define ILLEGAL	2
+#define WIN	3
+#define TIE	4
+#define SAVE	5
+
+#define A 1
+#define B 2
+#define C 3
+#define D 4
+#define E 5
+#define F 6
+#define G 7
+#define H 8
+#define J 9
+#define K 10
+#define L 11
+#define M 12
+#define N 13
+#define O 14
+#define P 15
+#define Q 16
+#define R 17
+#define S 18
+#define T 19
+
+#define PT(x,y)		((x) + BSZ1 * (y))
+
+/*
+ * A 'frame' is a group of five or six contiguous board locations.
+ * An open ended frame is one with spaces on both ends; otherwise, its closed.
+ * A 'combo' is a group of intersecting frames and consists of two numbers:
+ * 'A' is the number of moves to make the combo non-blockable.
+ * 'B' is the minimum number of moves needed to win once it can't be blocked.
+ * A 'force' is a combo that is one move away from being non-blockable
+ *
+ * Single frame combo values:
+ *     <A,B>	board values
+ *	5,0	. . . . . O
+ *	4,1	. . . . . .
+ *	4,0	. . . . X O
+ *	3,1	. . . . X .
+ *	3,0	. . . X X O
+ *	2,1	. . . X X .
+ *	2,0	. . X X X O
+ *	1,1	. . X X X .
+ *	1,0	. X X X X O
+ *	0,1	. X X X X .
+ *	0,0	X X X X X O
+ *
+ * The rule for combining two combos (<A1,B1> <A2,B2>)
+ * with V valid intersection points, is:
+ *	A' = A1 + A2 - 2 - V
+ *	B' = MIN(A1 + B1 - 1, A2 + B2 - 1)
+ * Each time a frame is added to the combo, the number of moves to complete
+ * the force is the number of moves needed to 'fill' the frame plus one at
+ * the intersection point. The number of moves to win is the number of moves
+ * to complete the best frame minus the last move to complete the force.
+ * Note that it doesn't make sense to combine a <1,x> with anything since
+ * it is already a force. Also, the frames have to be independent so a
+ * single move doesn't affect more than one frame making up the combo.
+ *
+ * Rules for comparing which of two combos (<A1,B1> <A2,B2>) is better:
+ * Both the same color:
+ *	<A',B'> = (A1 < A2 || A1 == A2 && B1 <= B2) ? <A1,B1> : <A2,B2>
+ *	We want to complete the force first, then the combo with the
+ *	fewest moves to win.
+ * Different colors, <A1,B1> is the combo for the player with the next move:
+ *	<A',B'> = A2 <= 1 && (A1 > 1 || A2 + B2 < A1 + B1) ? <A2,B2> : <A1,B1>
+ *	We want to block only if we have to (i.e., if they are one move away
+ *	from completing a force and we don't have a force that we can
+ *	complete which takes fewer or the same number of moves to win).
+ */
+
+#define MAXA		6
+#define MAXB		2
+#define MAXCOMBO	0x600
+
+union	comboval {
+	struct {
+#if BYTE_ORDER == BIG_ENDIAN
+		u_char	a;	/* # moves to complete force */
+		u_char	b;	/* # moves to win */
+#endif
+#if BYTE_ORDER == LITTLE_ENDIAN
+		u_char	b;	/* # moves to win */
+		u_char	a;	/* # moves to complete force */
+#endif
+	} c;
+	u_short	s;
+};
+
+/*
+ * This structure is used to record information about single frames (F) and
+ * combinations of two more frames (C).
+ * For combinations of two or more frames, there is an additional
+ * array of pointers to the frames of the combination which is sorted
+ * by the index into the frames[] array. This is used to prevent duplication
+ * since frame A combined with B is the same as B with A.
+ *	struct combostr *c_sort[size c_nframes];
+ * The leaves of the tree (frames) are numbered 0 (bottom, leftmost)
+ * to c_nframes - 1 (top, right). This is stored in c_frameindex and
+ * c_dir if C_LOOP is set.
+ */
+struct combostr {
+	struct combostr	*c_next;	/* list of combos at the same level */
+	struct combostr	*c_prev;	/* list of combos at the same level */
+	struct combostr	*c_link[2];	/* C:previous level or F:NULL */
+	union comboval	c_linkv[2];	/* C:combo value for link[0,1] */
+	union comboval	c_combo;	/* C:combo value for this level */
+	u_short		c_vertex;	/* C:intersection or F:frame head */
+	u_char		c_nframes;	/* number of frames in the combo */
+	u_char		c_dir;		/* C:loop frame or F:frame direction */
+	u_char		c_flg;		/* C:combo flags */
+	u_char		c_frameindex;	/* C:intersection frame index */
+	u_char		c_framecnt[2];	/* number of frames left to attach */
+	u_char		c_emask[2];	/* C:bit mask of completion spots for
+					 * link[0] and link[1] */
+	u_char		c_voff[2];	/* C:vertex offset within frame */
+};
+
+/* flag values for c_flg */
+#define C_OPEN_0	0x01		/* link[0] is an open ended frame */
+#define C_OPEN_1	0x02		/* link[1] is an open ended frame */
+#define C_LOOP		0x04		/* link[1] intersects previous frame */
+#define C_MARK		0x08		/* indicates combo processed */
+
+/*
+ * This structure is used for recording the completion points of
+ * multi frame combos.
+ */
+struct	elist {
+	struct elist	*e_next;	/* list of completion points */
+	struct combostr	*e_combo;	/* the whole combo */
+	u_char		e_off;		/* offset in frame of this empty spot */
+	u_char		e_frameindex;	/* intersection frame index */
+	u_char		e_framecnt;	/* number of frames left to attach */
+	u_char		e_emask;	/* real value of the frame's emask */
+	union comboval	e_fval;		/* frame combo value */
+};
+
+/*
+ * One spot structure for each location on the board.
+ * A frame consists of the combination for the current spot plus the five spots
+ * 0: right, 1: right & down, 2: down, 3: down & left.
+ */
+struct	spotstr {
+	short		s_occ;		/* color of occupant */
+	short		s_wval;		/* weighted value */
+	int		s_flg;		/* flags for graph walks */
+	struct combostr	*s_frame[4];	/* level 1 combo for frame[dir] */
+	union comboval	s_fval[2][4];	/* combo value for [color][frame] */
+	union comboval	s_combo[2];	/* minimum combo value for BLK & WHT */
+	u_char		s_level[2];	/* number of frames in the min combo */
+	u_char		s_nforce[2];	/* number of <1,x> combos */
+	struct elist	*s_empty;	/* level n combo completion spots */
+	struct elist	*s_nempty;	/* level n+1 combo completion spots */
+	int		dummy[2];	/* XXX */
+};
+
+/* flag values for s_flg */
+#define CFLAG		0x000001	/* frame is part of a combo */
+#define CFLAGALL	0x00000F	/* all frame directions marked */
+#define IFLAG		0x000010	/* legal intersection point */
+#define IFLAGALL	0x0000F0	/* any intersection points? */
+#define FFLAG		0x000100	/* frame is part of a <1,x> combo */
+#define FFLAGALL	0x000F00	/* all force frames */
+#define MFLAG		0x001000	/* frame has already been seen */
+#define MFLAGALL	0x00F000	/* all frames seen */
+#define BFLAG		0x010000	/* frame intersects border or dead */
+#define BFLAGALL	0x0F0000	/* all frames dead */
+
+/*
+ * This structure is used to store overlap information between frames.
+ */
+struct	ovlp_info {
+	int		o_intersect;	/* intersection spot */
+	struct combostr	*o_fcombo;	/* the connecting combo */
+	u_char		o_link;		/* which link to update (0 or 1) */
+	u_char		o_off;		/* offset in frame of intersection */
+	u_char		o_frameindex;	/* intersection frame index */
+};
+
+extern	const char	*letters;
+extern	char	fmtbuf[];
+extern	const char	pdir[];
+
+extern	const int     dd[4];
+extern	struct	spotstr	board[BAREA];		/* info for board */
+extern	struct	combostr frames[FAREA];		/* storage for single frames */
+extern	struct	combostr *sortframes[2];	/* sorted, non-empty frames */
+extern	u_char	overlap[FAREA * FAREA];		/* frame [a][b] overlap */
+extern	short	intersect[FAREA * FAREA];	/* frame [a][b] intersection */
+extern	int	movelog[BSZ * BSZ];		/* history of moves */
+extern	int	movenum;
+extern	int	debug;
+
+#define ASSERT(x)
+
+void	bdinit(struct spotstr *);
+void	init_overlap(void);
+int	g_getline(char *, int);
+void	ask(const char *);
+void	dislog(const char *);
+void	bdump(FILE *);
+void	bdisp(void);
+void	bdisp_init(void);
+void	cursfini(void);
+void	cursinit(void);
+void	bdwho(int);
+void	panic(const char *) __attribute__((__noreturn__));
+void	glog(const char *);
+void	dlog(const char *);
+void	quit(void) __attribute__((__noreturn__));
+void	quitsig(int) __attribute__((__noreturn__));
+void	whatsup(int);
+int	readinput(FILE *);
+const char   *stoc(int);
+int	lton(int);
+int	ctos(const char *);
+void	update_overlap(struct spotstr *);
+int	makemove(int, int);
+int	list_eq(struct combostr **, struct combostr **, int);
+void	clearcombo(struct combostr *, int);
+void	makeempty(struct combostr *);
+void	appendcombo(struct combostr *, int);
+void	updatecombo(struct combostr *, int);
+void	markcombo(struct combostr *);
+void	printcombo(struct combostr *, char *);
+void	makecombo(struct combostr *, struct spotstr *, int, int);
+void	makecombo2(struct combostr *, struct spotstr *, int, int);
+int	sortcombo(struct combostr **, struct combostr **, struct combostr *);
+int	checkframes(struct combostr *, struct combostr *, struct spotstr *,
+		    int, struct ovlp_info *);
+void	addframes(int);
+void	scanframes(int);
+int	better(const struct spotstr *, const struct spotstr *, int);
+int	pickmove(int);
Index: main.c
===================================================================
--- main.c	(nonexistent)
+++ main.c	(revision 5)
@@ -0,0 +1,550 @@
+/*	$NetBSD: main.c,v 1.12 2004/01/27 20:30:29 jsm Exp $	*/
+
+/*
+ * Copyright (c) 1994
+ *	The Regents of the University of California.  All rights reserved.
+ *
+ * This code is derived from software contributed to Berkeley by
+ * Ralph Campbell.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the University nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <sys/cdefs.h>
+#ifndef lint
+__COPYRIGHT("@(#) Copyright (c) 1994\n\
+	The Regents of the University of California.  All rights reserved.\n");
+#endif /* not lint */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)main.c	8.4 (Berkeley) 5/4/95";
+#else
+__RCSID("$NetBSD: main.c,v 1.12 2004/01/27 20:30:29 jsm Exp $");
+#endif
+#endif /* not lint */
+
+#include <curses.h>
+#include <err.h>
+#include <signal.h>
+#include <stdlib.h>
+#include <string.h>
+#include <time.h>
+#include <unistd.h>
+
+#include "gomoku.h"
+
+#define USER	0		/* get input from standard input */
+#define PROGRAM	1		/* get input from program */
+#define INPUTF	2		/* get input from a file */
+
+int	interactive = 1;	/* true if interactive */
+int	debug;			/* true if debugging */
+int	test;			/* both moves come from 1: input, 2: computer */
+char	*prog;			/* name of program */
+FILE	*debugfp;		/* file for debug output */
+FILE	*inputfp;		/* file for debug input */
+
+const char	pdir[4]		= "-\\|/";
+char	fmtbuf[128];
+
+struct	spotstr	board[BAREA];		/* info for board */
+struct	combostr frames[FAREA];		/* storage for all frames */
+struct	combostr *sortframes[2];	/* sorted list of non-empty frames */
+u_char	overlap[FAREA * FAREA];		/* true if frame [a][b] overlap */
+short	intersect[FAREA * FAREA];	/* frame [a][b] intersection */
+int	movelog[BSZ * BSZ];		/* log of all the moves */
+int	movenum;			/* current move number */
+const char	*plyr[2];			/* who's who */
+
+int	main(int, char *[]);
+
+int
+main(argc, argv)
+	int argc;
+	char **argv;
+{
+	char buf[128];
+	int color, curmove, i, ch;
+	int input[2];
+	static const char *const fmt[2] = {
+		"%3d %-6s",
+		"%3d        %-6s"
+	};
+
+	/* Revoke setgid privileges */
+	setregid(getgid(), getgid());
+
+	color = curmove = 0;
+
+	prog = strrchr(argv[0], '/');
+	if (prog)
+		prog++;
+	else
+		prog = argv[0];
+
+	while ((ch = getopt(argc, argv, "bcdD:u")) != -1) {
+		switch (ch) {
+		case 'b':	/* background */
+			interactive = 0;
+			break;
+		case 'd':	/* debugging */
+			debug++;
+			break;
+		case 'D':	/* log debug output to file */
+			if ((debugfp = fopen(optarg, "w")) == NULL)
+				err(1, "%s", optarg);
+			break;
+		case 'u':	/* testing: user verses user */
+			test = 1;
+			break;
+		case 'c':	/* testing: computer verses computer */
+			test = 2;
+			break;
+		}
+	}
+	argc -= optind;
+	argv += optind;
+	if (argc) {
+		if ((inputfp = fopen(*argv, "r")) == NULL)
+			err(1, "%s", *argv);
+	}
+
+	if (!debug)
+#ifdef SVR4
+		srand(time(0));
+#else
+		srandom(time(0));
+#endif
+	if (interactive)
+		cursinit();		/* initialize curses */
+again:
+	bdinit(board);			/* initialize board contents */
+
+	if (interactive) {
+		plyr[BLACK] = plyr[WHITE] = "???";
+		bdisp_init();		/* initialize display of board */
+#ifdef DEBUG
+		signal(SIGINT, whatsup);
+#else
+		signal(SIGINT, quitsig);
+#endif
+
+		if (inputfp == NULL && test == 0) {
+			for (;;) {
+				ask("black or white? ");
+				g_getline(buf, sizeof(buf));
+				if (buf[0] == 'b' || buf[0] == 'B') {
+					color = BLACK;
+					break;
+				}
+				if (buf[0] == 'w' || buf[0] == 'W') {
+					color = WHITE;
+					break;
+				}
+				move(22, 0);
+				printw("Black moves first. Please enter `black' or `white'\n");
+			}
+			move(22, 0);
+			clrtoeol();
+		}
+	} else {
+		setbuf(stdout, 0);
+		g_getline(buf, sizeof(buf));
+		if (strcmp(buf, "black") == 0)
+			color = BLACK;
+		else if (strcmp(buf, "white") == 0)
+			color = WHITE;
+		else {
+			sprintf(fmtbuf,
+			    "Huh?  Expected `black' or `white', got `%s'\n",
+			    buf);
+			panic(fmtbuf);
+		}
+	}
+
+	if (inputfp) {
+		input[BLACK] = INPUTF;
+		input[WHITE] = INPUTF;
+	} else {
+		switch (test) {
+		case 0: /* user verses program */
+			input[color] = USER;
+			input[!color] = PROGRAM;
+			break;
+
+		case 1: /* user verses user */
+			input[BLACK] = USER;
+			input[WHITE] = USER;
+			break;
+
+		case 2: /* program verses program */
+			input[BLACK] = PROGRAM;
+			input[WHITE] = PROGRAM;
+			break;
+		}
+	}
+	if (interactive) {
+		plyr[BLACK] = input[BLACK] == USER ? "you" : prog;
+		plyr[WHITE] = input[WHITE] == USER ? "you" : prog;
+		bdwho(1);
+	}
+
+	for (color = BLACK; ; color = !color) {
+	top:
+		switch (input[color]) {
+		case INPUTF: /* input comes from a file */
+			curmove = readinput(inputfp);
+			if (curmove != ILLEGAL)
+				break;
+			switch (test) {
+			case 0: /* user verses program */
+				input[color] = USER;
+				input[!color] = PROGRAM;
+				break;
+
+			case 1: /* user verses user */
+				input[BLACK] = USER;
+				input[WHITE] = USER;
+				break;
+
+			case 2: /* program verses program */
+				input[BLACK] = PROGRAM;
+				input[WHITE] = PROGRAM;
+				break;
+			}
+			plyr[BLACK] = input[BLACK] == USER ? "you" : prog;
+			plyr[WHITE] = input[WHITE] == USER ? "you" : prog;
+			bdwho(1);
+			goto top;
+
+		case USER: /* input comes from standard input */
+		getinput:
+			if (interactive)
+				ask("move? ");
+			if (!g_getline(buf, sizeof(buf))) {
+				curmove = RESIGN;
+				break;
+			}
+			if (buf[0] == '\0')
+				goto getinput;
+			curmove = ctos(buf);
+			if (interactive) {
+				if (curmove == SAVE) {
+					FILE *fp;
+
+					ask("save file name? ");
+					(void)g_getline(buf, sizeof(buf));
+					if ((fp = fopen(buf, "w")) == NULL) {
+						glog("cannot create save file");
+						goto getinput;
+					}
+					for (i = 0; i < movenum - 1; i++)
+						fprintf(fp, "%s\n",
+							stoc(movelog[i]));
+					fclose(fp);
+					goto getinput;
+				}
+				if (curmove != RESIGN &&
+				    board[curmove].s_occ != EMPTY) {
+					glog("Illegal move");
+					goto getinput;
+				}
+			}
+			break;
+
+		case PROGRAM: /* input comes from the program */
+			curmove = pickmove(color);
+			break;
+		}
+		if (interactive) {
+			sprintf(fmtbuf, fmt[color], movenum, stoc(curmove));
+			glog(fmtbuf);
+		}
+		if ((i = makemove(color, curmove)) != MOVEOK)
+			break;
+		if (interactive)
+			bdisp();
+	}
+	if (interactive) {
+		move(22, 0);
+		switch (i) {
+		case WIN:
+			if (input[color] == PROGRAM)
+				addstr("Ha ha, I won");
+			else
+				addstr("Rats! you won");
+			break;
+		case TIE:
+			addstr("Wow! its a tie");
+			break;
+		case ILLEGAL:
+			addstr("Illegal move");
+			break;
+		}
+		clrtoeol();
+		bdisp();
+		if (i != RESIGN) {
+		replay:
+			ask("replay? ");
+			if (g_getline(buf, sizeof(buf)) &&
+			    (buf[0] == 'y' || buf[0] == 'Y'))
+				goto again;
+			if (strcmp(buf, "save") == 0) {
+				FILE *fp;
+
+				ask("save file name? ");
+				(void)g_getline(buf, sizeof(buf));
+				if ((fp = fopen(buf, "w")) == NULL) {
+					glog("cannot create save file");
+					goto replay;
+				}
+				for (i = 0; i < movenum - 1; i++)
+					fprintf(fp, "%s\n",
+						stoc(movelog[i]));
+				fclose(fp);
+				goto replay;
+			}
+		}
+	}
+	quit();
+	/* NOTREACHED */
+	return(0);
+}
+
+int
+readinput(fp)
+	FILE *fp;
+{
+	char *cp;
+	int c;
+
+	cp = fmtbuf;
+	while ((c = getc(fp)) != EOF && c != '\n')
+		*cp++ = c;
+	*cp = '\0';
+	return (ctos(fmtbuf));
+}
+
+#ifdef DEBUG
+/*
+ * Handle strange situations.
+ */
+void
+whatsup(signum)
+	int signum;
+{
+	int i, pnum, n, s1, s2, d1, d2;
+	struct spotstr *sp;
+	FILE *fp;
+	char *str;
+	struct elist *ep;
+	struct combostr *cbp;
+
+	if (!interactive)
+		quit();
+top:
+	ask("cmd? ");
+	if (!g_getline(fmtbuf, sizeof(fmtbuf)))
+		quit();
+	switch (*fmtbuf) {
+	case '\0':
+		goto top;
+	case 'q':		/* conservative quit */
+		quit();
+	case 'd':		/* set debug level */
+		debug = fmtbuf[1] - '0';
+		sprintf(fmtbuf, "Debug set to %d", debug);
+		dlog(fmtbuf);
+		sleep(1);
+	case 'c':
+		break;
+	case 'b':		/* back up a move */
+		if (movenum > 1) {
+			movenum--;
+			board[movelog[movenum - 1]].s_occ = EMPTY;
+			bdisp();
+		}
+		goto top;
+	case 's':		/* suggest a move */
+		i = fmtbuf[1] == 'b' ? BLACK : WHITE;
+		sprintf(fmtbuf, "suggest %c %s", i == BLACK ? 'B' : 'W',
+			stoc(pickmove(i)));
+		dlog(fmtbuf);
+		goto top;
+	case 'f':		/* go forward a move */
+		board[movelog[movenum - 1]].s_occ = movenum & 1 ? BLACK : WHITE;
+		movenum++;
+		bdisp();
+		goto top;
+	case 'l':		/* print move history */
+		if (fmtbuf[1] == '\0') {
+			for (i = 0; i < movenum - 1; i++)
+				dlog(stoc(movelog[i]));
+			goto top;
+		}
+		if ((fp = fopen(fmtbuf + 1, "w")) == NULL)
+			goto top;
+		for (i = 0; i < movenum - 1; i++) {
+			fprintf(fp, "%s", stoc(movelog[i]));
+			if (++i < movenum - 1)
+				fprintf(fp, " %s\n", stoc(movelog[i]));
+			else
+				fputc('\n', fp);
+		}
+		bdump(fp);
+		fclose(fp);
+		goto top;
+	case 'o':
+		n = 0;
+		for (str = fmtbuf + 1; *str; str++)
+			if (*str == ',') {
+				for (d1 = 0; d1 < 4; d1++)
+					if (str[-1] == pdir[d1])
+						break;
+				str[-1] = '\0';
+				sp = &board[s1 = ctos(fmtbuf + 1)];
+				n = (sp->s_frame[d1] - frames) * FAREA;
+				*str++ = '\0';
+				break;
+			}
+		sp = &board[s2 = ctos(str)];
+		while (*str)
+			str++;
+		for (d2 = 0; d2 < 4; d2++)
+			if (str[-1] == pdir[d2])
+				break;
+		n += sp->s_frame[d2] - frames;
+		str = fmtbuf;
+		sprintf(str, "overlap %s%c,", stoc(s1), pdir[d1]);
+		str += strlen(str);
+		sprintf(str, "%s%c = %x", stoc(s2), pdir[d2], overlap[n]);
+		dlog(fmtbuf);
+		goto top;
+	case 'p':
+		sp = &board[i = ctos(fmtbuf + 1)];
+		sprintf(fmtbuf, "V %s %x/%d %d %x/%d %d %d %x", stoc(i),
+			sp->s_combo[BLACK].s, sp->s_level[BLACK],
+			sp->s_nforce[BLACK],
+			sp->s_combo[WHITE].s, sp->s_level[WHITE],
+			sp->s_nforce[WHITE], sp->s_wval, sp->s_flg);
+		dlog(fmtbuf);
+		sprintf(fmtbuf, "FB %s %x %x %x %x", stoc(i),
+			sp->s_fval[BLACK][0].s, sp->s_fval[BLACK][1].s,
+			sp->s_fval[BLACK][2].s, sp->s_fval[BLACK][3].s);
+		dlog(fmtbuf);
+		sprintf(fmtbuf, "FW %s %x %x %x %x", stoc(i),
+			sp->s_fval[WHITE][0].s, sp->s_fval[WHITE][1].s,
+			sp->s_fval[WHITE][2].s, sp->s_fval[WHITE][3].s);
+		dlog(fmtbuf);
+		goto top;
+	case 'e':	/* e {b|w} [0-9] spot */
+		str = fmtbuf + 1;
+		if (*str >= '0' && *str <= '9')
+			n = *str++ - '0';
+		else
+			n = 0;
+		sp = &board[i = ctos(str)];
+		for (ep = sp->s_empty; ep; ep = ep->e_next) {
+			cbp = ep->e_combo;
+			if (n) {
+				if (cbp->c_nframes > n)
+					continue;
+				if (cbp->c_nframes != n)
+					break;
+			}
+			printcombo(cbp, fmtbuf);
+			dlog(fmtbuf);
+		}
+		goto top;
+	default:
+syntax:
+		dlog("Options are:");
+		dlog("q    - quit");
+		dlog("c    - continue");
+		dlog("d#   - set debug level to #");
+		dlog("p#   - print values at #");
+		goto top;
+	}
+}
+#endif /* DEBUG */
+
+/*
+ * Display debug info.
+ */
+void
+dlog(str)
+	const char *str;
+{
+
+	if (debugfp)
+		fprintf(debugfp, "%s\n", str);
+	if (interactive)
+		dislog(str);
+	else
+		fprintf(stderr, "%s\n", str);
+}
+
+void
+glog(str)
+	const char *str;
+{
+
+	if (debugfp)
+		fprintf(debugfp, "%s\n", str);
+	if (interactive)
+		dislog(str);
+	else
+		printf("%s\n", str);
+}
+
+void
+quit()
+{
+	if (interactive) {
+		bdisp();		/* show final board */
+		cursfini();
+	}
+	exit(0);
+}
+
+void
+quitsig(dummy)
+	int dummy __attribute__((__unused__));
+{
+	quit();
+}
+
+/*
+ * Die gracefully.
+ */
+void
+panic(str)
+	const char *str;
+{
+	fprintf(stderr, "%s: %s\n", prog, str);
+	fputs("resign\n", stdout);
+	quit();
+}
Index: .
===================================================================
--- .	(nonexistent)
+++ .	(revision 5)

Property changes on: .
___________________________________________________________________
Added: svn:ignore
## -0,0 +1,73 ##
+
+# install dir
+dist
+
+# Target build dirs
+.a1x-newlib
+.a2x-newlib
+.at91sam7s-newlib
+
+.build-machine
+
+.a1x-glibc
+.a2x-glibc
+.h3-glibc
+.h5-glibc
+.i586-glibc
+.i686-glibc
+.imx6-glibc
+.jz47xx-glibc
+.makefile
+.am335x-glibc
+.omap543x-glibc
+.p5600-glibc
+.power8-glibc
+.power8le-glibc
+.power9-glibc
+.power9le-glibc
+.m1000-glibc
+.riscv64-glibc
+.rk328x-glibc
+.rk33xx-glibc
+.rk339x-glibc
+.s8xx-glibc
+.s9xx-glibc
+.x86_64-glibc
+
+# Hidden files (each file)
+.makefile
+.dist
+.rootfs
+
+# src & hw requires
+.src_requires
+.src_requires_depend
+.requires
+.requires_depend
+
+# Tarballs
+*.gz
+*.bz2
+*.lz
+*.xz
+*.tgz
+*.txz
+
+# Signatures
+*.asc
+*.sig
+*.sign
+*.sha1sum
+
+# Patches
+*.patch
+
+# Descriptions
+*.dsc
+*.txt
+
+# Default linux config files
+*.defconfig
+
+# backup copies
+*~