summaryrefslogtreecommitdiff
path: root/games/mille
diff options
context:
space:
mode:
Diffstat (limited to 'games/mille')
-rw-r--r--games/mille/Makefile13
-rw-r--r--games/mille/comp.c485
-rw-r--r--games/mille/end.c154
-rw-r--r--games/mille/extern.c178
-rw-r--r--games/mille/init.c256
-rw-r--r--games/mille/mille.6381
-rw-r--r--games/mille/mille.c169
-rw-r--r--games/mille/mille.h231
-rw-r--r--games/mille/misc.c259
-rw-r--r--games/mille/move.c570
-rw-r--r--games/mille/print.c175
-rw-r--r--games/mille/roll.c63
-rw-r--r--games/mille/save.c180
-rw-r--r--games/mille/table.c70
-rw-r--r--games/mille/types.c81
-rw-r--r--games/mille/unctrl.h44
-rw-r--r--games/mille/varpush.c98
17 files changed, 3407 insertions, 0 deletions
diff --git a/games/mille/Makefile b/games/mille/Makefile
new file mode 100644
index 00000000000..db585de3e8a
--- /dev/null
+++ b/games/mille/Makefile
@@ -0,0 +1,13 @@
+# $NetBSD: Makefile,v 1.5 1995/03/24 05:00:43 cgd Exp $
+# @(#)Makefile 8.1 (Berkeley) 5/31/93
+
+PROG= mille
+SRCS= comp.c end.c extern.c init.c mille.c misc.c move.c print.c \
+ roll.c save.c types.c varpush.c
+DPADD= ${LIBCURSES} ${LIBTERM} ${LIBCOMPAT}
+LDADD= -lcurses -ltermlib -lcompat
+MAN= mille.6
+HIDEGAME=hidegame
+
+.include <bsd.prog.mk>
+
diff --git a/games/mille/comp.c b/games/mille/comp.c
new file mode 100644
index 00000000000..58538e3b3c8
--- /dev/null
+++ b/games/mille/comp.c
@@ -0,0 +1,485 @@
+/* $NetBSD: comp.c,v 1.4 1995/03/24 05:01:11 cgd Exp $ */
+
+/*
+ * Copyright (c) 1982, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)comp.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: comp.c,v 1.4 1995/03/24 05:01:11 cgd Exp $";
+#endif
+#endif /* not lint */
+
+# include "mille.h"
+
+/*
+ * @(#)comp.c 1.1 (Berkeley) 4/1/82
+ */
+
+# define V_VALUABLE 40
+
+calcmove()
+{
+ register CARD card;
+ register int *value;
+ register PLAY *pp, *op;
+ register bool foundend, cango, canstop, foundlow;
+ register unsgn int i, count200, badcount, nummin, nummax, diff;
+ register int curmin, curmax;
+ register CARD safe, oppos;
+ int valbuf[HAND_SZ], count[NUM_CARDS];
+ bool playit[HAND_SZ];
+
+ wmove(Score, ERR_Y, ERR_X); /* get rid of error messages */
+ wclrtoeol(Score);
+ pp = &Player[COMP];
+ op = &Player[PLAYER];
+ safe = 0;
+ cango = 0;
+ canstop = FALSE;
+ foundend = FALSE;
+
+ /* Try for a Coup Forre, and see what we have. */
+ for (i = 0; i < NUM_CARDS; i++)
+ count[i] = 0;
+ for (i = 0; i < HAND_SZ; i++) {
+ card = pp->hand[i];
+ switch (card) {
+ case C_STOP: case C_CRASH:
+ case C_FLAT: case C_EMPTY:
+ if (playit[i] = canplay(pp, op, card))
+ canstop = TRUE;
+ goto norm;
+ case C_LIMIT:
+ if ((playit[i] = canplay(pp, op, card))
+ && Numseen[C_25] == Numcards[C_25]
+ && Numseen[C_50] == Numcards[C_50])
+ canstop = TRUE;
+ goto norm;
+ case C_25: case C_50: case C_75:
+ case C_100: case C_200:
+ if ((playit[i] = canplay(pp, op, card))
+ && pp->mileage + Value[card] == End)
+ foundend = TRUE;
+ goto norm;
+ default:
+ playit[i] = canplay(pp, op, card);
+norm:
+ if (playit[i])
+ ++cango;
+ break;
+ case C_GAS_SAFE: case C_DRIVE_SAFE:
+ case C_SPARE_SAFE: case C_RIGHT_WAY:
+ if (pp->battle == opposite(card) ||
+ (pp->speed == C_LIMIT && card == C_RIGHT_WAY)) {
+ Movetype = M_PLAY;
+ Card_no = i;
+ return;
+ }
+ ++safe;
+ playit[i] = TRUE;
+ break;
+ }
+ if (card >= 0)
+ ++count[card];
+ }
+
+ /* No Coup Forre. Draw to fill hand, then restart, as needed. */
+ if (pp->hand[0] == C_INIT && Topcard > Deck) {
+ Movetype = M_DRAW;
+ return;
+ }
+
+#ifdef DEBUG
+ if (Debug)
+ fprintf(outf, "CALCMOVE: cango = %d, canstop = %d, safe = %d\n",
+ cango, canstop, safe);
+#endif
+ if (foundend)
+ foundend = !check_ext(TRUE);
+ for (i = 0; safe && i < HAND_SZ; i++) {
+ if (issafety(pp->hand[i])) {
+ if (onecard(op) || (foundend && cango && !canstop)) {
+#ifdef DEBUG
+ if (Debug)
+ fprintf(outf,
+ "CALCMOVE: onecard(op) = %d, foundend = %d\n",
+ onecard(op), foundend);
+#endif
+playsafe:
+ Movetype = M_PLAY;
+ Card_no = i;
+ return;
+ }
+ oppos = opposite(pp->hand[i]);
+ if (Numseen[oppos] == Numcards[oppos] &&
+ !(pp->hand[i] == C_RIGHT_WAY &&
+ Numseen[C_LIMIT] != Numcards[C_LIMIT]))
+ goto playsafe;
+ else if (!cango
+ && (op->can_go || !pp->can_go || Topcard < Deck)) {
+ card = (Topcard - Deck) - roll(1, 10);
+ if ((!pp->mileage) != (!op->mileage))
+ card -= 7;
+#ifdef DEBUG
+ if (Debug)
+ fprintf(outf,
+ "CALCMOVE: card = %d, DECK_SZ / 4 = %d\n",
+ card, DECK_SZ / 4);
+#endif
+ if (card < DECK_SZ / 4)
+ goto playsafe;
+ }
+ safe--;
+ playit[i] = cango;
+ }
+ }
+ if (!pp->can_go && !isrepair(pp->battle))
+ Numneed[opposite(pp->battle)]++;
+redoit:
+ foundlow = (cango || count[C_END_LIMIT] != 0
+ || Numseen[C_LIMIT] == Numcards[C_LIMIT]
+ || pp->safety[S_RIGHT_WAY] != S_UNKNOWN);
+ foundend = FALSE;
+ count200 = pp->nummiles[C_200];
+ badcount = 0;
+ curmax = -1;
+ curmin = 101;
+ nummin = -1;
+ nummax = -1;
+ value = valbuf;
+ for (i = 0; i < HAND_SZ; i++) {
+ card = pp->hand[i];
+ if (issafety(card) || playit[i] == (cango != 0)) {
+#ifdef DEBUG
+ if (Debug)
+ fprintf(outf, "CALCMOVE: switch(\"%s\")\n",
+ C_name[card]);
+#endif
+ switch (card) {
+ case C_25: case C_50:
+ diff = End - pp->mileage;
+ /* avoid getting too close */
+ if (Topcard > Deck && cango && diff <= 100
+ && diff / Value[card] > count[card]
+ && (card == C_25 || diff % 50 == 0)) {
+ if (card == C_50 && diff - 50 == 25
+ && count[C_25] > 0)
+ goto okay;
+ *value = 0;
+ if (--cango <= 0)
+ goto redoit;
+ break;
+ }
+okay:
+ *value = (Value[card] >> 3);
+ if (pp->speed == C_LIMIT)
+ ++*value;
+ else
+ --*value;
+ if (!foundlow
+ && (card == C_50 || count[C_50] == 0)) {
+ *value = (pp->mileage ? 10 : 20);
+ foundlow = TRUE;
+ }
+ goto miles;
+ case C_200:
+ if (++count200 > 2) {
+ *value = 0;
+ break;
+ }
+ case C_75: case C_100:
+ *value = (Value[card] >> 3);
+ if (pp->speed == C_LIMIT)
+ --*value;
+ else
+ ++*value;
+miles:
+ if (pp->mileage + Value[card] > End)
+ *value = (End == 700 ? card : 0);
+ else if (pp->mileage + Value[card] == End) {
+ *value = (foundend ? card : V_VALUABLE);
+ foundend = TRUE;
+ }
+ break;
+ case C_END_LIMIT:
+ if (pp->safety[S_RIGHT_WAY] != S_UNKNOWN)
+ *value = (pp->safety[S_RIGHT_WAY] ==
+ S_PLAYED ? -1 : 1);
+ else if (pp->speed == C_LIMIT &&
+ End - pp->mileage <= 50)
+ *value = 1;
+ else if (pp->speed == C_LIMIT
+ || Numseen[C_LIMIT] != Numcards[C_LIMIT]) {
+ safe = S_RIGHT_WAY;
+ oppos = C_LIMIT;
+ goto repair;
+ }
+ else {
+ *value = 0;
+ --count[C_END_LIMIT];
+ }
+ break;
+ case C_REPAIRS: case C_SPARE: case C_GAS:
+ safe = safety(card) - S_CONV;
+ oppos = opposite(card);
+ if (pp->safety[safe] != S_UNKNOWN)
+ *value = (pp->safety[safe] ==
+ S_PLAYED ? -1 : 1);
+ else if (pp->battle != oppos
+ && (Numseen[oppos] == Numcards[oppos] ||
+ Numseen[oppos] + count[card] >
+ Numcards[oppos])) {
+ *value = 0;
+ --count[card];
+ }
+ else {
+repair:
+ *value = Numcards[oppos] * 6;
+ *value += Numseen[card] -
+ Numseen[oppos];
+ if (!cango)
+ *value /= (count[card]*count[card]);
+ count[card]--;
+ }
+ break;
+ case C_GO:
+ if (pp->safety[S_RIGHT_WAY] != S_UNKNOWN)
+ *value = (pp->safety[S_RIGHT_WAY] ==
+ S_PLAYED ? -1 : 2);
+ else if (pp->can_go
+ && Numgos + count[C_GO] == Numneed[C_GO]) {
+ *value = 0;
+ --count[C_GO];
+ }
+ else {
+ *value = Numneed[C_GO] * 3;
+ *value += (Numseen[C_GO] - Numgos);
+ *value /= (count[C_GO] * count[C_GO]);
+ count[C_GO]--;
+ }
+ break;
+ case C_LIMIT:
+ if (op->mileage + 50 >= End) {
+ *value = (End == 700 && !cango);
+ break;
+ }
+ if (canstop || (cango && !op->can_go))
+ *value = 1;
+ else {
+ *value = (pp->safety[S_RIGHT_WAY] !=
+ S_UNKNOWN ? 2 : 3);
+ safe = S_RIGHT_WAY;
+ oppos = C_END_LIMIT;
+ goto normbad;
+ }
+ break;
+ case C_CRASH: case C_EMPTY: case C_FLAT:
+ safe = safety(card) - S_CONV;
+ oppos = opposite(card);
+ *value = (pp->safety[safe]!=S_UNKNOWN ? 3 : 4);
+normbad:
+ if (op->safety[safe] == S_PLAYED)
+ *value = -1;
+ else {
+ *value *= Numneed[oppos] +
+ Numseen[oppos] + 2;
+ if (!pp->mileage || foundend ||
+ onecard(op))
+ *value += 5;
+ if (op->mileage == 0 || onecard(op))
+ *value += 5;
+ if (op->speed == C_LIMIT)
+ *value -= 3;
+ if (cango &&
+ pp->safety[safe] != S_UNKNOWN)
+ *value += 3;
+ if (!cango)
+ *value /= ++badcount;
+ }
+ break;
+ case C_STOP:
+ if (op->safety[S_RIGHT_WAY] == S_PLAYED)
+ *value = -1;
+ else {
+ *value = (pp->safety[S_RIGHT_WAY] !=
+ S_UNKNOWN ? 3 : 4);
+ *value *= Numcards[C_STOP] +
+ Numseen[C_GO];
+ if (!pp->mileage || foundend ||
+ onecard(op))
+ *value += 5;
+ if (!cango)
+ *value /= ++badcount;
+ if (op->mileage == 0)
+ *value += 5;
+ if ((card == C_LIMIT &&
+ op->speed == C_LIMIT) ||
+ !op->can_go)
+ *value -= 5;
+ if (cango && pp->safety[S_RIGHT_WAY] !=
+ S_UNKNOWN)
+ *value += 5;
+ }
+ break;
+ case C_GAS_SAFE: case C_DRIVE_SAFE:
+ case C_SPARE_SAFE: case C_RIGHT_WAY:
+ *value = cango ? 0 : 101;
+ break;
+ case C_INIT:
+ *value = 0;
+ break;
+ }
+ }
+ else
+ *value = cango ? 0 : 101;
+ if (card != C_INIT) {
+ if (*value >= curmax) {
+ nummax = i;
+ curmax = *value;
+ }
+ if (*value <= curmin) {
+ nummin = i;
+ curmin = *value;
+ }
+ }
+#ifdef DEBUG
+ if (Debug)
+ mvprintw(i + 6, 2, "%3d %-14s", *value,
+ C_name[pp->hand[i]]);
+#endif
+ value++;
+ }
+ if (!pp->can_go && !isrepair(pp->battle))
+ Numneed[opposite(pp->battle)]++;
+ if (cango) {
+play_it:
+ mvaddstr(MOVE_Y + 1, MOVE_X, "PLAY\n");
+ Movetype = M_PLAY;
+ Card_no = nummax;
+ }
+ else {
+ if (issafety(pp->hand[nummin])) { /* NEVER discard a safety */
+ nummax = nummin;
+ goto play_it;
+ }
+ mvaddstr(MOVE_Y + 1, MOVE_X, "DISCARD\n");
+ Movetype = M_DISCARD;
+ Card_no = nummin;
+ }
+ mvprintw(MOVE_Y + 2, MOVE_X, "%16s", C_name[pp->hand[Card_no]]);
+}
+
+/*
+ * Return true if the given player could conceivably win with his next card.
+ */
+onecard(pp)
+register PLAY *pp;
+{
+ register CARD bat, spd, card;
+
+ bat = pp->battle;
+ spd = pp->speed;
+ card = -1;
+ if (pp->can_go || ((isrepair(bat) || bat == C_STOP || spd == C_LIMIT) &&
+ Numseen[S_RIGHT_WAY] != 0) ||
+ bat >= 0 && Numseen[safety(bat)] != 0)
+ switch (End - pp->mileage) {
+ case 200:
+ if (pp->nummiles[C_200] == 2)
+ return FALSE;
+ card = C_200;
+ /* FALLTHROUGH */
+ case 100:
+ case 75:
+ if (card == -1)
+ card = (End - pp->mileage == 75 ? C_75 : C_100);
+ if (spd == C_LIMIT)
+ return Numseen[S_RIGHT_WAY] == 0;
+ case 50:
+ case 25:
+ if (card == -1)
+ card = (End - pp->mileage == 25 ? C_25 : C_50);
+ return Numseen[card] != Numcards[card];
+ }
+ return FALSE;
+}
+
+canplay(pp, op, card)
+register PLAY *pp, *op;
+register CARD card;
+{
+ switch (card) {
+ case C_200:
+ if (pp->nummiles[C_200] == 2)
+ break;
+ /* FALLTHROUGH */
+ case C_75: case C_100:
+ if (pp->speed == C_LIMIT)
+ break;
+ /* FALLTHROUGH */
+ case C_50:
+ if (pp->mileage + Value[card] > End)
+ break;
+ /* FALLTHROUGH */
+ case C_25:
+ if (pp->can_go)
+ return TRUE;
+ break;
+ case C_EMPTY: case C_FLAT: case C_CRASH:
+ case C_STOP:
+ if (op->can_go && op->safety[safety(card) - S_CONV] != S_PLAYED)
+ return TRUE;
+ break;
+ case C_LIMIT:
+ if (op->speed != C_LIMIT &&
+ op->safety[S_RIGHT_WAY] != S_PLAYED &&
+ op->mileage + 50 < End)
+ return TRUE;
+ break;
+ case C_GAS: case C_SPARE: case C_REPAIRS:
+ if (pp->battle == opposite(card))
+ return TRUE;
+ break;
+ case C_GO:
+ if (!pp->can_go &&
+ (isrepair(pp->battle) || pp->battle == C_STOP))
+ return TRUE;
+ break;
+ case C_END_LIMIT:
+ if (pp->speed == C_LIMIT)
+ return TRUE;
+ }
+ return FALSE;
+}
diff --git a/games/mille/end.c b/games/mille/end.c
new file mode 100644
index 00000000000..a8fb8aa6fa7
--- /dev/null
+++ b/games/mille/end.c
@@ -0,0 +1,154 @@
+/* $NetBSD: end.c,v 1.4 1995/03/24 05:01:30 cgd Exp $ */
+
+/*
+ * Copyright (c) 1982, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)end.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: end.c,v 1.4 1995/03/24 05:01:30 cgd Exp $";
+#endif
+#endif /* not lint */
+
+# include "mille.h"
+
+/*
+ * @(#)end.c 1.1 (Berkeley) 4/1/82
+ */
+
+/*
+ * print out the score as if it was final, and add the totals for
+ * the end-of-games points to the user who deserves it (if any).
+ */
+finalscore(pp)
+reg PLAY *pp; {
+
+ reg int temp, tot, num;
+
+ if (pp->was_finished == Finished)
+ return;
+
+ pp->was_finished = Finished;
+ num = pp - Player;
+ temp = num * 6 + 21 + 1;
+ for (tot = 5; tot <= 9; tot++)
+ mvaddstr(tot, temp, " 0");
+ if (pp->mileage == End) {
+ mvaddstr(5, temp, "40");
+ tot = SC_TRIP;
+ if (pp->nummiles[C_200] == 0) {
+ mvaddstr(6, temp, "30");
+ tot = SC_TRIP + SC_SAFE;
+ }
+ if (Topcard <= Deck) {
+ mvaddstr(7, temp, "30");
+ tot += SC_DELAY;
+ }
+ if (End == 1000) {
+ mvaddstr(8, temp, "20");
+ tot += SC_EXTENSION;
+ }
+ if (Player[other(num)].mileage == 0) {
+ mvaddstr(9, temp, "50");
+ tot += SC_SHUT_OUT;
+ }
+ pp->total += tot;
+ pp->hand_tot += tot;
+ }
+}
+
+# ifdef EXTRAP
+static int Last_tot[2]; /* last tot used for extrapolate */
+
+/*
+ * print out the score as if it was final, and add the totals for
+ * the end-of-games points to the user who deserves it (if any).
+ */
+extrapolate(pp)
+reg PLAY *pp; {
+
+ reg int x, num, tot, count;
+
+ num = pp - Player;
+ tot += SC_TRIP + SC_DELAY + SC_EXT;
+ x = num * 6 + 21 + 3;
+ for (tot = 5; tot <= 9; tot++)
+ mvaddch(tot, x, '0');
+ x -= 2;
+ pp = &Player[other(num)];
+ for (count = 0, tot = 0; tot < NUM_SAFE; tot++)
+ if (pp->safety[tot] != S_PLAYED)
+ count += SC_SAFE;
+ mvprintw(3, x, "%3d", count);
+ tot += count;
+ if (count == 400) {
+ mvaddstr(4, x, "30");
+ tot += SC_ALL_SAFE;
+ }
+ pp = &Player[num];
+ for (count = 0, tot = 0; tot < NUM_SAFE; tot++)
+ if (pp->safety[tot] != S_PLAYED)
+ count += SC_COUP / 10;
+ mvprintw(4, x - 1, "%3d", count);
+ tot += count;
+ tot += 1000 - pp->mileage;
+ mvaddstr(5, x, "40");
+ mvaddstr(7, x, "30");
+ mvaddstr(8, x, "20");
+ if (pp->nummiles[C_200] == 0) {
+ mvaddstr(6, x, "30");
+ tot = SC_TRIP + SC_SAFE;
+ }
+ if (Player[other(num)].mileage == 0) {
+ mvaddstr(9, x, "50");
+ tot += SC_SHUT_OUT;
+ }
+ pp->total += tot;
+ pp->hand_tot += tot;
+ Last_tot[num] = tot;
+}
+
+undoex() {
+
+ reg PLAY *pp;
+ reg int i;
+
+ i = 0;
+ for (pp = Player; pp < &Player[2]; pp++) {
+ pp->total -= Last_tot[i];
+ pp->hand_tot -= Last_tot[i++];
+ }
+}
+# endif
+
diff --git a/games/mille/extern.c b/games/mille/extern.c
new file mode 100644
index 00000000000..927b7f23461
--- /dev/null
+++ b/games/mille/extern.c
@@ -0,0 +1,178 @@
+/* $NetBSD: extern.c,v 1.4 1995/03/24 05:01:36 cgd Exp $ */
+
+/*
+ * Copyright (c) 1982, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)extern.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: extern.c,v 1.4 1995/03/24 05:01:36 cgd Exp $";
+#endif
+#endif /* not lint */
+
+# include "mille.h"
+
+/*
+ * @(#)extern.c 1.1 (Berkeley) 4/1/82
+ */
+
+bool Debug, /* set if debugging code on */
+ Finished, /* set if current hand is finished */
+ Next, /* set if changing players */
+ On_exit, /* set if game saved on exiting */
+ Order, /* set if hand should be sorted */
+ Saved; /* set if game just saved */
+
+char *C_fmt = "%-18.18s", /* format for printing cards */
+ *Fromfile = NULL, /* startup file for game */
+ Initstr[100], /* initial string for error field */
+ *_cn[NUM_CARDS] = { /* Card name buffer */
+ "",
+ "25",
+ "50",
+ "75",
+ "100",
+ "200",
+ "Out of Gas",
+ "Flat Tire",
+ "Accident",
+ "Stop",
+ "Speed Limit",
+ "Gasoline",
+ "Spare Tire",
+ "Repairs",
+ "Go",
+ "End of Limit",
+ "Extra Tank",
+ "Puncture Proof",
+ "Driving Ace",
+ "Right of Way"
+ },
+ **C_name = &_cn[1]; /* Card names */
+
+int Card_no, /* Card number for current move */
+ End, /* End value for current hand */
+ Handstart = COMP, /* Player who starts hand */
+ Movetype, /* Current move type */
+ Play, /* Current player */
+ Numgos, /* Number of Go cards used by computer */
+ Window = W_SMALL, /* Current window wanted */
+ Numseen[NUM_CARDS], /* Number of cards seen in current hand */
+ Value[NUM_MILES] = { /* Value of mileage cards */
+ 25, 50, 75, 100, 200
+ },
+ Numcards[NUM_CARDS] = { /* Number of cards in deck */
+ 10, /* C_25 */
+ 10, /* C_50 */
+ 10, /* C_75 */
+ 12, /* C_100 */
+ 4, /* C_200 */
+ 2, /* C_EMPTY */
+ 2, /* C_FLAT */
+ 2, /* C_CRASH */
+ 4, /* C_STOP */
+ 3, /* C_LIMIT */
+ 6, /* C_GAS */
+ 6, /* C_SPARE */
+ 6, /* C_REPAIRS */
+ 14, /* C_GO */
+ 6, /* C_END_LIMIT */
+ 1, /* C_GAS_SAFE */
+ 1, /* C_SPARE_SAFE */
+ 1, /* C_DRIVE_SAFE */
+ 1, /* C_RIGHT_WAY */
+ 0 /* C_INIT */
+ },
+ Numneed[NUM_CARDS] = { /* number of cards needed per hand */
+ 0, /* C_25 */
+ 0, /* C_50 */
+ 0, /* C_75 */
+ 0, /* C_100 */
+ 0, /* C_200 */
+ 2, /* C_EMPTY */
+ 2, /* C_FLAT */
+ 2, /* C_CRASH */
+ 4, /* C_STOP */
+ 3, /* C_LIMIT */
+ 2, /* C_GAS */
+ 2, /* C_SPARE */
+ 2, /* C_REPAIRS */
+ 10, /* C_GO */
+ 3, /* C_END_LIMIT */
+ 1, /* C_GAS_SAFE */
+ 1, /* C_SPARE_SAFE */
+ 1, /* C_DRIVE_SAFE */
+ 1, /* C_RIGHT_WAY */
+ 0 /* C_INIT */
+ };
+
+CARD Discard, /* Top of discard pile */
+ Sh_discard, /* Last discard card shown */
+ *Topcard, /* Pointer to next card to be picked */
+ Opposite[NUM_CARDS] = { /* Opposites of each card */
+ C_25, C_50, C_75, C_100, C_200, C_GAS, C_SPARE,
+ C_REPAIRS, C_GO, C_END_LIMIT, C_EMPTY, C_FLAT, C_CRASH,
+ C_STOP, C_LIMIT, C_EMPTY, C_FLAT, C_CRASH, C_STOP, C_INIT
+ },
+ Deck[DECK_SZ] = { /* Current deck */
+ C_25, C_25, C_25, C_25, C_25, C_25, C_25, C_25, C_25, C_25,
+ C_50, C_50, C_50, C_50, C_50, C_50, C_50, C_50, C_50, C_50,
+ C_75, C_75, C_75, C_75, C_75, C_75, C_75, C_75, C_75, C_75,
+ C_100, C_100, C_100, C_100, C_100, C_100, C_100, C_100, C_100,
+ C_100, C_100, C_100,
+ C_200, C_200, C_200, C_200,
+ C_EMPTY, C_EMPTY,
+ C_FLAT, C_FLAT,
+ C_CRASH, C_CRASH,
+ C_STOP, C_STOP, C_STOP, C_STOP,
+ C_LIMIT, C_LIMIT, C_LIMIT,
+ C_GAS, C_GAS, C_GAS, C_GAS, C_GAS, C_GAS,
+ C_SPARE, C_SPARE, C_SPARE, C_SPARE, C_SPARE, C_SPARE,
+ C_REPAIRS, C_REPAIRS, C_REPAIRS, C_REPAIRS, C_REPAIRS,
+ C_REPAIRS,
+ C_END_LIMIT, C_END_LIMIT, C_END_LIMIT, C_END_LIMIT, C_END_LIMIT,
+ C_END_LIMIT,
+ C_GO, C_GO, C_GO, C_GO, C_GO, C_GO, C_GO, C_GO, C_GO, C_GO,
+ C_GO, C_GO, C_GO, C_GO,
+ C_GAS_SAFE, C_SPARE_SAFE, C_DRIVE_SAFE, C_RIGHT_WAY
+ };
+
+FILE *outf;
+
+PLAY Player[2]; /* Player descriptions */
+
+WINDOW *Board, /* Playing field screen */
+ *Miles, /* Mileage screen */
+ *Score; /* Score screen */
+
diff --git a/games/mille/init.c b/games/mille/init.c
new file mode 100644
index 00000000000..368862ad8e4
--- /dev/null
+++ b/games/mille/init.c
@@ -0,0 +1,256 @@
+/* $NetBSD: init.c,v 1.5 1995/03/24 05:01:40 cgd Exp $ */
+
+/*
+ * Copyright (c) 1982, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)init.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: init.c,v 1.5 1995/03/24 05:01:40 cgd Exp $";
+#endif
+#endif /* not lint */
+
+# include "mille.h"
+
+/*
+ * @(#)init.c 1.1 (Berkeley) 4/1/82
+ */
+
+init() {
+
+ reg PLAY *pp;
+ reg int i, j;
+ reg CARD card;
+
+ bzero(Numseen, sizeof Numseen);
+ Numgos = 0;
+
+ for (i = 0; i < 2; i++) {
+ pp = &Player[i];
+ pp->hand[0] = C_INIT;
+ for (j = 0; j < NUM_SAFE; j++) {
+ pp->safety[j] = S_UNKNOWN;
+ pp->coups[j] = FALSE;
+ }
+ for (j = 1; j < HAND_SZ; j++) {
+ pp->hand[j] = *--Topcard;
+ if (i == COMP) {
+ account(card = *Topcard);
+ if (issafety(card))
+ pp->safety[card - S_CONV] = S_IN_HAND;
+ }
+ }
+ pp->mileage = 0;
+ pp->hand_tot = 0;
+ pp->safescore = 0;
+ pp->coupscore = 0;
+ pp->can_go = FALSE;
+ pp->speed = C_INIT;
+ pp->battle = C_INIT;
+ pp->new_speed = FALSE;
+ pp->new_battle = FALSE;
+ for (j = 0; j < NUM_MILES; j++)
+ pp->nummiles[j] = 0;
+ }
+ if (Order)
+ sort(Player[PLAYER].hand);
+ Discard = C_INIT;
+ Finished = FALSE;
+ End = 700;
+}
+
+shuffle() {
+
+ reg int i, r;
+ reg CARD temp;
+
+ for (i = 0; i < DECK_SZ; i++) {
+ r = roll(1, DECK_SZ) - 1;
+ if (r < 0 || r > DECK_SZ - 1) {
+ fprintf(stderr, "shuffle: card no. error: %d\n", r);
+ die(1);
+ }
+ temp = Deck[r];
+ Deck[r] = Deck[i];
+ Deck[i] = temp;
+ }
+ Topcard = &Deck[DECK_SZ];
+}
+
+newboard() {
+
+ register int i;
+ register PLAY *pp;
+ static int first = TRUE;
+
+ if (first) {
+ werase(Board);
+ werase(Score);
+ mvaddstr(5, 0, "--HAND--");
+ mvaddch(6, 0, 'P');
+ mvaddch(7, 0, '1');
+ mvaddch(8, 0, '2');
+ mvaddch(9, 0, '3');
+ mvaddch(10, 0, '4');
+ mvaddch(11, 0, '5');
+ mvaddch(12, 0, '6');
+ mvaddstr(13, 0, "--BATTLE--");
+ mvaddstr(15, 0, "--SPEED--");
+ mvaddstr(5, 20, "--DECK--");
+ mvaddstr(7, 20, "--DISCARD--");
+ mvaddstr(13, 20, "--BATTLE--");
+ mvaddstr(15, 20, "--SPEED--");
+ mvwaddstr(Miles, 0, 0, "--MILEAGE--");
+ mvwaddstr(Miles, 0, 41, "--MILEAGE--");
+ Sh_discard = -1;
+ for (pp = Player; pp <= &Player[COMP]; pp++) {
+ for (i = 0; i < HAND_SZ; i++)
+ pp->sh_hand[i] = -1;
+ pp->sh_battle = -1;
+ pp->sh_speed = -1;
+ pp->sh_mileage = -1;
+ }
+ first = FALSE;
+ }
+ else {
+ for (i = 0; i < 5; i++) {
+ move(i, 0);
+ clrtoeol();
+ }
+ wmove(Miles, 1, 0);
+ wclrtobot(Miles);
+ wmove(Board, MOVE_Y + 1, MOVE_X);
+ wclrtoeol(Board);
+ wmove(Board, MOVE_Y + 2, MOVE_X);
+ wclrtoeol(Board);
+ }
+ Sh_discard = -1;
+ for (pp = Player; pp <= &Player[COMP]; pp++) {
+ for (i = 0; i < NUM_SAFE; i++)
+ pp->sh_safety[i] = FALSE;
+ for (i = 0; i < NUM_MILES; i++)
+ pp->sh_nummiles[i] = 0;
+ pp->sh_safescore = -1;
+ }
+ newscore();
+}
+
+newscore() {
+
+ reg int i, new;
+ register PLAY *pp;
+ static int was_full = -1;
+ static int last_win = -1;
+
+ if (was_full < 0)
+ was_full = (Window != W_FULL);
+ stdscr = Score;
+ move(0, 22);
+ new = FALSE;
+ if (inch() != 'Y') {
+ erase();
+ mvaddstr(0, 22, "You Comp Value");
+ mvaddstr(1, 2, "Milestones Played");
+ mvaddstr(2, 8, "Each Safety");
+ mvaddstr(3, 5, "All 4 Safeties");
+ mvaddstr(4, 3, "Each Coup Fourre");
+ mvaddstr(2, 37, "100");
+ mvaddstr(3, 37, "300");
+ mvaddstr(4, 37, "300");
+ new = TRUE;
+ }
+ else if ((Window == W_FULL || Finished) ^ was_full) {
+ move(5, 1);
+ clrtobot();
+ new = TRUE;
+ }
+ else if (Window != last_win)
+ new = TRUE;
+ if (new) {
+ for (i = 0; i < SCORE_Y; i++)
+ mvaddch(i, 0, '|');
+ move(SCORE_Y - 1, 1);
+ for (i = 0; i < SCORE_X; i++)
+ addch('_');
+ for (pp = Player; pp <= &Player[COMP]; pp++) {
+ pp->sh_hand_tot = -1;
+ pp->sh_total = -1;
+ pp->sh_games = -1;
+ pp->sh_safescore = -1;
+ }
+ }
+ Player[PLAYER].was_finished = !Finished;
+ Player[COMP].was_finished = !Finished;
+ if (Window == W_FULL || Finished) {
+ if (!was_full || new) {
+ mvaddstr(5, 5, "Trip Completed");
+ mvaddstr(6, 10, "Safe Trip");
+ mvaddstr(7, 5, "Delayed Action");
+ mvaddstr(8, 10, "Extension");
+ mvaddstr(9, 11, "Shut-Out");
+ mvaddstr(10, 21, "---- ---- -----");
+ mvaddstr(11, 9, "Hand Total");
+ mvaddstr(12, 20, "----- -----");
+ mvaddstr(13, 6, "Overall Total");
+ mvaddstr(14, 15, "Games");
+ mvaddstr(5, 37, "400");
+ mvaddstr(6, 37, "300");
+ mvaddstr(7, 37, "300");
+ mvaddstr(8, 37, "200");
+ mvaddstr(9, 37, "500");
+ }
+ }
+ else
+ if (was_full || new) {
+ mvaddstr(5, 21, "---- ---- -----");
+ mvaddstr(6, 9, "Hand Total");
+ mvaddstr(7, 20, "----- -----");
+ mvaddstr(8, 6, "Overall Total");
+ mvaddstr(9, 15, "Games");
+ mvaddstr(11, 2, "p: pick");
+ mvaddstr(12, 2, "u: use #");
+ mvaddstr(13, 2, "d: discard #");
+ mvaddstr(14, 2, "w: toggle window");
+ mvaddstr(11, 21, "q: quit");
+ if (!Order)
+ mvaddstr(12, 21, "o: order hand");
+ else
+ mvaddstr(12, 21, "o: stop ordering");
+ mvaddstr(13, 21, "s: save");
+ mvaddstr(14, 21, "r: reprint");
+ }
+ stdscr = Board;
+ was_full = (Window == W_FULL || Finished);
+ last_win = Window;
+}
diff --git a/games/mille/mille.6 b/games/mille/mille.6
new file mode 100644
index 00000000000..02ce56c4517
--- /dev/null
+++ b/games/mille/mille.6
@@ -0,0 +1,381 @@
+.\" $NetBSD: mille.6,v 1.4 1995/03/24 05:01:45 cgd Exp $
+.\"
+.\" Copyright (c) 1983, 1993
+.\" The Regents of the University of California. All rights reserved.
+.\"
+.\" 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. All advertising materials mentioning features or use of this software
+.\" must display the following acknowledgement:
+.\" This product includes software developed by the University of
+.\" California, Berkeley and its contributors.
+.\" 4. 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.
+.\"
+.\" @(#)mille.6 8.2 (Berkeley) 12/30/93
+.\"
+.TH MILLE 6 "December 30, 1993"
+.UC 4
+.SH NAME
+mille \- play Mille Bornes
+.SH SYNOPSIS
+.B /usr/games/mille
+[ file ]
+.SH DESCRIPTION
+.I Mille
+plays a two-handed game reminiscent of
+the Parker Brother's game of Mille Bornes with you.
+The rules are described below.
+If a file name is given on the command line,
+the game saved in that file is started.
+.PP
+When a game is started up,
+the bottom of the score window will contain a list of commands.
+They are:
+.IP P
+Pick a card from the deck.
+This card is placed in the `P' slot in your hand.
+.IP D
+Discard a card from your hand.
+To indicate which card, type the number of the card in the hand
+(or \*(lqP\*(rq for the just-picked card) followed by a <RETURN> or <SPACE>.
+The <RETURN or <SPACE> is required to allow recovery from typos
+which can be very expensive, like discarding safeties.
+.IP U
+Use a card.
+The card is again indicated by its number, followed by a <RETURN> or <SPACE>.
+.IP O
+Toggle ordering the hand.
+By default off, if turned on it will sort the cards in your hand appropriately.
+This is not recommended for the impatient on slow terminals.
+.IP Q
+Quit the game.
+This will ask for confirmation, just to be sure.
+Hitting <DELETE> (or <RUBOUT>) is equivalent.
+.IP S
+Save the game in a file.
+If the game was started from a file,
+you will be given an opportunity to save it on the same file.
+If you don't wish to, or you did not start from a file,
+you will be asked for the file name.
+If you type a <RETURN> without a name,
+the save will be terminated and the game resumed.
+.IP R
+Redraw the screen from scratch.
+The command ^L (control `L') will also work.
+.IP W
+Toggle window type.
+This switches the score window between the startup window
+(with all the command names) and the end-of-game window.
+Using the end-of-game window
+saves time by eliminating the switch at the end of the game
+to show the final score.
+Recommended for hackers and other miscreants.
+.PP
+If you make a mistake, an error message will be printed
+on the last line of the score window, and a bell will beep.
+.PP
+At the end of each hand or game,
+you will be asked if you wish to play another.
+If not, it will ask you if you want to save the game.
+If you do, and the save is unsuccessful,
+play will be resumed as if you had said you wanted to play another hand/game.
+This allows you to use the
+.RB \*(lq S \*(rq
+command to reattempt the save.
+.SH AUTHOR
+Ken Arnold
+.br
+(The game itself is a product of Parker Brothers, Inc.)
+.SH "SEE ALSO"
+curses(3X),
+.I "Screen Updating and Cursor Movement Optimization:"
+.IR "A Library Package" ,
+Ken Arnold
+.SH CARDS
+.PP
+Here is some useful information.
+The number in parentheses after the card name
+is the number of that card in the deck:
+.sp
+.nf
+.ne 10
+.ta \w'Speed Limit (3)'u+3n \w'Speed Limit (3)'u+\w'End of Limit (6)'u+6n
+Hazard Repair Safety
+.sp
+Out of Gas (2) Gasoline (6) Extra Tank (1)
+Flat Tire (2) Spare Tire (6) Puncture Proof (1)
+Accident (2) Repairs (6) Driving Ace (1)
+Stop (4) Go (14) Right of Way (1)
+Speed Limit (3) End of Limit (6)
+.sp
+.ce
+25 \- (10), 50 \- (10), 75 \- (10), 100 \- (12), 200 \- (4)
+.sp
+.fi
+.DT
+.SH RULES
+.PP
+.BR Object :
+The point of this game is to get a total of 5000 points in several hands.
+Each hand is a race to put down exactly 700 miles before your opponent does.
+Beyond the points gained by putting down milestones,
+there are several other ways of making points.
+.PP
+.BR Overview :
+The game is played with a deck of 101 cards.
+.I Distance
+cards represent a number of miles traveled.
+They come in denominations of 25, 50, 75, 100, and 200.
+When one is played,
+it adds that many miles to the player's trip so far this hand.
+.I Hazard
+cards are used to prevent your opponent from putting down Distance cards.
+They can only be played if your opponent has a
+.I Go
+card on top of the Battle pile.
+The cards are
+.IR "Out of Gas" ,
+.IR "Accident" ,
+.IR "Flat Tire" ,
+.IR "Speed Limit" ,
+and
+.IR "Stop" .
+.I Remedy
+cards fix problems caused by Hazard cards played on you by your opponent.
+The cards are
+.IR "Gasoline" ,
+.IR "Repairs" ,
+.IR "Spare Tire" ,
+.IR "End of Limit" ,
+and
+.IR "Go" .
+.I Safety
+cards prevent your opponent from putting specific Hazard cards on you
+in the first place.
+They are
+.IR "Extra Tank" ,
+.IR "Driving Ace" ,
+.IR "Puncture Proof" ,
+and
+.IR "Right of Way" ,
+and there are only one of each in the deck.
+.PP
+.BR "Board Layout" :
+The board is split into several areas.
+From top to bottom, they are:
+.B "SAFETY AREA"
+(unlabeled): This is where the safeties will be placed as they are played.
+.BR HAND :
+These are the cards in your hand.
+.BR BATTLE :
+This is the Battle pile.
+All the Hazard and Remedy Cards are played here, except the
+.I "Speed Limit"
+and
+.I "End of Limit"
+cards. Only the top card is displayed, as it is the only effective one.
+.BR SPEED :
+The Speed pile. The
+.I "Speed Limit"
+and
+.I "End of Limit"
+cards are played here
+to control the speed at which the player is allowed to put down miles.
+.BR MILEAGE :
+Miles are placed here.
+The total of the numbers shown here is the distance traveled so far.
+.PP
+.BR Play :
+The first pick alternates between the two players.
+Each turn usually starts with a pick from the deck.
+The player then plays a card, or if this is not possible or desirable,
+discards one. Normally, a play or discard of a single card
+constitutes a turn. If the card played is a safety, however,
+the same player takes another turn immediately.
+.PP
+This repeats until one of the players reaches 700 points or the deck runs out.
+If someone reaches 700, they have the option of going for an
+.IR Extension ,
+which means that the play continues until someone reaches 1000 miles.
+.PP
+.BR "Hazard and Remedy Cards" :
+Hazard Cards are played on your opponent's Battle and Speed piles.
+Remedy Cards are used for undoing the effects of your opponent's nastiness.
+.PP
+.RB "\ \ \ \ " Go
+(Green Light)
+must be the top card on your Battle pile for you to play any mileage,
+unless you have played the
+.I "Right of Way"
+card (see below).
+.br
+.RB "\ \ \ \ " Stop
+is played on your opponent's
+.I Go
+card to prevent them from playing mileage until they play a
+.I Go
+card.
+.br
+.RB "\ \ \ \ " "Speed Limit"
+is played on your opponent's Speed pile.
+Until they play an
+.I "End of Limit"
+they can only play 25 or 50 mile cards, presuming their
+.I Go
+card allows them to do even that.
+.br
+.RB "\ \ \ \ " "End of Limit"
+is played on your Speed pile to nullify a
+.I "Speed Limit"
+played by your opponent.
+.br
+.RB "\ \ \ \ " "Out of Gas"
+is played on your opponent's
+.I Go
+card. They must then play a
+.I Gasoline
+card, and then a
+.I Go
+card before they can play any more mileage.
+.br
+.RB "\ \ \ \ " "Flat Tire"
+is played on your opponent's
+.I Go
+card. They must then play a
+.I "Spare Tire"
+card, and then a
+.I Go
+card before they can play any more mileage.
+.br
+.RB "\ \ \ \ " "Accident"
+is played on your opponent's
+.I Go
+card. They must then play a
+.I Repairs
+card, and then a
+.I Go
+card before they can play any more mileage.
+.br
+.PP
+.BR "Safety Cards" :
+Safety cards prevent your opponent
+from playing the corresponding Hazard cards on you for the rest of the hand.
+It cancels an attack in progress, and
+.IR "always entitles the player to an extra turn" .
+.br
+.RB "\ \ \ \ " "Right of Way"
+prevents your opponent from playing both
+.I Stop
+and
+.I "Speed Limit"
+cards on you. It also acts as a permanent
+.I Go
+card for the rest of the hand, so you can play mileage
+as long as there is not a Hazard card on top of your Battle pile.
+In this case only, your opponent can play Hazard cards directly on a Remedy card
+other than a Go card.
+.br
+.RB "\ \ \ \ " "Extra Tank"
+When played, your opponent cannot play an
+.I "Out of Gas"
+on your Battle Pile.
+.br
+.RB "\ \ \ \ " "Puncture Proof"
+When played, your opponent cannot play a
+.I "Flat Tire"
+on your Battle Pile.
+.br
+.RB "\ \ \ \ " "Driving Ace"
+When played, your opponent cannot play an
+.I Accident
+on your Battle Pile.
+.PP
+.BR "Distance Cards" :
+Distance cards are played when you have a
+.I Go
+card on your Battle pile,
+or a Right of Way in your Safety area and are not stopped by a Hazard Card.
+They can be played in any combination that totals exactly 700 miles,
+except that
+.IR "you cannot play more than two 200 mile cards in one hand" .
+A hand ends whenever one player gets exactly 700 miles or the deck runs out.
+In that case, play continues until neither someone reaches 700,
+or neither player can use any cards in their hand.
+If the trip is completed after the deck runs out, this is called
+.IR "Delayed Action" .
+.PP
+.BR "Coup Fourr\o'\(aae'" :
+This is a French fencing term for a counter-thrust move as part of a parry
+to an opponent's attack.
+In current French colloquial language it means a sneaky, underhanded blow.
+In Mille Bornes, it is used as follows:
+If an opponent plays a Hazard card,
+and you have the corresponding Safety in your hand,
+you play it immediately, even
+.I before
+you draw. This immediately removes the Hazard card from your Battle pile,
+and protects you from that card for the rest of the game. This
+gives you more points (see \*(lqScoring\*(rq below).
+.PP
+.BR Scoring :
+Scores are totaled at the end of each hand,
+whether or not anyone completed the trip.
+The terms used in the Score window have the following meanings:
+.br
+.RB "\ \ \ \ " "Milestones Played" :
+Each player scores as many miles as they played before the trip ended.
+.br
+.RB "\ \ \ \ " "Each Safety" :
+100 points for each safety in the Safety area.
+.br
+.RB "\ \ \ \ " "All 4 Safeties" :
+300 points if all four safeties are played.
+.br
+.RB "\ \ \ \ " "Each Coup Fourr\o'\(aae'" :
+300 points for each Coup Fourr\o'\(aae' accomplished.
+.PP
+The following bonus scores can apply only to the winning player.
+.br
+.RB "\ \ \ \ " "Trip Completed" :
+400 points bonus for completing the trip to 700 or 1000.
+.br
+.RB "\ \ \ \ " "Safe Trip" :
+300 points bonus for completing the trip without using any 200 mile cards.
+.br
+.RB "\ \ \ \ " "Delayed Action" :
+300 points bonus for finishing after the deck was exhausted.
+.br
+.RB "\ \ \ \ " "Extension" :
+200 points bonus for completing a 1000 mile trip.
+.br
+.RB "\ \ \ \ " "Shut-Out" :
+500 points bonus for completing the trip
+before your opponent played any mileage cards.
+.PP
+Running totals are also kept for the current score for each player
+for the hand
+.RB ( "Hand Total" ),
+the game
+.RB ( "Overall Total" ),
+and number of games won
+.RB ( Games ).
diff --git a/games/mille/mille.c b/games/mille/mille.c
new file mode 100644
index 00000000000..cc4a6ac8c26
--- /dev/null
+++ b/games/mille/mille.c
@@ -0,0 +1,169 @@
+/* $NetBSD: mille.c,v 1.4 1995/03/24 05:01:48 cgd Exp $ */
+
+/*
+ * Copyright (c) 1982, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+static char copyright[] =
+"@(#) Copyright (c) 1982, 1993\n\
+ The Regents of the University of California. All rights reserved.\n";
+#endif /* not lint */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)mille.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: mille.c,v 1.4 1995/03/24 05:01:48 cgd Exp $";
+#endif
+#endif /* not lint */
+
+# include "mille.h"
+# include <signal.h>
+# ifdef attron
+# include <term.h>
+# endif attron
+
+/*
+ * @(#)mille.c 1.3 (Berkeley) 5/10/83
+ */
+
+void rub();
+
+main(ac, av)
+reg int ac;
+reg char *av[]; {
+
+ reg bool restore;
+
+ /* run as the user */
+ setuid(getuid());
+
+ if (strcmp(av[0], "a.out") == 0) {
+ outf = fopen("q", "w");
+ setbuf(outf, (char *)NULL);
+ Debug = TRUE;
+ }
+ restore = FALSE;
+ switch (ac) {
+ case 2:
+ rest_f(av[1]);
+ restore = TRUE;
+ case 1:
+ break;
+ default:
+ printf("usage: milles [ restore_file ]\n");
+ exit(-1);
+ /* NOTREACHED */
+ }
+ Play = PLAYER;
+ initscr();
+ delwin(stdscr);
+ stdscr = Board = newwin(BOARD_Y, BOARD_X, 0, 0);
+ Score = newwin(SCORE_Y, SCORE_X, 0, 40);
+ Miles = newwin(MILES_Y, MILES_X, 17, 0);
+#ifdef attron
+ idlok(Board, TRUE);
+ idlok(Score, TRUE);
+ idlok(Miles, TRUE);
+#endif
+ leaveok(Score, TRUE);
+ leaveok(Miles, TRUE);
+ clearok(curscr, TRUE);
+# ifndef PROF
+ srandom(getpid());
+# else
+ srandom(0);
+# endif
+ crmode();
+ noecho();
+ signal(SIGINT, rub);
+ for (;;) {
+ if (!restore || (Player[PLAYER].total >= 5000
+ || Player[COMP].total >= 5000)) {
+ if (Player[COMP].total < Player[PLAYER].total)
+ Player[PLAYER].games++;
+ else if (Player[COMP].total > Player[PLAYER].total)
+ Player[COMP].games++;
+ Player[COMP].total = 0;
+ Player[PLAYER].total = 0;
+ }
+ do {
+ if (!restore)
+ Handstart = Play = other(Handstart);
+ if (!restore || On_exit) {
+ shuffle();
+ init();
+ }
+ newboard();
+ if (restore)
+ mvwaddstr(Score, ERR_Y, ERR_X, Initstr);
+ prboard();
+ do {
+ domove();
+ if (Finished)
+ newscore();
+ prboard();
+ } while (!Finished);
+ check_more();
+ restore = On_exit = FALSE;
+ } while (Player[COMP].total < 5000
+ && Player[PLAYER].total < 5000);
+ }
+}
+
+/*
+ * Routine to trap rubouts, and make sure they really want to
+ * quit.
+ */
+void
+rub() {
+
+ (void)signal(SIGINT, SIG_IGN);
+ if (getyn(REALLYPROMPT))
+ die(0);
+ (void)signal(SIGINT, rub);
+}
+
+/*
+ * Time to go beddy-by
+ */
+die(code)
+int code; {
+
+ (void)signal(SIGINT, SIG_IGN);
+ if (outf)
+ fflush(outf);
+ mvcur(0, COLS - 1, LINES - 1, 0);
+ endwin();
+ exit(code);
+}
diff --git a/games/mille/mille.h b/games/mille/mille.h
new file mode 100644
index 00000000000..1d82942c19e
--- /dev/null
+++ b/games/mille/mille.h
@@ -0,0 +1,231 @@
+/* $NetBSD: mille.h,v 1.5 1995/03/24 05:01:51 cgd Exp $ */
+
+/*
+ * Copyright (c) 1982, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ *
+ * @(#)mille.h 8.1 (Berkeley) 5/31/93
+ */
+
+# include <sys/types.h>
+# include <ctype.h>
+# include <curses.h>
+# include <termios.h>
+# include <string.h>
+
+/*
+ * @(#)mille.h 1.1 (Berkeley) 4/1/82
+ */
+
+/*
+ * Miscellaneous constants
+ */
+
+# define unsgn unsigned
+# define CARD short
+
+# define HAND_SZ 7 /* number of cards in a hand */
+# define DECK_SZ 101 /* number of cards in decks */
+# define NUM_SAFE 4 /* number of saftey cards */
+# define NUM_MILES 5 /* number of milestones types */
+# define NUM_CARDS 20 /* number of types of cards */
+# define BOARD_Y 17 /* size of board screen */
+# define BOARD_X 40
+# define MILES_Y 7 /* size of mileage screen */
+# define MILES_X 80
+# define SCORE_Y 17 /* size of score screen */
+# define SCORE_X 40
+# define MOVE_Y 10 /* Where to print move prompt */
+# define MOVE_X 20
+# define ERR_Y 15 /* Where to print errors */
+# define ERR_X 5
+# define EXT_Y 4 /* Where to put Extension */
+# define EXT_X 9
+
+# define PLAYER 0
+# define COMP 1
+
+# define W_SMALL 0 /* Small (initial) window */
+# define W_FULL 1 /* Full (final) window */
+
+/*
+ * Move types
+ */
+
+# define M_DISCARD 0
+# define M_DRAW 1
+# define M_PLAY 2
+# define M_ORDER 3
+
+/*
+ * Scores
+ */
+
+# define SC_SAFETY 100
+# define SC_ALL_SAFE 300
+# define SC_COUP 300
+# define SC_TRIP 400
+# define SC_SAFE 300
+# define SC_DELAY 300
+# define SC_EXTENSION 200
+# define SC_SHUT_OUT 500
+
+/*
+ * safety descriptions
+ */
+
+# define S_UNKNOWN 0 /* location of safety unknown */
+# define S_IN_HAND 1 /* safety in player's hand */
+# define S_PLAYED 2 /* safety has been played */
+# define S_GAS_SAFE 0 /* Gas safety card index */
+# define S_SPARE_SAFE 1 /* Tire safety card index */
+# define S_DRIVE_SAFE 2 /* Driveing safety card index */
+# define S_RIGHT_WAY 3 /* Right-of-Way card index */
+# define S_CONV 15 /* conversion from C_ to S_ */
+
+/*
+ * card numbers
+ */
+
+# define C_INIT -1
+# define C_25 0
+# define C_50 1
+# define C_75 2
+# define C_100 3
+# define C_200 4
+# define C_EMPTY 5
+# define C_FLAT 6
+# define C_CRASH 7
+# define C_STOP 8
+# define C_LIMIT 9
+# define C_GAS 10
+# define C_SPARE 11
+# define C_REPAIRS 12
+# define C_GO 13
+# define C_END_LIMIT 14
+# define C_GAS_SAFE 15
+# define C_SPARE_SAFE 16
+# define C_DRIVE_SAFE 17
+# define C_RIGHT_WAY 18
+
+/*
+ * prompt types
+ */
+
+# define MOVEPROMPT 0
+# define REALLYPROMPT 1
+# define ANOTHERHANDPROMPT 2
+# define ANOTHERGAMEPROMPT 3
+# define SAVEGAMEPROMPT 4
+# define SAMEFILEPROMPT 5
+# define FILEPROMPT 6
+# define EXTENSIONPROMPT 7
+# define OVERWRITEFILEPROMPT 8
+
+# ifdef SYSV
+# define srandom(x) srand(x)
+# define random() rand()
+
+# ifndef attron
+# define erasechar() _tty.c_cc[VERASE]
+# define killchar() _tty.c_cc[VKILL]
+# endif
+# else
+# ifndef erasechar
+# define erasechar() _tty.sg_erase
+# define killchar() _tty.sg_kill
+# endif
+# endif SYSV
+
+typedef struct {
+ bool coups[NUM_SAFE];
+ bool can_go;
+ bool new_battle;
+ bool new_speed;
+ short safety[NUM_SAFE];
+ short sh_safety[NUM_SAFE];
+ short nummiles[NUM_MILES];
+ short sh_nummiles[NUM_MILES];
+ CARD hand[HAND_SZ];
+ CARD sh_hand[HAND_SZ];
+ CARD battle;
+ CARD sh_battle;
+ CARD speed;
+ CARD sh_speed;
+ int mileage;
+ int sh_mileage;
+ int hand_tot;
+ int sh_hand_tot;
+ int safescore;
+ int sh_safescore;
+ int coupscore;
+ int total;
+ int sh_total;
+ int games;
+ int sh_games;
+ int was_finished;
+} PLAY;
+
+/*
+ * macros
+ */
+
+# define other(x) (1 - x)
+# define nextplay() (Play = other(Play))
+# define nextwin(x) (1 - x)
+# define opposite(x) (Opposite[x])
+# define issafety(x) (x >= C_GAS_SAFE)
+
+/*
+ * externals
+ */
+
+extern bool Debug, Finished, Next, On_exit, Order, Saved;
+
+extern char *C_fmt, **C_name, *Fromfile, Initstr[];
+
+extern int Card_no, End, Handstart, Movetype, Numcards[], Numgos,
+ Numneed[], Numseen[NUM_CARDS], Play, Value[], Window;
+
+extern CARD Deck[DECK_SZ], Discard, Opposite[NUM_CARDS], Sh_discard,
+ *Topcard;
+
+extern FILE *outf;
+
+extern PLAY Player[2];
+
+extern WINDOW *Board, *Miles, *Score;
+
+/*
+ * functions
+ */
+
+CARD getcard();
diff --git a/games/mille/misc.c b/games/mille/misc.c
new file mode 100644
index 00000000000..8dafc778b66
--- /dev/null
+++ b/games/mille/misc.c
@@ -0,0 +1,259 @@
+/* $NetBSD: misc.c,v 1.4 1995/03/24 05:01:54 cgd Exp $ */
+
+/*
+ * Copyright (c) 1983, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)misc.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: misc.c,v 1.4 1995/03/24 05:01:54 cgd Exp $";
+#endif
+#endif /* not lint */
+
+#include <sys/file.h>
+#include <termios.h>
+
+#include "mille.h"
+#ifndef unctrl
+#include "unctrl.h"
+#endif
+
+
+# ifdef attron
+# include <term.h>
+# define _tty cur_term->Nttyb
+# endif attron
+
+/*
+ * @(#)misc.c 1.2 (Berkeley) 3/28/83
+ */
+
+#define NUMSAFE 4
+
+/* VARARGS1 */
+error(str, arg)
+char *str;
+{
+ stdscr = Score;
+ mvprintw(ERR_Y, ERR_X, str, arg);
+ clrtoeol();
+ putchar('\07');
+ refresh();
+ stdscr = Board;
+ return FALSE;
+}
+
+CARD
+getcard()
+{
+ reg int c, c1;
+
+ for (;;) {
+ while ((c = readch()) == '\n' || c == '\r' || c == ' ')
+ continue;
+ if (islower(c))
+ c = toupper(c);
+ if (c == killchar() || c == erasechar())
+ return -1;
+ addstr(unctrl(c));
+ clrtoeol();
+ switch (c) {
+ case '1': case '2': case '3':
+ case '4': case '5': case '6':
+ c -= '0';
+ break;
+ case '0': case 'P': case 'p':
+ c = 0;
+ break;
+ default:
+ putchar('\07');
+ addch('\b');
+ if (!isprint(c))
+ addch('\b');
+ c = -1;
+ break;
+ }
+ refresh();
+ if (c >= 0) {
+ while ((c1=readch()) != '\r' && c1 != '\n' && c1 != ' ')
+ if (c1 == killchar())
+ return -1;
+ else if (c1 == erasechar()) {
+ addch('\b');
+ clrtoeol();
+ refresh();
+ goto cont;
+ }
+ else
+ write(0, "\07", 1);
+ return c;
+ }
+cont: ;
+ }
+}
+
+check_ext(forcomp)
+reg bool forcomp; {
+
+
+ if (End == 700)
+ if (Play == PLAYER) {
+ if (getyn(EXTENSIONPROMPT)) {
+extend:
+ if (!forcomp)
+ End = 1000;
+ return TRUE;
+ }
+ else {
+done:
+ if (!forcomp)
+ Finished = TRUE;
+ return FALSE;
+ }
+ }
+ else {
+ reg PLAY *pp, *op;
+ reg int i, safe, miles;
+
+ pp = &Player[COMP];
+ op = &Player[PLAYER];
+ for (safe = 0, i = 0; i < NUMSAFE; i++)
+ if (pp->safety[i] != S_UNKNOWN)
+ safe++;
+ if (safe < 2)
+ goto done;
+ if (op->mileage == 0 || onecard(op)
+ || (op->can_go && op->mileage >= 500))
+ goto done;
+ for (miles = 0, i = 0; i < NUMSAFE; i++)
+ if (op->safety[i] != S_PLAYED
+ && pp->safety[i] == S_UNKNOWN)
+ miles++;
+ if (miles + safe == NUMSAFE)
+ goto extend;
+ for (miles = 0, i = 0; i < HAND_SZ; i++)
+ if ((safe = pp->hand[i]) <= C_200)
+ miles += Value[safe];
+ if (miles + (Topcard - Deck) * 3 > 1000)
+ goto extend;
+ goto done;
+ }
+ else
+ goto done;
+}
+
+/*
+ * Get a yes or no answer to the given question. Saves are
+ * also allowed. Return TRUE if the answer was yes, FALSE if no.
+ */
+getyn(promptno)
+register int promptno; {
+
+ reg char c;
+
+ Saved = FALSE;
+ for (;;) {
+ leaveok(Board, FALSE);
+ prompt(promptno);
+ clrtoeol();
+ refresh();
+ switch (c = readch()) {
+ case 'n': case 'N':
+ addch('N');
+ refresh();
+ leaveok(Board, TRUE);
+ return FALSE;
+ case 'y': case 'Y':
+ addch('Y');
+ refresh();
+ leaveok(Board, TRUE);
+ return TRUE;
+ case 's': case 'S':
+ addch('S');
+ refresh();
+ Saved = save();
+ continue;
+ case CTRL('L'):
+ wrefresh(curscr);
+ break;
+ default:
+ addstr(unctrl(c));
+ refresh();
+ putchar('\07');
+ break;
+ }
+ }
+}
+
+/*
+ * Check to see if more games are desired. If not, and game
+ * came from a saved file, make sure that they don't want to restore
+ * it. Exit appropriately.
+ */
+check_more() {
+
+ On_exit = TRUE;
+ if (Player[PLAYER].total >= 5000 || Player[COMP].total >= 5000)
+ if (getyn(ANOTHERGAMEPROMPT))
+ return;
+ else {
+ /*
+ * must do accounting normally done in main()
+ */
+ if (Player[PLAYER].total > Player[COMP].total)
+ Player[PLAYER].games++;
+ else if (Player[PLAYER].total < Player[COMP].total)
+ Player[COMP].games++;
+ Player[COMP].total = 0;
+ Player[PLAYER].total = 0;
+ }
+ else
+ if (getyn(ANOTHERHANDPROMPT))
+ return;
+ if (!Saved && getyn(SAVEGAMEPROMPT))
+ if (!save())
+ return;
+ die(0);
+}
+
+readch()
+{
+ reg int cnt;
+ static char c;
+
+ for (cnt = 0; read(0, &c, 1) <= 0; cnt++)
+ if (cnt > 100)
+ exit(1);
+ return c;
+}
diff --git a/games/mille/move.c b/games/mille/move.c
new file mode 100644
index 00000000000..422e8db72df
--- /dev/null
+++ b/games/mille/move.c
@@ -0,0 +1,570 @@
+/* $NetBSD: move.c,v 1.4 1995/03/24 05:01:57 cgd Exp $ */
+
+/*
+ * Copyright (c) 1983, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)move.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: move.c,v 1.4 1995/03/24 05:01:57 cgd Exp $";
+#endif
+#endif /* not lint */
+
+#include <termios.h>
+
+#include "mille.h"
+#ifndef unctrl
+#include "unctrl.h"
+#endif
+
+# ifdef attron
+# include <term.h>
+# define _tty cur_term->Nttyb
+# endif attron
+
+/*
+ * @(#)move.c 1.2 (Berkeley) 3/28/83
+ */
+
+#undef CTRL
+#define CTRL(c) (c - 'A' + 1)
+
+char *Movenames[] = {
+ "M_DISCARD", "M_DRAW", "M_PLAY", "M_ORDER"
+ };
+
+domove()
+{
+ reg PLAY *pp;
+ reg int i, j;
+ reg bool goodplay;
+
+ pp = &Player[Play];
+ if (Play == PLAYER)
+ getmove();
+ else
+ calcmove();
+ Next = FALSE;
+ goodplay = TRUE;
+ switch (Movetype) {
+ case M_DISCARD:
+ if (haspicked(pp)) {
+ if (pp->hand[Card_no] == C_INIT)
+ if (Card_no == 6)
+ Finished = TRUE;
+ else
+ error("no card there");
+ else {
+ if (issafety(pp->hand[Card_no])) {
+ error("discard a safety?");
+ goodplay = FALSE;
+ break;
+ }
+ Discard = pp->hand[Card_no];
+ pp->hand[Card_no] = C_INIT;
+ Next = TRUE;
+ if (Play == PLAYER)
+ account(Discard);
+ }
+ }
+ else
+ error("must pick first");
+ break;
+ case M_PLAY:
+ goodplay = playcard(pp);
+ break;
+ case M_DRAW:
+ Card_no = 0;
+ if (Topcard <= Deck)
+ error("no more cards");
+ else if (haspicked(pp))
+ error("already picked");
+ else {
+ pp->hand[0] = *--Topcard;
+#ifdef DEBUG
+ if (Debug)
+ fprintf(outf, "DOMOVE: Draw %s\n", C_name[*Topcard]);
+#endif
+acc:
+ if (Play == COMP) {
+ account(*Topcard);
+ if (issafety(*Topcard))
+ pp->safety[*Topcard-S_CONV] = S_IN_HAND;
+ }
+ if (pp->hand[1] == C_INIT && Topcard > Deck) {
+ Card_no = 1;
+ pp->hand[1] = *--Topcard;
+#ifdef DEBUG
+ if (Debug)
+ fprintf(outf, "DOMOVE: Draw %s\n", C_name[*Topcard]);
+#endif
+ goto acc;
+ }
+ pp->new_battle = FALSE;
+ pp->new_speed = FALSE;
+ }
+ break;
+
+ case M_ORDER:
+ break;
+ }
+ /*
+ * move blank card to top by one of two methods. If the
+ * computer's hand was sorted, the randomness for picking
+ * between equally valued cards would be lost
+ */
+ if (Order && Movetype != M_DRAW && goodplay && pp == &Player[PLAYER])
+ sort(pp->hand);
+ else
+ for (i = 1; i < HAND_SZ; i++)
+ if (pp->hand[i] == C_INIT) {
+ for (j = 0; pp->hand[j] == C_INIT; j++)
+ if (j >= HAND_SZ) {
+ j = 0;
+ break;
+ }
+ pp->hand[i] = pp->hand[j];
+ pp->hand[j] = C_INIT;
+ }
+ if (Topcard <= Deck)
+ check_go();
+ if (Next)
+ nextplay();
+}
+
+/*
+ * Check and see if either side can go. If they cannot,
+ * the game is over
+ */
+check_go() {
+
+ reg CARD card;
+ reg PLAY *pp, *op;
+ reg int i;
+
+ for (pp = Player; pp < &Player[2]; pp++) {
+ op = (pp == &Player[COMP] ? &Player[PLAYER] : &Player[COMP]);
+ for (i = 0; i < HAND_SZ; i++) {
+ card = pp->hand[i];
+ if (issafety(card) || canplay(pp, op, card)) {
+#ifdef DEBUG
+ if (Debug) {
+ fprintf(outf, "CHECK_GO: can play %s (%d), ", C_name[card], card);
+ fprintf(outf, "issafety(card) = %d, ", issafety(card));
+ fprintf(outf, "canplay(pp, op, card) = %d\n", canplay(pp, op, card));
+ }
+#endif
+ return;
+ }
+#ifdef DEBUG
+ else if (Debug)
+ fprintf(outf, "CHECK_GO: cannot play %s\n",
+ C_name[card]);
+#endif
+ }
+ }
+ Finished = TRUE;
+}
+
+playcard(pp)
+reg PLAY *pp;
+{
+ reg int v;
+ reg CARD card;
+
+ /*
+ * check and see if player has picked
+ */
+ switch (pp->hand[Card_no]) {
+ default:
+ if (!haspicked(pp))
+mustpick:
+ return error("must pick first");
+ case C_GAS_SAFE: case C_SPARE_SAFE:
+ case C_DRIVE_SAFE: case C_RIGHT_WAY:
+ break;
+ }
+
+ card = pp->hand[Card_no];
+#ifdef DEBUG
+ if (Debug)
+ fprintf(outf, "PLAYCARD: Card = %s\n", C_name[card]);
+#endif
+ Next = FALSE;
+ switch (card) {
+ case C_200:
+ if (pp->nummiles[C_200] == 2)
+ return error("only two 200's per hand");
+ case C_100: case C_75:
+ if (pp->speed == C_LIMIT)
+ return error("limit of 50");
+ case C_50:
+ if (pp->mileage + Value[card] > End)
+ return error("puts you over %d", End);
+ case C_25:
+ if (!pp->can_go)
+ return error("cannot move now");
+ pp->nummiles[card]++;
+ v = Value[card];
+ pp->total += v;
+ pp->hand_tot += v;
+ if ((pp->mileage += v) == End)
+ check_ext(FALSE);
+ break;
+
+ case C_GAS: case C_SPARE: case C_REPAIRS:
+ if (pp->battle != opposite(card))
+ return error("can't play \"%s\"", C_name[card]);
+ pp->battle = card;
+ if (pp->safety[S_RIGHT_WAY] == S_PLAYED)
+ pp->can_go = TRUE;
+ break;
+
+ case C_GO:
+ if (pp->battle != C_INIT && pp->battle != C_STOP
+ && !isrepair(pp->battle))
+ return error("cannot play \"Go\" on a \"%s\"",
+ C_name[pp->battle]);
+ pp->battle = C_GO;
+ pp->can_go = TRUE;
+ break;
+
+ case C_END_LIMIT:
+ if (pp->speed != C_LIMIT)
+ return error("not limited");
+ pp->speed = C_END_LIMIT;
+ break;
+
+ case C_EMPTY: case C_FLAT: case C_CRASH:
+ case C_STOP:
+ pp = &Player[other(Play)];
+ if (!pp->can_go)
+ return error("opponent cannot go");
+ else if (pp->safety[safety(card) - S_CONV] == S_PLAYED)
+protected:
+ return error("opponent is protected");
+ pp->battle = card;
+ pp->new_battle = TRUE;
+ pp->can_go = FALSE;
+ pp = &Player[Play];
+ break;
+
+ case C_LIMIT:
+ pp = &Player[other(Play)];
+ if (pp->speed == C_LIMIT)
+ return error("opponent has limit");
+ if (pp->safety[S_RIGHT_WAY] == S_PLAYED)
+ goto protected;
+ pp->speed = C_LIMIT;
+ pp->new_speed = TRUE;
+ pp = &Player[Play];
+ break;
+
+ case C_GAS_SAFE: case C_SPARE_SAFE:
+ case C_DRIVE_SAFE: case C_RIGHT_WAY:
+ if (pp->battle == opposite(card)
+ || (card == C_RIGHT_WAY && pp->speed == C_LIMIT)) {
+ if (!(card == C_RIGHT_WAY && !isrepair(pp->battle))) {
+ pp->battle = C_GO;
+ pp->can_go = TRUE;
+ }
+ if (card == C_RIGHT_WAY && pp->speed == C_LIMIT)
+ pp->speed = C_INIT;
+ if (pp->new_battle
+ || (pp->new_speed && card == C_RIGHT_WAY)) {
+ pp->coups[card - S_CONV] = TRUE;
+ pp->total += SC_COUP;
+ pp->hand_tot += SC_COUP;
+ pp->coupscore += SC_COUP;
+ }
+ }
+ /*
+ * if not coup, must pick first
+ */
+ else if (pp->hand[0] == C_INIT && Topcard > Deck)
+ goto mustpick;
+ pp->safety[card - S_CONV] = S_PLAYED;
+ pp->total += SC_SAFETY;
+ pp->hand_tot += SC_SAFETY;
+ if ((pp->safescore += SC_SAFETY) == NUM_SAFE * SC_SAFETY) {
+ pp->total += SC_ALL_SAFE;
+ pp->hand_tot += SC_ALL_SAFE;
+ }
+ if (card == C_RIGHT_WAY) {
+ if (pp->speed == C_LIMIT)
+ pp->speed = C_INIT;
+ if (pp->battle == C_STOP || pp->battle == C_INIT) {
+ pp->can_go = TRUE;
+ pp->battle = C_INIT;
+ }
+ if (!pp->can_go && isrepair(pp->battle))
+ pp->can_go = TRUE;
+ }
+ Next = -1;
+ break;
+
+ case C_INIT:
+ error("no card there");
+ Next = -1;
+ break;
+ }
+ if (pp == &Player[PLAYER])
+ account(card);
+ pp->hand[Card_no] = C_INIT;
+ Next = (Next == -1 ? FALSE : TRUE);
+ return TRUE;
+}
+
+getmove()
+{
+ reg char c, *sp;
+#ifdef EXTRAP
+ static bool last_ex = FALSE; /* set if last command was E */
+
+ if (last_ex) {
+ undoex();
+ prboard();
+ last_ex = FALSE;
+ }
+#endif
+ for (;;) {
+ prompt(MOVEPROMPT);
+ leaveok(Board, FALSE);
+ refresh();
+ while ((c = readch()) == killchar() || c == erasechar())
+ continue;
+ if (islower(c))
+ c = toupper(c);
+ if (isprint(c) && !isspace(c)) {
+ addch(c);
+ refresh();
+ }
+ switch (c) {
+ case 'P': /* Pick */
+ Movetype = M_DRAW;
+ goto ret;
+ case 'U': /* Use Card */
+ case 'D': /* Discard Card */
+ if ((Card_no = getcard()) < 0)
+ break;
+ Movetype = (c == 'U' ? M_PLAY : M_DISCARD);
+ goto ret;
+ case 'O': /* Order */
+ Order = !Order;
+ if (Window == W_SMALL) {
+ if (!Order)
+ mvwaddstr(Score, 12, 21,
+ "o: order hand");
+ else
+ mvwaddstr(Score, 12, 21,
+ "o: stop ordering");
+ wclrtoeol(Score);
+ }
+ Movetype = M_ORDER;
+ goto ret;
+ case 'Q': /* Quit */
+ rub(); /* Same as a rubout */
+ break;
+ case 'W': /* Window toggle */
+ Window = nextwin(Window);
+ newscore();
+ prscore(TRUE);
+ wrefresh(Score);
+ break;
+ case 'R': /* Redraw screen */
+ case CTRL('L'):
+ wrefresh(curscr);
+ break;
+ case 'S': /* Save game */
+ On_exit = FALSE;
+ save();
+ break;
+ case 'E': /* Extrapolate */
+#ifdef EXTRAP
+ if (last_ex)
+ break;
+ Finished = TRUE;
+ if (Window != W_FULL)
+ newscore();
+ prscore(FALSE);
+ wrefresh(Score);
+ last_ex = TRUE;
+ Finished = FALSE;
+#else
+ error("%c: command not implemented", c);
+#endif
+ break;
+ case '\r': /* Ignore RETURNs and */
+ case '\n': /* Line Feeds */
+ case ' ': /* Spaces */
+ case '\0': /* and nulls */
+ break;
+#ifdef DEBUG
+ case 'Z': /* Debug code */
+ if (!Debug && outf == NULL) {
+ char buf[MAXPATHLEN];
+
+ prompt(FILEPROMPT);
+ leaveok(Board, FALSE);
+ refresh();
+ sp = buf;
+ while ((*sp = readch()) != '\n') {
+ if (*sp == killchar())
+ goto over;
+ else if (*sp == erasechar()) {
+ if (--sp < buf)
+ sp = buf;
+ else {
+ addch('\b');
+ if (*sp < ' ')
+ addch('\b');
+ clrtoeol();
+ }
+ }
+ else
+ addstr(unctrl(*sp++));
+ refresh();
+ }
+ *sp = '\0';
+ leaveok(Board, TRUE);
+ if ((outf = fopen(buf, "w")) == NULL)
+ perror(buf);
+ setbuf(outf, (char *)NULL);
+ }
+ Debug = !Debug;
+ break;
+#endif
+ default:
+ error("unknown command: %s", unctrl(c));
+ break;
+ }
+ }
+ret:
+ leaveok(Board, TRUE);
+}
+/*
+ * return whether or not the player has picked
+ */
+haspicked(pp)
+reg PLAY *pp; {
+
+ reg int card;
+
+ if (Topcard <= Deck)
+ return TRUE;
+ switch (pp->hand[Card_no]) {
+ case C_GAS_SAFE: case C_SPARE_SAFE:
+ case C_DRIVE_SAFE: case C_RIGHT_WAY:
+ card = 1;
+ break;
+ default:
+ card = 0;
+ break;
+ }
+ return (pp->hand[card] != C_INIT);
+}
+
+account(card)
+reg CARD card; {
+
+ reg CARD oppos;
+
+ if (card == C_INIT)
+ return;
+ ++Numseen[card];
+ if (Play == COMP)
+ switch (card) {
+ case C_GAS_SAFE:
+ case C_SPARE_SAFE:
+ case C_DRIVE_SAFE:
+ oppos = opposite(card);
+ Numgos += Numcards[oppos] - Numseen[oppos];
+ break;
+ case C_CRASH:
+ case C_FLAT:
+ case C_EMPTY:
+ case C_STOP:
+ Numgos++;
+ break;
+ }
+}
+
+prompt(promptno)
+int promptno;
+{
+ static char *names[] = {
+ ">>:Move:",
+ "Really?",
+ "Another hand?",
+ "Another game?",
+ "Save game?",
+ "Same file?",
+ "file:",
+ "Extension?",
+ "Overwrite file?",
+ };
+ static int last_prompt = -1;
+
+ if (promptno == last_prompt)
+ move(MOVE_Y, MOVE_X + strlen(names[promptno]) + 1);
+ else {
+ move(MOVE_Y, MOVE_X);
+ if (promptno == MOVEPROMPT)
+ standout();
+ addstr(names[promptno]);
+ if (promptno == MOVEPROMPT)
+ standend();
+ addch(' ');
+ last_prompt = promptno;
+ }
+ clrtoeol();
+}
+
+sort(hand)
+reg CARD *hand;
+{
+ reg CARD *cp, *tp;
+ reg CARD temp;
+
+ cp = hand;
+ hand += HAND_SZ;
+ for ( ; cp < &hand[-1]; cp++)
+ for (tp = cp + 1; tp < hand; tp++)
+ if (*cp > *tp) {
+ temp = *cp;
+ *cp = *tp;
+ *tp = temp;
+ }
+}
+
diff --git a/games/mille/print.c b/games/mille/print.c
new file mode 100644
index 00000000000..5c2427c6d20
--- /dev/null
+++ b/games/mille/print.c
@@ -0,0 +1,175 @@
+/* $NetBSD: print.c,v 1.4 1995/03/24 05:02:02 cgd Exp $ */
+
+/*
+ * Copyright (c) 1982, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)print.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: print.c,v 1.4 1995/03/24 05:02:02 cgd Exp $";
+#endif
+#endif /* not lint */
+
+# include "mille.h"
+
+/*
+ * @(#)print.c 1.1 (Berkeley) 4/1/82
+ */
+
+# define COMP_STRT 20
+# define CARD_STRT 2
+
+prboard() {
+
+ reg PLAY *pp;
+ reg int i, j, k, temp;
+
+ for (k = 0; k < 2; k++) {
+ pp = &Player[k];
+ temp = k * COMP_STRT + CARD_STRT;
+ for (i = 0; i < NUM_SAFE; i++)
+ if (pp->safety[i] == S_PLAYED && !pp->sh_safety[i]) {
+ mvaddstr(i, temp, C_name[i + S_CONV]);
+ if (pp->coups[i])
+ mvaddch(i, temp - CARD_STRT, '*');
+ pp->sh_safety[i] = TRUE;
+ }
+ show_card(14, temp, pp->battle, &pp->sh_battle);
+ show_card(16, temp, pp->speed, &pp->sh_speed);
+ for (i = C_25; i <= C_200; i++) {
+ reg char *name;
+ reg int end;
+
+ if (pp->nummiles[i] == pp->sh_nummiles[i])
+ continue;
+
+ name = C_name[i];
+ temp = k * 40;
+ end = pp->nummiles[i];
+ for (j = pp->sh_nummiles[i]; j < end; j++)
+ mvwaddstr(Miles, i + 1, (j << 2) + temp, name);
+ pp->sh_nummiles[i] = end;
+ }
+ }
+ prscore(TRUE);
+ temp = CARD_STRT;
+ pp = &Player[PLAYER];
+ for (i = 0; i < HAND_SZ; i++)
+ show_card(i + 6, temp, pp->hand[i], &pp->sh_hand[i]);
+ mvprintw(6, COMP_STRT + CARD_STRT, "%2d", Topcard - Deck);
+ show_card(8, COMP_STRT + CARD_STRT, Discard, &Sh_discard);
+ if (End == 1000) {
+ move(EXT_Y, EXT_X);
+ standout();
+ addstr("Extension");
+ standend();
+ }
+ wrefresh(Board);
+ wrefresh(Miles);
+ wrefresh(Score);
+}
+
+/*
+ * show_card:
+ * Show the given card if it is different from the last one shown
+ */
+show_card(y, x, c, lc)
+int y, x;
+register CARD c, *lc;
+{
+ if (c == *lc)
+ return;
+
+ mvprintw(y, x, C_fmt, C_name[c]);
+ *lc = c;
+}
+
+static char Score_fmt[] = "%4d";
+
+prscore(for_real)
+reg bool for_real; {
+
+ reg PLAY *pp;
+ reg int x;
+
+ stdscr = Score;
+ for (pp = Player; pp < &Player[2]; pp++) {
+ x = (pp - Player) * 6 + 21;
+ show_score(1, x, pp->mileage, &pp->sh_mileage);
+ if (pp->safescore != pp->sh_safescore) {
+ mvprintw(2, x, Score_fmt, pp->safescore);
+ if (pp->safescore == 400)
+ mvaddstr(3, x + 1, "300");
+ else
+ mvaddstr(3, x + 1, " 0");
+ mvprintw(4, x, Score_fmt, pp->coupscore);
+ pp->sh_safescore = pp->safescore;
+ }
+ if (Window == W_FULL || Finished) {
+#ifdef EXTRAP
+ if (for_real)
+ finalscore(pp);
+ else
+ extrapolate(pp);
+#else
+ finalscore(pp);
+#endif
+ show_score(11, x, pp->hand_tot, &pp->sh_hand_tot);
+ show_score(13, x, pp->total, &pp->sh_total);
+ show_score(14, x, pp->games, &pp->sh_games);
+ }
+ else {
+ show_score(6, x, pp->hand_tot, &pp->sh_hand_tot);
+ show_score(8, x, pp->total, &pp->sh_total);
+ show_score(9, x, pp->games, &pp->sh_games);
+ }
+ }
+ stdscr = Board;
+}
+
+/*
+ * show_score:
+ * Show a score value if it is different from the last time we
+ * showed it.
+ */
+show_score(y, x, s, ls)
+int y, x;
+register int s, *ls;
+{
+ if (s == *ls)
+ return;
+
+ mvprintw(y, x, Score_fmt, s);
+ *ls = s;
+}
diff --git a/games/mille/roll.c b/games/mille/roll.c
new file mode 100644
index 00000000000..fa589ba95b6
--- /dev/null
+++ b/games/mille/roll.c
@@ -0,0 +1,63 @@
+/* $NetBSD: roll.c,v 1.4 1995/03/24 05:02:07 cgd Exp $ */
+
+/*
+ * Copyright (c) 1982, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)roll.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: roll.c,v 1.4 1995/03/24 05:02:07 cgd Exp $";
+#endif
+#endif /* not lint */
+
+# include "mille.h"
+
+/*
+ * This routine rolls ndie nside-sided dice.
+ *
+ * @(#)roll.c 1.1 (Berkeley) 4/1/82
+ *
+ */
+
+roll(ndie, nsides)
+reg int ndie, nsides; {
+
+ reg int tot;
+ extern unsigned int random();
+
+ tot = 0;
+ while (ndie--)
+ tot += random() % nsides + 1;
+ return tot;
+}
diff --git a/games/mille/save.c b/games/mille/save.c
new file mode 100644
index 00000000000..1e0ad47e5b6
--- /dev/null
+++ b/games/mille/save.c
@@ -0,0 +1,180 @@
+/* $NetBSD: save.c,v 1.4 1995/03/24 05:02:13 cgd Exp $ */
+
+/*
+ * Copyright (c) 1983, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)save.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: save.c,v 1.4 1995/03/24 05:02:13 cgd Exp $";
+#endif
+#endif /* not lint */
+
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <string.h>
+#include <termios.h>
+#include "mille.h"
+
+#ifndef unctrl
+#include "unctrl.h"
+#endif
+
+# ifdef attron
+# include <term.h>
+# define _tty cur_term->Nttyb
+# endif attron
+
+/*
+ * @(#)save.c 1.2 (Berkeley) 3/28/83
+ */
+
+typedef struct stat STAT;
+
+char *ctime();
+
+int read(), write();
+
+/*
+ * This routine saves the current game for use at a later date
+ */
+
+save() {
+
+ extern int errno;
+ reg char *sp;
+ reg int outf;
+ reg time_t *tp;
+ char buf[80];
+ time_t tme;
+ STAT junk;
+
+ tp = &tme;
+ if (Fromfile && getyn(SAMEFILEPROMPT))
+ strcpy(buf, Fromfile);
+ else {
+over:
+ prompt(FILEPROMPT);
+ leaveok(Board, FALSE);
+ refresh();
+ sp = buf;
+ while ((*sp = readch()) != '\n') {
+ if (*sp == killchar())
+ goto over;
+ else if (*sp == erasechar()) {
+ if (--sp < buf)
+ sp = buf;
+ else {
+ addch('\b');
+ /*
+ * if the previous char was a control
+ * char, cover up two characters.
+ */
+ if (*sp < ' ')
+ addch('\b');
+ clrtoeol();
+ }
+ }
+ else {
+ addstr(unctrl(*sp));
+ ++sp;
+ }
+ refresh();
+ }
+ *sp = '\0';
+ leaveok(Board, TRUE);
+ }
+
+ /*
+ * check for existing files, and confirm overwrite if needed
+ */
+
+ if (sp == buf || (!Fromfile && stat(buf, &junk) > -1
+ && getyn(OVERWRITEFILEPROMPT) == FALSE))
+ return FALSE;
+
+ if ((outf = creat(buf, 0644)) < 0) {
+ error(strerror(errno));
+ return FALSE;
+ }
+ mvwaddstr(Score, ERR_Y, ERR_X, buf);
+ wrefresh(Score);
+ time(tp); /* get current time */
+ strcpy(buf, ctime(tp));
+ for (sp = buf; *sp != '\n'; sp++)
+ continue;
+ *sp = '\0';
+ varpush(outf, write);
+ close(outf);
+ wprintw(Score, " [%s]", buf);
+ wclrtoeol(Score);
+ wrefresh(Score);
+ return TRUE;
+}
+
+/*
+ * This does the actual restoring. It returns TRUE if the
+ * backup was made on exiting, in which case certain things must
+ * be cleaned up before the game starts.
+ */
+rest_f(file)
+reg char *file; {
+
+ reg char *sp;
+ reg int inf;
+ char buf[80];
+ STAT sbuf;
+
+ if ((inf = open(file, 0)) < 0) {
+ perror(file);
+ exit(1);
+ }
+ if (fstat(inf, &sbuf) < 0) { /* get file stats */
+ perror(file);
+ exit(1);
+ }
+ varpush(inf, read);
+ close(inf);
+ strcpy(buf, ctime(&sbuf.st_mtime));
+ for (sp = buf; *sp != '\n'; sp++)
+ continue;
+ *sp = '\0';
+ /*
+ * initialize some necessary values
+ */
+ (void)sprintf(Initstr, "%s [%s]\n", file, buf);
+ Fromfile = file;
+ return !On_exit;
+}
+
diff --git a/games/mille/table.c b/games/mille/table.c
new file mode 100644
index 00000000000..7b0f9cd2cf4
--- /dev/null
+++ b/games/mille/table.c
@@ -0,0 +1,70 @@
+/* $NetBSD: table.c,v 1.4 1995/03/24 05:02:18 cgd Exp $ */
+
+/*
+ * Copyright (c) 1982, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+static char copyright[] =
+"@(#) Copyright (c) 1982, 1993\n\
+ The Regents of the University of California. All rights reserved.\n";
+#endif /* not lint */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)table.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: table.c,v 1.4 1995/03/24 05:02:18 cgd Exp $";
+#endif
+#endif /* not lint */
+
+# define DEBUG
+
+/*
+ * @(#)table.c 1.1 (Berkeley) 4/1/82
+ */
+
+# include "mille.h"
+
+main() {
+
+ reg int i, j, count;
+
+ printf(" %16s -> %5s %5s %4s %s\n", "Card", "cards", "count", "need", "opposite");
+ for (i = 0; i < NUM_CARDS - 1; i++) {
+ for (j = 0, count = 0; j < DECK_SZ; j++)
+ if (Deck[j] == i)
+ count++;
+ printf("%2d %16s -> %5d %5d %4d %s\n", i, C_name[i], Numcards[i], count, Numneed[i], C_name[opposite(i)]);
+ }
+}
+
diff --git a/games/mille/types.c b/games/mille/types.c
new file mode 100644
index 00000000000..cbe8d6ed30b
--- /dev/null
+++ b/games/mille/types.c
@@ -0,0 +1,81 @@
+/* $NetBSD: types.c,v 1.4 1995/03/24 05:02:22 cgd Exp $ */
+
+/*
+ * Copyright (c) 1982, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)types.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: types.c,v 1.4 1995/03/24 05:02:22 cgd Exp $";
+#endif
+#endif /* not lint */
+
+# include "mille.h"
+
+/*
+ * @(#)types.c 1.1 (Berkeley) 4/1/82
+ */
+
+isrepair(card)
+reg CARD card; {
+
+ return card == C_GAS || card == C_SPARE || card == C_REPAIRS || card == C_INIT;
+}
+
+safety(card)
+reg CARD card; {
+
+ switch (card) {
+ case C_EMPTY:
+ case C_GAS:
+ case C_GAS_SAFE:
+ return C_GAS_SAFE;
+ case C_FLAT:
+ case C_SPARE:
+ case C_SPARE_SAFE:
+ return C_SPARE_SAFE;
+ case C_CRASH:
+ case C_REPAIRS:
+ case C_DRIVE_SAFE:
+ return C_DRIVE_SAFE;
+ case C_GO:
+ case C_STOP:
+ case C_RIGHT_WAY:
+ case C_LIMIT:
+ case C_END_LIMIT:
+ return C_RIGHT_WAY;
+ }
+ /* NOTREACHED */
+}
+
diff --git a/games/mille/unctrl.h b/games/mille/unctrl.h
new file mode 100644
index 00000000000..e75d0f0bece
--- /dev/null
+++ b/games/mille/unctrl.h
@@ -0,0 +1,44 @@
+/* $NetBSD: unctrl.h,v 1.4 1995/03/24 05:02:28 cgd Exp $ */
+
+/*
+ * Copyright (c) 1982, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ *
+ * @(#)unctrl.h 8.1 (Berkeley) 5/31/93
+ */
+
+/*
+ * unctrl.h
+ */
+
+extern char *_unctrl[];
+
+# define unctrl(ch) (_unctrl[ch & 0177])
diff --git a/games/mille/varpush.c b/games/mille/varpush.c
new file mode 100644
index 00000000000..1fac4cf0d5b
--- /dev/null
+++ b/games/mille/varpush.c
@@ -0,0 +1,98 @@
+/* $NetBSD: varpush.c,v 1.4 1995/03/24 05:02:35 cgd Exp $ */
+
+/*
+ * Copyright (c) 1982, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * 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. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. 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.
+ */
+
+#ifndef lint
+#if 0
+static char sccsid[] = "@(#)varpush.c 8.1 (Berkeley) 5/31/93";
+#else
+static char rcsid[] = "$NetBSD: varpush.c,v 1.4 1995/03/24 05:02:35 cgd Exp $";
+#endif
+#endif /* not lint */
+
+# include <paths.h>
+# include "mille.h"
+
+/*
+ * @(#)varpush.c 1.1 (Berkeley) 4/1/82
+ */
+
+int read(), write();
+
+/*
+ * push variables around via the routine func() on the file
+ * channel file. func() is either read or write.
+ */
+varpush(file, func)
+reg int file;
+reg int (*func)(); {
+
+ int temp;
+
+ (*func)(file, (char *) &Debug, sizeof Debug);
+ (*func)(file, (char *) &Finished, sizeof Finished);
+ (*func)(file, (char *) &Order, sizeof Order);
+ (*func)(file, (char *) &End, sizeof End);
+ (*func)(file, (char *) &On_exit, sizeof On_exit);
+ (*func)(file, (char *) &Handstart, sizeof Handstart);
+ (*func)(file, (char *) &Numgos, sizeof Numgos);
+ (*func)(file, (char *) Numseen, sizeof Numseen);
+ (*func)(file, (char *) &Play, sizeof Play);
+ (*func)(file, (char *) &Window, sizeof Window);
+ (*func)(file, (char *) Deck, sizeof Deck);
+ (*func)(file, (char *) &Discard, sizeof Discard);
+ (*func)(file, (char *) Player, sizeof Player);
+ if (func == read) {
+ read(file, (char *) &temp, sizeof temp);
+ Topcard = &Deck[temp];
+#ifdef DEBUG
+ if (Debug) {
+ char buf[80];
+over:
+ printf("Debug file:");
+ gets(buf);
+ if ((outf = fopen(buf, "w")) == NULL) {
+ perror(buf);
+ goto over;
+ }
+ if (strcmp(buf, _PATH_DEVNULL) != 0)
+ setbuf(outf, (char *)NULL);
+ }
+#endif
+ }
+ else {
+ temp = Topcard - Deck;
+ write(file, (char *) &temp, sizeof temp);
+ }
+}