In its current form, tetris is a setgid program and needs a whopping
pledge("stdio rpath wpath cpath flock getpw id tty")
throughout its lifetime because of the score file in /var/games.
As discussed with Theo off-list, this is risk-only. Thus, drop the
score file support, lose the setgid bit and make tetris a much more
reasonable pledge("stdio rpath tty") program for relaxed game play.
Index: games/tetris/Makefile
===================================================================
RCS file: /cvs/src/games/tetris/Makefile,v
retrieving revision 1.7
diff -u -p -r1.7 Makefile
--- games/tetris/Makefile 31 May 2002 03:46:35 -0000 1.7
+++ games/tetris/Makefile 17 Nov 2015 04:50:55 -0000
@@ -1,18 +1,9 @@
# $OpenBSD: Makefile,v 1.7 2002/05/31 03:46:35 pjanzen Exp $
PROG= tetris
-SRCS= input.c screen.c shapes.c scores.c tetris.c
+SRCS= input.c screen.c shapes.c tetris.c
MAN= tetris.6
DPADD= ${LIBCURSES}
LDADD= -lcurses
-BINMODE=2555
-
-beforeinstall:
- @if [ ! -f ${DESTDIR}/var/games/tetris.scores ]; then \
- ${INSTALL} ${INSTALL_COPY} -o ${BINOWN} -g ${BINGRP} -m 664 \
- /dev/null ${DESTDIR}/var/games/tetris.scores ; \
- else \
- true ; \
- fi
.include <bsd.prog.mk>
Index: games/tetris/pathnames.h
===================================================================
RCS file: games/tetris/pathnames.h
diff -N games/tetris/pathnames.h
--- games/tetris/pathnames.h 3 Jun 2003 03:01:41 -0000 1.3
+++ /dev/null 1 Jan 1970 00:00:00 -0000
@@ -1,38 +0,0 @@
-/* $OpenBSD: pathnames.h,v 1.3 2003/06/03 03:01:41 millert Exp $ */
-/* $NetBSD: pathnames.h,v 1.2 1995/04/22 07:42:37 cgd Exp $ */
-
-/*-
- * Copyright (c) 1992, 1993
- * The Regents of the University of California. All rights reserved.
- *
- * This code is derived from software contributed to Berkeley by
- * Chris Torek and Darren F. Provine.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. Neither the name of the University nor the names of its contributors
- * may be used to endorse or promote products derived from this software
- * without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
- * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
- * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
- * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
- * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
- * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
- * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- *
- * @(#)pathnames.h 8.1 (Berkeley) 5/31/93
- */
-
-#define _PATH_SCOREFILE "/var/games/tetris.scores"
Index: games/tetris/scores.c
===================================================================
RCS file: games/tetris/scores.c
diff -N games/tetris/scores.c
--- games/tetris/scores.c 16 Nov 2014 04:49:49 -0000 1.12
+++ /dev/null 1 Jan 1970 00:00:00 -0000
@@ -1,444 +0,0 @@
-/* $OpenBSD: scores.c,v 1.12 2014/11/16 04:49:49 guenther Exp $ */
-/* $NetBSD: scores.c,v 1.2 1995/04/22 07:42:38 cgd Exp $ */
-
-/*-
- * Copyright (c) 1992, 1993
- * The Regents of the University of California. All rights reserved.
- *
- * This code is derived from software contributed to Berkeley by
- * Chris Torek and Darren F. Provine.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. Neither the name of the University nor the names of its contributors
- * may be used to endorse or promote products derived from this software
- * without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
- * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
- * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
- * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
- * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
- * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
- * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- *
- * @(#)scores.c 8.1 (Berkeley) 5/31/93
- */
-
-/*
- * Score code for Tetris, by Darren Provine ([email protected])
- * modified 22 January 1992, to limit the number of entries any one
- * person has.
- *
- * Major whacks since then.
- */
-#include <sys/types.h>
-#include <sys/stat.h>
-
-#include <errno.h>
-#include <err.h>
-#include <fcntl.h>
-#include <limits.h>
-#include <pwd.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <time.h>
-#include <term.h>
-#include <unistd.h>
-
-#include "pathnames.h"
-#include "screen.h"
-#include "scores.h"
-#include "tetris.h"
-
-/*
- * Within this code, we can hang onto one extra "high score", leaving
- * room for our current score (whether or not it is high).
- *
- * We also sometimes keep tabs on the "highest" score on each level.
- * As long as the scores are kept sorted, this is simply the first one at
- * that level.
- */
-#define NUMSPOTS (MAXHISCORES + 1)
-#define NLEVELS (MAXLEVEL + 1)
-
-static time_t now;
-static int nscores;
-static int gotscores;
-static struct highscore scores[NUMSPOTS];
-
-static int checkscores(struct highscore *, int);
-static int cmpscores(const void *, const void *);
-static void getscores(FILE **);
-static void printem(int, int, struct highscore *, int, const char *);
-static char *thisuser(void);
-
-/*
- * Read the score file. Can be called from savescore (before showscores)
- * or showscores (if savescore will not be called). If the given pointer
- * is not NULL, sets *fpp to an open file pointer that corresponds to a
- * read/write score file that is locked with LOCK_EX. Otherwise, the
- * file is locked with LOCK_SH for the read and closed before return.
- *
- * Note, we assume closing the stdio file releases the lock.
- */
-static void
-getscores(FILE **fpp)
-{
- int sd, mint, lck, mask, i;
- char *mstr, *human;
- FILE *sf;
-
- if (fpp != NULL) {
- mint = O_RDWR | O_CREAT;
- mstr = "r+";
- human = "read/write";
- lck = LOCK_EX;
- } else {
- mint = O_RDONLY;
- mstr = "r";
- human = "reading";
- lck = LOCK_SH;
- }
- setegid(egid);
- mask = umask(S_IWOTH);
- sd = open(_PATH_SCOREFILE, mint, 0666);
- (void)umask(mask);
- setegid(gid);
- if (sd < 0) {
- if (fpp == NULL) {
- nscores = 0;
- return;
- }
- err(1, "cannot open %s for %s", _PATH_SCOREFILE, human);
- }
- setegid(egid);
- if ((sf = fdopen(sd, mstr)) == NULL)
- err(1, "cannot fdopen %s for %s", _PATH_SCOREFILE, human);
- setegid(gid);
-
- /*
- * Grab a lock.
- */
- if (flock(sd, lck))
- warn("warning: score file %s cannot be locked",
- _PATH_SCOREFILE);
-
- nscores = fread(scores, sizeof(scores[0]), MAXHISCORES, sf);
- if (ferror(sf))
- err(1, "error reading %s", _PATH_SCOREFILE);
- for (i = 0; i < nscores; i++)
- if (scores[i].hs_level < MINLEVEL ||
- scores[i].hs_level > MAXLEVEL)
- errx(1, "scorefile %s corrupt", _PATH_SCOREFILE);
-
- if (fpp)
- *fpp = sf;
- else
- (void)fclose(sf);
-}
-
-void
-savescore(int level)
-{
- struct highscore *sp;
- int i;
- int change;
- FILE *sf;
- const char *me;
-
- getscores(&sf);
- gotscores = 1;
- (void)time(&now);
-
- /*
- * Allow at most one score per person per level -- see if we
- * can replace an existing score, or (easiest) do nothing.
- * Otherwise add new score at end (there is always room).
- */
- change = 0;
- me = thisuser();
- for (i = 0, sp = &scores[0]; i < nscores; i++, sp++) {
- if (sp->hs_level != level || strcmp(sp->hs_name, me) != 0)
- continue;
- if (score > sp->hs_score) {
- (void)printf("%s bettered %s %d score of %d!\n",
- "\nYou", "your old level", level,
- sp->hs_score * sp->hs_level);
- sp->hs_score = score; /* new score */
- sp->hs_time = now; /* and time */
- change = 1;
- } else if (score == sp->hs_score) {
- (void)printf("%s tied %s %d high score.\n",
- "\nYou", "your old level", level);
- sp->hs_time = now; /* renew it */
- change = 1; /* gotta rewrite, sigh */
- } /* else new score < old score: do nothing */
- break;
- }
- if (i >= nscores) {
- strlcpy(sp->hs_name, me, sizeof sp->hs_name);
- sp->hs_level = level;
- sp->hs_score = score;
- sp->hs_time = now;
- nscores++;
- change = 1;
- }
-
- if (change) {
- /*
- * Sort & clean the scores, then rewrite.
- */
- nscores = checkscores(scores, nscores);
- rewind(sf);
- if (fwrite(scores, sizeof(*sp), nscores, sf) != nscores ||
- fflush(sf) == EOF)
- warnx("error writing %s: %s\n\t-- %s",
- _PATH_SCOREFILE, strerror(errno),
- "high scores may be damaged");
- }
- (void)fclose(sf); /* releases lock */
-}
-
-/*
- * Get login name, or if that fails, get something suitable.
- * The result is always trimmed to fit in a score.
- */
-static char *
-thisuser(void)
-{
- const char *p;
- struct passwd *pw;
- static char u[sizeof(scores[0].hs_name)];
-
- if (u[0])
- return (u);
- p = getlogin();
- if (p == NULL || *p == '\0') {
- pw = getpwuid(getuid());
- if (pw != NULL)
- p = pw->pw_name;
- else
- p = " ???";
- }
- strlcpy(u, p, sizeof(u));
- return (u);
-}
-
-/*
- * Score comparison function for qsort.
- *
- * If two scores are equal, the person who had the score first is
- * listed first in the highscore file.
- */
-static int
-cmpscores(const void *x, const void *y)
-{
- const struct highscore *a, *b;
- long l;
-
- a = x;
- b = y;
- l = (long)b->hs_level * b->hs_score - (long)a->hs_level * a->hs_score;
- if (l < 0)
- return (-1);
- if (l > 0)
- return (1);
- if (a->hs_time < b->hs_time)
- return (-1);
- if (a->hs_time > b->hs_time)
- return (1);
- return (0);
-}
-
-/*
- * If we've added a score to the file, we need to check the file and ensure
- * that this player has only a few entries. The number of entries is
- * controlled by MAXSCORES, and is to ensure that the highscore file is not
- * monopolised by just a few people. People who no longer have accounts are
- * only allowed the highest score. Scores older than EXPIRATION seconds are
- * removed, unless they are someone's personal best.
- * Caveat: the highest score on each level is always kept.
- */
-static int
-checkscores(struct highscore *hs, int num)
-{
- struct highscore *sp;
- int i, j, k, numnames;
- int levelfound[NLEVELS];
- struct peruser {
- char *name;
- int times;
- } count[NUMSPOTS];
- struct peruser *pu;
-
- /*
- * Sort so that highest totals come first.
- *
- * levelfound[i] becomes set when the first high score for that
- * level is encountered. By definition this is the highest score.
- */
- qsort((void *)hs, nscores, sizeof(*hs), cmpscores);
- for (i = MINLEVEL; i < NLEVELS; i++)
- levelfound[i] = 0;
- numnames = 0;
- for (i = 0, sp = hs; i < num;) {
- /*
- * This is O(n^2), but do you think we care?
- */
- for (j = 0, pu = count; j < numnames; j++, pu++)
- if (strcmp(sp->hs_name, pu->name) == 0)
- break;
- if (j == numnames) {
- /*
- * Add new user, set per-user count to 1.
- */
- pu->name = sp->hs_name;
- pu->times = 1;
- numnames++;
- } else {
- /*
- * Two ways to keep this score:
- * - Not too many (per user), still has acct, &
- * score not dated; or
- * - High score on this level.
- */
- if ((pu->times < MAXSCORES &&
- getpwnam(sp->hs_name) != NULL &&
- sp->hs_time + EXPIRATION >= now) ||
- levelfound[sp->hs_level] == 0)
- pu->times++;
- else {
- /*
- * Delete this score, do not count it,
- * do not pass go, do not collect $200.
- */
- num--;
- for (k = i; k < num; k++)
- hs[k] = hs[k + 1];
- continue;
- }
- }
- levelfound[sp->hs_level] = 1;
- i++, sp++;
- }
- return (num > MAXHISCORES ? MAXHISCORES : num);
-}
-
-/*
- * Show current scores. This must be called after savescore, if
- * savescore is called at all, for two reasons:
- * - Showscores munches the time field.
- * - Even if that were not the case, a new score must be recorded
- * before it can be shown anyway.
- */
-void
-showscores(int level)
-{
- struct highscore *sp;
- int i, n, c;
- const char *me;
- int levelfound[NLEVELS];
-
- if (!gotscores)
- getscores((FILE **)NULL);
- (void)printf("\n\t\t Tetris High Scores\n");
-
- /*
- * If level == 0, the person has not played a game but just asked for
- * the high scores; we do not need to check for printing in highlight
- * mode. If SOstr is null, we can't do highlighting anyway.
- */
- me = level && SOstr ? thisuser() : NULL;
-
- /*
- * Set times to 0 except for high score on each level.
- */
- for (i = MINLEVEL; i < NLEVELS; i++)
- levelfound[i] = 0;
- for (i = 0, sp = scores; i < nscores; i++, sp++) {
- if (levelfound[sp->hs_level])
- sp->hs_time = 0;
- else {
- sp->hs_time = 1;
- levelfound[sp->hs_level] = 1;
- }
- }
-
- /*
- * Page each screenful of scores.
- */
- for (i = 0, sp = scores; i < nscores; sp += n) {
- n = 20;
- if (i + n > nscores)
- n = nscores - i;
- printem(level, i + 1, sp, n, me);
- if ((i += n) < nscores) {
- (void)printf("\nHit RETURN to continue.");
- (void)fflush(stdout);
- while ((c = getchar()) != '\n')
- if (c == EOF)
- break;
- (void)printf("\n");
- }
- }
-
- if (nscores == 0)
- printf("\t\t\t - none to date.\n");
-}
-
-static void
-printem(int level, int offset, struct highscore *hs, int n, const char *me)
-{
- struct highscore *sp;
- int row, highlight, i;
- char buf[100];
-#define TITLE "Rank Score Name
(points/level)"
-#define TITL2
"=========================================================="
-
- printf("%s\n%s\n", TITLE, TITL2);
-
- highlight = 0;
-
- for (row = 0; row < n; row++) {
- sp = &hs[row];
- (void)snprintf(buf, sizeof(buf),
- "%3d%c %6d %-31s (%6d on %d)\n",
- row + offset, sp->hs_time ? '*' : ' ',
- sp->hs_score * sp->hs_level,
- sp->hs_name, sp->hs_score, sp->hs_level);
- /* Print leaders every three lines */
- if ((row + 1) % 3 == 0) {
- for (i = 0; i < sizeof(buf); i++)
- if (buf[i] == ' ')
- buf[i] = '_';
- }
- /*
- * Highlight if appropriate. This works because
- * we only get one score per level.
- */
- if (me != NULL &&
- sp->hs_level == level &&
- sp->hs_score == score &&
- strcmp(sp->hs_name, me) == 0) {
- putpad(SOstr);
- highlight = 1;
- }
- (void)printf("%s", buf);
- if (highlight) {
- putpad(SEstr);
- highlight = 0;
- }
- }
-}
Index: games/tetris/scores.h
===================================================================
RCS file: games/tetris/scores.h
diff -N games/tetris/scores.h
--- games/tetris/scores.h 16 Nov 2014 04:49:49 -0000 1.6
+++ /dev/null 1 Jan 1970 00:00:00 -0000
@@ -1,53 +0,0 @@
-/* $OpenBSD: scores.h,v 1.6 2014/11/16 04:49:49 guenther Exp $ */
-/* $NetBSD: scores.h,v 1.2 1995/04/22 07:42:40 cgd Exp $ */
-
-/*-
- * Copyright (c) 1992, 1993
- * The Regents of the University of California. All rights reserved.
- *
- * This code is derived from software contributed to Berkeley by
- * Chris Torek and Darren F. Provine.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. Neither the name of the University nor the names of its contributors
- * may be used to endorse or promote products derived from this software
- * without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
- * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
- * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
- * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
- * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
- * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
- * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- *
- * @(#)scores.h 8.1 (Berkeley) 5/31/93
- */
-
-/*
- * Tetris scores.
- */
-struct highscore {
- char hs_name[LOGIN_NAME_MAX]; /* login name */
- int hs_score; /* raw score */
- int hs_level; /* play level */
- time_t hs_time; /* time at game end */
-};
-
-#define MAXHISCORES 80
-#define MAXSCORES 9 /* maximum high score entries per person */
-#define EXPIRATION (5L * 365 * 24 * 60 * 60)
-
-void savescore(int);
-void showscores(int);
Index: games/tetris/tetris.6
===================================================================
RCS file: /cvs/src/games/tetris/tetris.6,v
retrieving revision 1.16
diff -u -p -r1.16 tetris.6
--- games/tetris/tetris.6 27 Jul 2015 18:48:04 -0000 1.16
+++ games/tetris/tetris.6 17 Nov 2015 04:50:55 -0000
@@ -40,7 +40,7 @@
.Nd the game of tetris
.Sh SYNOPSIS
.Nm tetris
-.Op Fl cps
+.Op Fl cp
.Op Fl k Ar keys
.Op Fl l Ar level
.Sh DESCRIPTION
@@ -97,8 +97,6 @@ Select a level of play.
.It Fl p
Switch on previewing of the shape that will appear next.
This penalizes your score.
-.It Fl s
-Display the top scores.
.El
.Sh PLAY
At the start of the game, a shape will appear at the top of the screen,
@@ -128,28 +126,6 @@ and your accumulated
.ie t points\(em200
.el points -- 200
points on level 3 gives you a score of 600.
-Each player gets at most one entry on any level,
-for a total of nine scores in the high scores file.
-Players who no longer have accounts are limited to one score.
-Also, scores over 5 years old are expired.
-The exception to these conditions is that the highest score on a given
-level is
-.Em always
-kept,
-so that following generations can pay homage to those who have
-wasted serious amounts of time.
-.Pp
-The score list is produced at the end of the game.
-The printout includes each player's overall ranking,
-name, score, and how many points were scored on what level.
-Scores which are the highest on a given level
-are marked with asterisks
-.Dq * .
-.Sh FILES
-.Bl -tag -width /var/games/tetris.scoresxx
-.It Pa /var/games/tetris.scores
-high score file
-.El
.Sh AUTHORS
.An -nosplit
Adapted from a 1989 International Obfuscated C Code Contest winner by
Index: games/tetris/tetris.c
===================================================================
RCS file: /cvs/src/games/tetris/tetris.c,v
retrieving revision 1.25
diff -u -p -r1.25 tetris.c
--- games/tetris/tetris.c 16 Nov 2014 04:49:49 -0000 1.25
+++ games/tetris/tetris.c 17 Nov 2015 04:50:55 -0000
@@ -51,7 +51,6 @@
#include <unistd.h>
#include "input.h"
-#include "scores.h"
#include "screen.h"
#include "tetris.h"
@@ -61,7 +60,6 @@ const struct shape *curshape;
const struct shape *nextshape;
long fallrate;
int score;
-gid_t gid, egid;
char key_msg[100];
int showpreview, classic;
@@ -157,14 +155,13 @@ main(int argc, char *argv[])
const char *errstr;
int ch, i, j;
- keys = "jkl pq";
+ if (pledge("stdio rpath tty", NULL) == -1)
+ err(1, "pledge");
- gid = getgid();
- egid = getegid();
- setegid(gid);
+ keys = "jkl pq";
classic = showpreview = 0;
- while ((ch = getopt(argc, argv, "ck:l:ps")) != -1)
+ while ((ch = getopt(argc, argv, "ck:l:p")) != -1)
switch(ch) {
case 'c':
/*
@@ -188,9 +185,6 @@ main(int argc, char *argv[])
case 'p':
showpreview = 1;
break;
- case 's':
- showscores(0);
- exit(0);
default:
usage();
}
@@ -337,15 +331,6 @@ main(int argc, char *argv[])
(int)(score * level * PRE_PENALTY));
score = score * PRE_PENALTY;
}
- savescore(level);
-
- printf("\nHit RETURN to see high scores, ^C to skip.\n");
-
- while ((i = getchar()) != '\n')
- if (i == EOF)
- break;
-
- showscores(level);
exit(0);
}
@@ -361,6 +346,6 @@ onintr(int signo)
void
usage(void)
{
- (void)fprintf(stderr, "usage: tetris [-cps] [-k keys] [-l level]\n");
+ (void)fprintf(stderr, "usage: tetris [-cp] [-k keys] [-l level]\n");
exit(1);
}
Index: games/tetris/tetris.h
===================================================================
RCS file: /cvs/src/games/tetris/tetris.h,v
retrieving revision 1.10
diff -u -p -r1.10 tetris.h
--- games/tetris/tetris.h 10 Aug 2008 12:23:25 -0000 1.10
+++ games/tetris/tetris.h 17 Nov 2015 04:50:55 -0000
@@ -167,7 +167,6 @@ extern long fallrate; /* less than 1 mil
#define PRE_PENALTY 0.75
extern int score; /* the obvious thing */
-extern gid_t gid, egid;
extern char key_msg[100];
extern int showpreview;