From 58592490738c25bcf1eaa6e884d35105d8db2076 Mon Sep 17 00:00:00 2001 From: Peter Avalos Date: Sun, 3 Sep 2006 23:23:10 +0000 Subject: [PATCH] Sync with NetBSD. Many fixes to include: -if getpwuid() returns null, print out the uid rather than dereferencing -Control -d by #ifdef DEBUG; adjust usage message accordingly -lseek to the beginning of the file in post() which may be called twice if a bonus occurs -add -t flag for slow terminals -convert to curses and general cleanups -security improvements which opens scorefile, then drops privs -use POSIX tty semantics --- games/snake/snake/Makefile | 8 +- games/snake/snake/move.c | 689 ---------------------------------- games/snake/snake/snake.6 | 8 +- games/snake/snake/snake.c | 440 +++++++++++++--------- games/snake/snake/snake.h | 89 ----- games/snake/snscore/snscore.c | 31 +- 6 files changed, 287 insertions(+), 978 deletions(-) delete mode 100644 games/snake/snake/move.c delete mode 100644 games/snake/snake/snake.h diff --git a/games/snake/snake/Makefile b/games/snake/snake/Makefile index e9befe2694..b139473fe5 100644 --- a/games/snake/snake/Makefile +++ b/games/snake/snake/Makefile @@ -1,12 +1,12 @@ # @(#)Makefile 8.1 (Berkeley) 5/31/93 # $FreeBSD: src/games/snake/snake/Makefile,v 1.5.2.3 2002/08/07 16:31:42 ru Exp $ -# $DragonFly: src/games/snake/snake/Makefile,v 1.2 2003/06/17 04:25:25 dillon Exp $ +# $DragonFly: src/games/snake/snake/Makefile,v 1.3 2006/09/03 23:23:10 pavalos Exp $ PROG= snake -SRCS= snake.c move.c +SRCS= snake.c MAN= snake.6 -DPADD= ${LIBM} ${LIBTERMCAP} ${LIBCOMPAT} -LDADD= -lm -ltermcap -lcompat +DPADD= ${LIBM} ${LIBCURSES} +LDADD= -lm -lcurses HIDEGAME=hidegame MLINKS= snake.6 snscore.6 diff --git a/games/snake/snake/move.c b/games/snake/snake/move.c deleted file mode 100644 index 35a3a097eb..0000000000 --- a/games/snake/snake/move.c +++ /dev/null @@ -1,689 +0,0 @@ -/* - * Copyright (c) 1980, 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. - * - * @(#)move.c 8.1 (Berkeley) 7/19/93 - * $FreeBSD: src/games/snake/snake/move.c,v 1.5.2.1 2000/08/17 06:21:44 jhb Exp $ - * $DragonFly: src/games/snake/snake/Attic/move.c,v 1.3 2004/07/27 07:37:39 asmodai Exp $ - */ - -/************************************************************************* - * - * MOVE LIBRARY - * - * This set of subroutines moves a cursor to a predefined - * location, independent of the terminal type. If the - * terminal has an addressable cursor, it uses it. If - * not, it optimizes for tabs (currently) even if you don't - * have them. - * - * At all times the current address of the cursor must be maintained, - * and that is available as structure cursor. - * - * The following calls are allowed: - * move(sp) move to point sp. - * up() move up one line. - * down() move down one line. - * bs() move left one space (except column 0). - * nd() move right one space(no write). - * clear() clear screen. - * home() home. - * ll() move to lower left corner of screen. - * cr() carriage return (no line feed). - * pr() just like standard printf, but keeps track - * of cursor position. (Uses pstring). - * apr() same as printf, but first argument is &point. - * (Uses pstring). - * pstring(s) output the string of printing characters. - * However, '\r' is interpreted to mean return - * to column of origination AND do linefeed. - * '\n' causes . - * putpad(str) calls tputs to output character with proper - * padding. - * outch() the output routine for a character used by - * tputs. It just calls putchar. - * pch(ch) output character to screen and update - * cursor address (must be a standard - * printing character). WILL SCROLL. - * pchar(ps,ch) prints one character if it is on the - * screen at the specified location; - * otherwise, dumps it.(no wrap-around). - * - * getcap() initializes strings for later calls. - * cap(string) outputs the string designated in the termcap - * data base. (Should not move the cursor.) - * done() returns the terminal to intial state and exits. - * - * point(&p,x,y) return point set to x,y. - * - * baudrate() returns the baudrate of the terminal. - * delay(t) causes an approximately constant delay - * independent of baudrate. - * Duration is ~ t/20 seconds. - * - ******************************************************************************/ - -#include -#include -#include -#include - -#include "snake.h" - -int CMlength; -int NDlength; -int BSlength; -int delaystr[10]; -short ospeed; - -static char str[80]; - -move(sp) -struct point *sp; -{ - int distance; - int tabcol,ct; - struct point z; - - if (sp->line <0 || sp->col <0 || sp->col > COLUMNS){ - pr("move to [%d,%d]?",sp->line,sp->col); - return; - } - if (sp->line >= LINES){ - move(point(&z,sp->col,LINES-1)); - while(sp->line-- >= LINES)putchar('\n'); - return; - } - - if (CM != 0) { - char *cmstr = tgoto(CM, sp->col, sp->line); - - CMlength = strlen(cmstr); - if(cursor.line == sp->line){ - distance = sp->col - cursor.col; - if(distance == 0)return; /* Already there! */ - if(distance > 0){ /* Moving to the right */ - if(distance*NDlength < CMlength){ - right(sp); - return; - } - if(TA){ - ct=sp->col&7; - tabcol=(cursor.col|7)+1; - do{ - ct++; - tabcol=(tabcol|7)+1; - } - while(tabcolcol); - if(ctcol < CMlength){ - cr(); - right(sp); - return; - } - /* No more optimizations on same row. */ - } - distance = sp->col - cursor.col; - distance = distance > 0 ? - distance*NDlength : -distance * BSlength; - if (distance < 0) - pr("ERROR: distance is negative: %d",distance); - distance += abs(sp->line - cursor.line); - if(distance >= CMlength){ - putpad(cmstr); - cursor.line = sp->line; - cursor.col = sp->col; - return; - } - } - - /* - * If we get here we have a terminal that can't cursor - * address but has local motions or one which can cursor - * address but can get there quicker with local motions. - */ - gto(sp); -} -gto(sp) -struct point *sp; -{ - - int distance,f,tfield; - - if (cursor.line > LINES || cursor.line <0 || - cursor.col <0 || cursor.col > COLUMNS) - pr("ERROR: cursor is at %d,%d\n", - cursor.line,cursor.col); - if (sp->line > LINES || sp->line <0 || - sp->col <0 || sp->col > COLUMNS) - pr("ERROR: target is %d,%d\n",sp->line,sp->col); - tfield = (sp->col) >> 3; - if (sp->line == cursor.line){ - if (sp->col > cursor.col)right(sp); - else{ - distance = (cursor.col -sp->col)*BSlength; - if (((TA) && - (distance > tfield+((sp->col)&7)*NDlength) - ) || - (((cursor.col)*NDlength) < distance) - ){ - cr(); - right(sp); - } - else{ - while(cursor.col > sp->col) bs(); - } - } - return; - } - /*must change row */ - if (cursor.col - sp->col > (cursor.col >> 3)){ - if (cursor.col == 0)f = 0; - else f = -1; - } - else f = cursor.col >> 3; - if (((sp->line << 1) + 1 < cursor.line - f) && (HO != 0)){ - /* - * home quicker than rlf: - * (sp->line + f > cursor.line - sp->line) - */ - putpad(HO); - cursor.col = cursor.line = 0; - gto(sp); - return; - } - if (((sp->line << 1) > cursor.line + LINES+1 + f) && (LL != 0)){ - /* home,rlf quicker than lf - * (LINES+1 - sp->line + f < sp->line - cursor.line) - */ - if (cursor.line > f + 1){ - /* is home faster than wraparound lf? - * (cursor.line + 20 - sp->line > 21 - sp->line + f) - */ - ll(); - gto(sp); - return; - } - } - if ((LL != 0) && (sp->line > cursor.line + (LINES >> 1) - 1)) - cursor.line += LINES; - while(sp->line > cursor.line)down(); - while(sp->line < cursor.line)up(); - gto(sp); /*can recurse since cursor.line = sp->line */ -} - -right(sp) -struct point *sp; -{ - int field,tfield; - int tabcol,strlength; - - if (sp->col < cursor.col) - pr("ERROR:right() can't move left\n"); - if(TA){ /* If No Tabs: can't send tabs because ttydrive - * loses count with control characters. - */ - field = cursor.col >> 3; -/* - * This code is useful for a terminal which wraps around on backspaces. - * (Mine does.) Unfortunately, this is not specified in termcap, and - * most terminals don't work that way. (Of course, most terminals - * have addressible cursors, too). - */ - if (BW && (CM == 0) && - ((sp->col << 1) - field > (COLUMNS - 8) << 1 ) - ){ - if (cursor.line == 0){ - outch('\n'); - } - outch('\r'); - cursor.col = COLUMNS + 1; - while(cursor.col > sp->col)bs(); - if (cursor.line != 0) outch('\n'); - return; - } - - tfield = sp->col >> 3; - - while (field < tfield){ - putpad(TA); - cursor.col = ++field << 3; - } - tabcol = (cursor.col|7) + 1; - strlength = (tabcol - sp->col)*BSlength + 1; - /* length of sequence to overshoot */ - if (((sp->col - cursor.col)*NDlength > strlength) && - (tabcol < COLUMNS) - ){ - /* - * Tab past and backup - */ - putpad(TA); - cursor.col = (cursor.col | 7) + 1; - while(cursor.col > sp->col)bs(); - } - } - while (sp->col > cursor.col){ - nd(); - } -} - -cr(){ - outch('\r'); - cursor.col = 0; -} - -clear(){ - int i; - - if (CL){ - putpad(CL); - cursor.col=cursor.line=0; - } else { - for(i=0; i= LINES)cursor.line=LINES-1; -} -bs(){ - if (cursor.col > 0){ - putpad(BS); - cursor.col--; - } -} - -nd(){ - putpad(ND); - cursor.col++; - if (cursor.col == COLUMNS+1){ - cursor.line++; - cursor.col = 0; - if (cursor.line >= LINES)cursor.line=LINES-1; - } -} - -pch(c) -{ - outch(c); - if(++cursor.col >= COLUMNS && AM) { - cursor.col = 0; - ++cursor.line; - } -} - -void -apr(struct point *ps, const char *fmt, ...) -{ - struct point p; - va_list ap; - - p.line = ps->line+1; p.col = ps->col+1; - move(&p); - va_start(ap, fmt); - (void)vsprintf(str, fmt, ap); - va_end(ap); - pstring(str); -} - -void -pr(const char *fmt, ...) -{ - va_list ap; - - va_start(ap, fmt); - (void)vsprintf(str, fmt, ap); - va_end(ap); - pstring(str); -} - -pstring(s) -char *s;{ - struct point z; - int stcol; - - stcol = cursor.col; - while (s[0] != '\0'){ - switch (s[0]){ - case '\n': - move(point(&z,0,cursor.line+1)); - break; - case '\r': - move(point(&z,stcol,cursor.line+1)); - break; - case '\t': - z.col = (((cursor.col + 8) >> 3) << 3); - z.line = cursor.line; - move(&z); - break; - case '\b': - bs(); - break; - case CTRL('g'): - outch(CTRL('g')); - break; - default: - if (s[0] < ' ')break; - pch(s[0]); - } - s++; - } -} - -pchar(ps,ch) -struct point *ps; -char ch;{ - struct point p; - p.col = ps->col + 1; p.line = ps->line + 1; - if ( - (p.col >= 0) && - (p.line >= 0) && - ( - ( - (p.line < LINES) && - (p.col < COLUMNS) - ) || - ( - (p.col == COLUMNS) && - (p.line < LINES-1) - ) - ) - ){ - move(&p); - pch(ch); - } -} - - -outch(c) -{ - putchar(c); -} - -putpad(str) -char *str; -{ - if (str) - tputs(str, 1, outch); -} - -#if 0 -baudrate() -{ - - switch (orig.sg_ospeed){ - case B300: - return(300); - case B1200: - return(1200); - case B4800: - return(4800); - case B9600: - return(9600); - default: - return(0); - } -} -#endif - -delay(t) -unsigned int t; -{ - while (usleep(t*50000U) == -1 && errno == EINTR) ; -} - -done() -{ - cook(); - exit(0); -} - -cook() -{ - delay(1); - putpad(TE); - putpad(KE); - putpad(VE); - fflush(stdout); - stty(0, &orig); -#ifdef TIOCSLTC - ioctl(0, TIOCSLTC, &olttyc); -#endif -} - -raw() -{ - stty(0, &new); -#ifdef TIOCSLTC - ioctl(0, TIOCSLTC, &nlttyc); -#endif -} - -struct point *point(ps,x,y) -struct point *ps; -int x,y; -{ - ps->col=x; - ps->line=y; - return(ps); -} - -char *ap; - -getcap() -{ - char *getenv(); - char *term; - char *xPC; - void stop(); -#ifdef TIOCGWINSZ - struct winsize win; -#endif - - term = getenv("TERM"); - if (term==0) { - fprintf(stderr, "No TERM in environment\n"); - exit(1); - } - - switch (tgetent(tbuf, term)) { - case -1: - fprintf(stderr, "Cannot open termcap file\n"); - exit(2); - case 0: - fprintf(stderr, "%s: unknown terminal", term); - exit(3); - } - - ap = tcapbuf; - -#ifdef TIOCGWINSZ - if (ioctl(0, TIOCGWINSZ, (char *) &win) < 0 || - (LINES = win.ws_row) == 0 || (COLUMNS = win.ws_col) == 0) { -#endif - LINES = tgetnum("li"); - COLUMNS = tgetnum("co"); -#ifdef TIOCGWINSZ - } -#endif - if (!lcnt) - lcnt = LINES - 2; - if (!ccnt) - ccnt = COLUMNS - 3; - - AM = tgetflag("am"); - BW = tgetflag("bw"); - - ND = tgetstr("nd", &ap); - UP = tgetstr("up", &ap); - - DO = tgetstr("do", &ap); - if (DO == 0) - DO = "\n"; - - BS = tgetstr("bc", &ap); - if (BS == 0 && tgetflag("bs")) - BS = "\b"; - if (BS) - xBC = *BS; - - TA = tgetstr("ta", &ap); - if (TA == 0 && tgetflag("pt")) - TA = "\t"; - - HO = tgetstr("ho", &ap); - CL = tgetstr("cl", &ap); - CM = tgetstr("cm", &ap); - LL = tgetstr("ll", &ap); - - KL = tgetstr("kl", &ap); - KR = tgetstr("kr", &ap); - KU = tgetstr("ku", &ap); - KD = tgetstr("kd", &ap); - if (KL) - Klength = strlen(KL); - else - Klength = strlen(KL); - /* - * NOTE: If KL, KR, KU, and KD are not - * all the same length, some problems - * may arise, since tests are made on - * all of them together. - */ - - TI = tgetstr("ti", &ap); - TE = tgetstr("te", &ap); - KS = tgetstr("ks", &ap); - KE = tgetstr("ke", &ap); - - VI = tgetstr("vi", &ap); - VE = tgetstr("ve", &ap); - - xPC = tgetstr("pc", &ap); - if (xPC) - PC = *xPC; - - if (ND) - NDlength = strlen(ND); - else - NDlength = 0; - - if (BS) - BSlength = strlen(BS); - else - BSlength = 0; - - if ((CM == 0) && - (HO == 0 || DO == 0 || UP==0 || BS==0 || ND==0)) - { - /* XXX as written in rev.1.6, we can assert(DO) */ - fprintf(stderr, "Terminal must have addressible "); - fprintf(stderr, "cursor or home + 4 local motions\n"); - exit(5); - } - if (tgetflag("os")) { - fprintf(stderr, "Terminal must not overstrike\n"); - exit(5); - } - if (LINES <= 0 || COLUMNS <= 0) { - fprintf(stderr, "Must know the screen size\n"); - exit(5); - } - - gtty(0, &orig); - new=orig; - new.sg_flags &= ~(ECHO|CRMOD|ALLDELAY|XTABS); - new.sg_flags |= CBREAK; - signal(SIGINT,stop); - ospeed = orig.sg_ospeed; -#ifdef TIOCGLTC - ioctl(0, TIOCGLTC, &olttyc); - nlttyc = olttyc; - nlttyc.t_suspc = '\377'; - nlttyc.t_dsuspc = '\377'; -#endif - raw(); - - if ((orig.sg_flags & XTABS) == XTABS) TA=0; - putpad(KS); - putpad(TI); - point(&cursor,0,LINES-1); -} diff --git a/games/snake/snake/snake.6 b/games/snake/snake/snake.6 index cbc6860fdb..2d361ae44e 100644 --- a/games/snake/snake/snake.6 +++ b/games/snake/snake/snake.6 @@ -31,7 +31,7 @@ .\" .\" @(#)snake.6 8.1 (Berkeley) 5/31/93 .\" $FreeBSD: src/games/snake/snake/snake.6,v 1.4.2.1 2001/07/22 11:01:23 dd Exp $ -.\" $DragonFly: src/games/snake/snake/snake.6,v 1.2 2003/06/17 04:25:25 dillon Exp $ +.\" $DragonFly: src/games/snake/snake/snake.6,v 1.3 2006/09/03 23:23:10 pavalos Exp $ .\" .TH SNAKE 6 "May 31, 1993" .UC 4 @@ -43,6 +43,8 @@ snake, snscore \- display chase game .B -w width ] [ .B -l length +] [ +.B -t ] .br .B snscore @@ -54,7 +56,9 @@ getting eaten by the snake. The and .B \-w options allow you to specify the length and width of the field. -By default the entire screen (except for the last column) is used. +By default the entire screen is used. The +.B \-t +option makes the game assume you are on a slow terminal. .PP You are represented on the screen by an I. The snake is 6 squares long and is represented by S's. diff --git a/games/snake/snake/snake.c b/games/snake/snake/snake.c index 8bb2374d00..fcf0730daa 100644 --- a/games/snake/snake/snake.c +++ b/games/snake/snake/snake.c @@ -33,7 +33,7 @@ * @(#) Copyright (c) 1980, 1993 The Regents of the University of California. All rights reserved. * @(#)snake.c 8.2 (Berkeley) 1/7/94 * $FreeBSD: src/games/snake/snake/snake.c,v 1.11.2.1 2000/08/17 06:21:44 jhb Exp $ - * $DragonFly: src/games/snake/snake/snake.c,v 1.2 2003/06/17 04:25:25 dillon Exp $ + * $DragonFly: src/games/snake/snake/snake.c,v 1.3 2006/09/03 23:23:10 pavalos Exp $ */ /* @@ -49,16 +49,31 @@ #include -#include +#include #include #include #include #include #include +#include +#include +#include +#include +#include +#include +#include +#include -#include "snake.h" #include "pathnames.h" +#define cashvalue chunk*(loot-penalty)/25 + +struct point { + int col, line; +}; + +#define same(s1, s2) ((s1)->line == (s2)->line && (s1)->col == (s2)->col) + #define PENALTY 10 /* % penalty for invoking spacewarp */ #define EOT '\004' @@ -71,7 +86,12 @@ #define TREASURE '$' #define GOAL '#' -#define BSIZE 80 +#ifndef MIN +#define MIN(a, b) ((a) < (b) ? (a) : (b)) +#endif + +#define pchar(point, c) mvaddch((point)->line + 1, (point)->col + 1, (c)) +#define delay(t) usleep(t * 50000); struct point you; struct point money; @@ -79,40 +99,65 @@ struct point finish; struct point snake[6]; int loot, penalty; -int long tl, tm=0L; int moves; -char stri[BSIZE]; -char *p; -char ch, savec; -char *kl, *kr, *ku, *kd; -int fast=1; -int repeat=1; -long tv; -char *tn; +int fast = 1; int rawscores; FILE *logfile; +int lcnt, ccnt; /* user's idea of screen size */ +int chunk; /* amount of money given at a time */ + +void chase(struct point *, struct point *); +int chk(const struct point *); +void drawbox(void); +void flushi(void); +void home(void); +void length(int); +void logit(const char *); +int main(int, char **); +void mainloop(void) __attribute__((__noreturn__)); +struct point *point(struct point *, int, int); +int post(int, int); +int pushsnake(void); +void right(const struct point *); +void setup(void); +void snap(void); +void snrand(struct point *); +void spacewarp(int); +void stop(int) __attribute__((__noreturn__)); +int stretch(const struct point *); +void surround(struct point *); +void suspend(void); +void win(const struct point *); +void winnings(int); + main(argc,argv) int argc; char **argv; { - extern char *optarg; - extern int optind; int ch, i; - void stop(); + time_t tv; + /* Open score files then revoke setgid privileges */ rawscores = open(_PATH_RAWSCORES, O_RDWR|O_CREAT, 0664); + if (rawscores < 0) { + warn("open %s", _PATH_RAWSCORES); + sleep(2); + } else if (rawscores < 3) + exit(1); logfile = fopen(_PATH_LOGFILE, "a"); - - /* revoke privs */ + if (logfile == NULL) { + warn("fopen %s", _PATH_LOGFILE); + sleep(2); + } setgid(getgid()); - srandomdev(); + (void) time(&tv); - while ((ch = getopt(argc, argv, "l:w:")) != -1) - switch((char)ch) { -#ifdef notdef + while ((ch = getopt(argc, argv, "l:w:t")) != -1) + switch ((char) ch) { +#ifdef DEBUG case 'd': tv = atol(optarg); break; @@ -123,20 +168,37 @@ char **argv; case 'l': /* length */ lcnt = atoi(optarg); break; + case 't': + fast = 0; + break; case '?': default: - fputs("usage: snake [-d seed] [-w width] [-l length]\n", stderr); +#ifdef DEBUG + fputs("usage: snake [-d seed] [-w width] [-l length] [-t]\n", stderr); +#else + fputs("usage: snake [-w width] [-l length] [-t]\n", stderr); +#endif exit(1); } + srandom((int) tv); + penalty = loot = 0; - getcap(); + initscr(); + cbreak(); + noecho(); +#ifdef KEY_LEFT + keypad(stdscr, TRUE); +#endif + if (!lcnt || lcnt > LINES - 2) + lcnt = LINES - 2; + if (!ccnt || ccnt > COLS - 2) + ccnt = COLS - 2; i = MIN(lcnt, ccnt); if (i < 4) { - cook(); - pr("snake: screen too small for a fair game.\n"); - exit(1); + endwin(); + errx(1, "screen too small for a fair game."); } /* @@ -163,84 +225,54 @@ char **argv; chunk = (675.0 / (i+6)) + 2.5; /* min screen edge */ signal (SIGINT, stop); - putpad(TI); /* String to begin programs that use cm */ - putpad(KS); /* Put terminal in keypad transmit mode */ - putpad(VI); /* Hide cursor */ snrand(&finish); snrand(&you); snrand(&money); snrand(&snake[0]); - if ((orig.sg_ospeed < B9600) || - ((! CM) && (! TA))) fast=0; for(i=1;i<6;i++) chase (&snake[i], &snake[i-1]); setup(); mainloop(); + /* NOTREACHED */ + return (0); +} + +struct point * +point(ps, x, y) + struct point *ps; + int x, y; +{ + ps->col = x; + ps->line = y; + return (ps); } /* Main command loop */ +void mainloop() { - int j, k; + int k; + int repeat = 1; + int lastc = 0; for (;;) { - int c,lastc,match; - - move(&you); - fflush(stdout); - if (((c = getchar() & 0177) <= '9') && (c >= '0')) { - ungetc(c,stdin); - j = scanf("%d",&repeat); - c = getchar() & 0177; + int c; + + /* Highlight you, not left & above */ + move(you.line + 1, you.col + 1); + refresh(); + if (((c = getch()) <= '9') && (c >= '0')) { + repeat = c - '0'; + while (((c = getch()) <= '9') && (c >= '0')) + repeat = 10 * repeat + (c - '0'); } else { if (c != '.') repeat = 1; } if (c == '.') { c = lastc; } - if ((Klength > 0) && - (c == *KL || c == *KR || c == *KU || c == *KD)) { - savec = c; - match = 0; - kl = KL; - kr = KR; - ku = KU; - kd = KD; - for (j=Klength;j>0;j--){ - if (match != 1) { - match = 0; - if (*kl++ == c) { - ch = 'h'; - match++; - } - if (*kr++ == c) { - ch = 'l'; - match++; - } - if (*ku++ == c) { - ch = 'k'; - match++; - } - if (*kd++ == c) { - ch = 'j'; - match++; - } - if (match == 0) { - ungetc(c,stdin); - ch = savec; - /* Oops! - * This works if we figure it out on second character. - */ - break; - } - } - savec = c; - if(j != 1) c = getchar() & 0177; - } - c = ch; - } if (!fast) flushi(); lastc = c; switch (c){ @@ -250,10 +282,10 @@ mainloop() case EOT: case 'x': case 0177: /* del or end of file */ - ll(); + endwin(); length(moves); logit("quit"); - done(); + exit(0); case CTRL('l'): setup(); winnings(cashvalue); @@ -307,6 +339,9 @@ mainloop() switch(c) { case 's': case 'h': +#ifdef KEY_LEFT + case KEY_LEFT: +#endif case '\b': if (you.col >0) { if((fast)||(k == 1)) @@ -319,6 +354,9 @@ mainloop() break; case 'f': case 'l': +#ifdef KEY_RIGHT + case KEY_RIGHT: +#endif case ' ': if (you.col < ccnt-1) { if((fast)||(k == 1)) @@ -332,6 +370,9 @@ mainloop() case CTRL('p'): case 'e': case 'k': +#ifdef KEY_UP + case KEY_UP: +#endif case 'i': if (you.line > 0) { if((fast)||(k == 1)) @@ -345,6 +386,9 @@ mainloop() case CTRL('n'): case 'c': case 'j': +#ifdef KEY_DOWN + case KEY_DOWN: +#endif case LF: case 'm': if (you.line+1 < lcnt) { @@ -375,18 +419,17 @@ mainloop() if (same(&you,&finish)) { win(&finish); - ll(); - cook(); - pr("You have won with $%d.\n",cashvalue); + flushi(); + endwin(); + printf("You have won with $%d.\n", cashvalue); fflush(stdout); logit("won"); post(cashvalue,1); length(moves); - done(); + exit(0); } if (pushsnake())break; } - fflush(stdout); } } @@ -395,7 +438,7 @@ setup(){ /* */ int i; - clear(); + erase(); pchar(&you,ME); pchar(&finish,GOAL); pchar(&money,TREASURE); @@ -404,33 +447,21 @@ setup(){ /* } pchar(&snake[0], SNAKEHEAD); drawbox(); - fflush(stdout); + refresh(); } +void drawbox() { int i; - struct point p; - p.line = -1; - for (i= 0; i oldbest ? 1 : 0); + } /* Update this jokers best */ if (score > oldbest) { lseek(rawscores, ((off_t)uid)*sizeof(short), 0); write(rawscores, &score, sizeof(short)); - pr("You bettered your previous best of $%d\n", oldbest); + printf("You bettered your previous best of $%d\n", oldbest); } else - pr("Your best to date is $%d\n", oldbest); + printf("Your best to date is $%d\n", oldbest); /* See if we have a new champ */ p = getpwuid(allbwho); - if (p == NULL || score > allbscore) { - lseek(rawscores, (off_t)0, 0); + if (score > allbscore) { + lseek(rawscores, 0, SEEK_SET); write(rawscores, &score, sizeof(short)); write(rawscores, &uid, sizeof(short)); - if (allbwho) - pr("You beat %s's old record of $%d!\n", + if (allbwho) { + if (p) + printf("You beat %s's old record of $%d!\n", p->pw_name, allbscore); else - pr("You set a new record!\n"); - } else - pr("The highest is %s with $%d\n", p->pw_name, allbscore); - close(rawscores); + printf("You beat (%d)'s old record of $%d!\n", + (int)allbwho, allbscore); + } + else + printf("You set a new record!\n"); + } else if (p) + printf("The highest is %s with $%d\n", p->pw_name, allbscore); + else + printf("The highest is (%d) with $%d\n", (int)allbwho, + allbscore); + lseek(rawscores, 0, SEEK_SET); return (1); } @@ -524,7 +570,7 @@ int iscore, flag; */ flushi() { - stty(0, &new); + tcflush(0, TCIFLUSH); } int mx [8] = { 0, 1, 1, 1, 0,-1,-1,-1}; @@ -579,14 +625,14 @@ struct point *sp, *np; } for(w=i=0; i<8; i++) w+= wt[i]; - vp = random() % w; + vp = ((random() >> 6) & 01777) % w; for(i=0; i<8; i++) if (vp lcnt-4){ - pchar(point(&p,you.col,lcnt-1),'_'); + if (you.line > lcnt - 4) { + mvaddch(lcnt, you.col + 1, '_'); } - if(you.col < 10){ - pchar(point(&p,0,you.line),'('); + if (you.col < 10) { + mvaddch(you.line + 1, 1, '('); } - if(you.col > ccnt-10){ - pchar(point(&p,ccnt-1,you.line),')'); + if (you.col > ccnt - 10) { + mvaddch(you.line + 1, ccnt, ')'); } - if (! stretch(&money)) if (! stretch(&finish)) delay(10); - if(you.line < 3){ - point(&p,you.col,0); +#endif + if (!stretch(&money)) + if (!stretch(&finish)) { + pchar(&you, '?'); + refresh(); + delay(10); + pchar(&you, ME); + } +#if 0 + if (you.line < 3) { + point(&p, you.col, 0); chk(&p); } if(you.line > lcnt-4){ @@ -657,40 +714,47 @@ snap() point(&p,ccnt-1,you.line); chk(&p); } - fflush(stdout); +#endif + refresh(); } stretch(ps) -struct point *ps;{ +const struct point *ps;{ struct point p; point(&p,you.col,you.line); - if(abs(ps->col-you.col) < 6){ + if ((abs(ps->col - you.col) < (ccnt / 12)) && (you.line != ps->line)) { if(you.line < ps->line){ for (p.line = you.line+1;p.line <= ps->line;p.line++) pchar(&p,'v'); + refresh(); delay(10); for (;p.line > you.line;p.line--) chk(&p); } else { for (p.line = you.line-1;p.line >= ps->line;p.line--) pchar(&p,'^'); + refresh(); delay(10); for (;p.line < you.line;p.line++) chk(&p); } return(1); - } else if(abs(ps->line-you.line) < 3){ + } else + if ((abs(ps->line - you.line) < (lcnt/7)) + && (you.col != ps->col)) { p.line = you.line; if(you.col < ps->col){ for (p.col = you.col+1;p.col <= ps->col;p.col++) pchar(&p,'>'); + refresh(); delay(10); for (;p.col > you.col;p.col--) chk(&p); } else { for (p.col = you.col-1;p.col >= ps->col;p.col--) pchar(&p,'<'); + refresh(); delay(10); for (;p.col < you.col;p.col++) chk(&p); @@ -702,31 +766,44 @@ struct point *ps;{ surround(ps) struct point *ps;{ - struct point x; int j; if(ps->col == 0)ps->col++; if(ps->line == 0)ps->line++; if(ps->line == LINES -1)ps->line--; - if(ps->col == COLUMNS -1)ps->col--; - apr(point(&x,ps->col-1,ps->line-1),"/*\\\r* *\r\\*/"); + if(ps->col == COLS -1)ps->col--; + mvaddstr(ps->line, ps->col, "/*\\"); + mvaddstr(ps->line + 1, ps->col, "* *"); + mvaddstr(ps->line + 2, ps->col, "\\*/"); for (j=0;j<20;j++){ pchar(ps,'@'); + refresh(); delay(1); pchar(ps,' '); + refresh(); delay(1); } if (post(cashvalue,0)) { - apr(point(&x,ps->col-1,ps->line-1)," \ro.o\r\\_/"); + mvaddstr(ps->line, ps->col, " "); + mvaddstr(ps->line + 1, ps->col, "o.o"); + mvaddstr(ps->line + 2, ps->col, "\\_/"); + refresh(); delay(6); - apr(point(&x,ps->col-1,ps->line-1)," \ro.-\r\\_/"); + mvaddstr(ps->line, ps->col, " "); + mvaddstr(ps->line + 1, ps->col, "o.-"); + mvaddstr(ps->line + 2, ps->col, "\\_/"); + refresh(); delay(6); } - apr(point(&x,ps->col-1,ps->line-1)," \ro.o\r\\_/"); + mvaddstr(ps->line, ps->col, " "); + mvaddstr(ps->line + 1, ps->col, "o.o"); + mvaddstr(ps->line + 2, ps->col, "\\_/"); + refresh(); + delay(6); } win(ps) -struct point *ps; +const struct point *ps; { struct point x; int j,k; @@ -752,14 +829,16 @@ struct point *ps; pchar(&x,'#'); x.col--; } + refresh(); + delay(1); } - fflush(stdout); } pushsnake() { int i, bonus; int issame = 0; + struct point tmp; /* * My manual says times doesn't return a value. Furthermore, the @@ -772,6 +851,9 @@ pushsnake() issame++; if (!issame) pchar(&snake[5],' '); + /* Need the following to catch you if you step on the snake's tail */ + tmp.col = snake[5].col; + tmp.line = snake[5].line; for(i=4; i>=0; i--) snake[i+1]= snake[i]; chase(&snake[0], &snake[1]); @@ -779,13 +861,13 @@ pushsnake() pchar(&snake[0],SNAKEHEAD); for(i=0; i<6; i++) { - if (same(&snake[i],&you)) + if (same(&snake[i],&you) || same(&tmp, &you)) { surround(&you); i = (cashvalue) % 10; - bonus = random() % 10; - ll(); - pr("%d\n", bonus); + bonus = ((random() >> 8) & 0377) % 10; + mvprintw(lcnt + 1, 0, "%d\n", bonus); + refresh(); delay(30); if (bonus == i) { spacewarp(1); @@ -793,23 +875,25 @@ pushsnake() flushi(); return(1); } + flushi(); + endwin(); if ( loot >= penalty ){ - pr("You and your $%d have been eaten\n", + printf("\nYou and your $%d have been eaten\n", cashvalue); } else { - pr("The snake ate you. You owe $%d.\n", + printf("\nThe snake ate you. You owe $%d.\n", -cashvalue); } logit("eaten"); length(moves); - done(); + exit(0); } } return(0); } chk(sp) -struct point *sp; +const struct point *sp; { int j; @@ -846,41 +930,35 @@ struct point *sp; winnings(won) int won; { - struct point p; - - p.line = p.col = 1; - if(won>0){ - move(&p); - pr("$%d",won); + if (won > 0) { + mvprintw(1, 1, "$%d", won); } } void -stop(){ +stop(dummy){ signal(SIGINT,SIG_IGN); - ll(); + endwin(); length(moves); - done(); + exit(0); } suspend() { - ll(); - cook(); + endwin(); kill(getpid(), SIGTSTP); - raw(); - setup(); + refresh(); winnings(cashvalue); } length(num) int num; { - pr("You made %d moves.\n",num); + printf("You made %d moves.\n", num); } logit(msg) -char *msg; +const char *msg; { time_t t; @@ -888,6 +966,6 @@ char *msg; time(&t); fprintf(logfile, "%s $%d %dx%d %s %s", getlogin(), cashvalue, lcnt, ccnt, msg, ctime(&t)); - fclose(logfile); + fflush(logfile); } } diff --git a/games/snake/snake/snake.h b/games/snake/snake/snake.h deleted file mode 100644 index f76da49487..0000000000 --- a/games/snake/snake/snake.h +++ /dev/null @@ -1,89 +0,0 @@ -/* - * Copyright (c) 1980, 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. - * - * @(#)snake.h 8.1 (Berkeley) 5/31/93 - * - * $FreeBSD: src/games/snake/snake/snake.h,v 1.1.1.1.14.1 2000/08/17 06:21:44 jhb Exp $ - * $DragonFly: src/games/snake/snake/Attic/snake.h,v 1.2 2003/06/17 04:25:25 dillon Exp $ - */ - -# include -# include -# include -# include -# include -# include - -#define ESC '\033' - -struct tbuffer { - long t[4]; -} tbuffer; - -char *CL, *UP, *DO, *ND, *BS, - *HO, *CM, - *TA, *LL, - *KL, *KR, *KU, *KD, - *TI, *TE, *KS, *KE, - *VI, *VE; -int LINES, COLUMNS; /* physical screen size. */ -int lcnt, ccnt; /* user's idea of screen size */ -char xBC, PC; -int AM, BW; -char tbuf[1024], tcapbuf[128]; -char *tgetstr(), *tgoto(); -int Klength; /* length of KX strings */ -int chunk; /* amount of money given at a time */ -#ifdef debug -#define cashvalue (loot-penalty)/25 -#else -#define cashvalue chunk*(loot-penalty)/25 -#endif - -struct point { - int col, line; -}; -struct point cursor; -struct sgttyb orig, new; -#ifdef TIOCLGET -struct ltchars olttyc, nlttyc; -#endif -struct point *point(); -#if __STDC__ -void apr(struct point *, const char *, ...); -void pr(const char *, ...); -#else -void apr(); -void pr(); -#endif - -#define same(s1, s2) ((s1)->line == (s2)->line && (s1)->col == (s2)->col) diff --git a/games/snake/snscore/snscore.c b/games/snake/snscore/snscore.c index 212b2ce6fd..edce627c42 100644 --- a/games/snake/snscore/snscore.c +++ b/games/snake/snscore/snscore.c @@ -33,17 +33,19 @@ * @(#) Copyright (c) 1980, 1993 The Regents of the University of California. All rights reserved. * @(#)snscore.c 8.1 (Berkeley) 7/19/93 * $FreeBSD: src/games/snake/snscore/snscore.c,v 1.5 1999/11/30 03:49:42 billf Exp $ - * $DragonFly: src/games/snake/snscore/snscore.c,v 1.2 2003/06/17 04:25:25 dillon Exp $ + * $DragonFly: src/games/snake/snscore/snscore.c,v 1.3 2006/09/03 23:23:10 pavalos Exp $ */ #include +#include #include #include #include #include +#include #include "pathnames.h" -char *recfile = _PATH_RAWSCORES; +const char *recfile = _PATH_RAWSCORES; #define MAXPLAYERS 256 struct player { @@ -60,25 +62,27 @@ main() int noplayers; int i, j, notsorted; short whoallbest, allbest; - char *q; + const char *q; struct passwd *p; - fd = fopen(recfile, "r"); - - if (fd == NULL) { - perror(recfile); - exit(1); - } + /* Revoke setgid privileges */ + setgid(getgid()); + fd = fopen(recfile, "r"); + if (fd == NULL) + err(1, "opening `%s'", recfile); printf("Snake players scores to date\n"); - fread(&whoallbest, sizeof(short), 1, fd); + if (fread(&whoallbest, sizeof(short), 1, fd) == 0) { + printf("No scores recorded yet!\n"); + exit(0); + } fread(&allbest, sizeof(short), 1, fd); noplayers = 0; for (uid = 2; ;uid++) { if(fread(&score, sizeof(short), 1, fd) == 0) break; if (score > 0) { - if (noplayers > MAXPLAYERS) { + if (noplayers >= MAXPLAYERS) { printf("too many players\n"); exit(2); } @@ -88,8 +92,9 @@ main() if (p == NULL) continue; q = p -> pw_name; - players[noplayers].name = malloc(strlen(q) + 1); - strcpy(players[noplayers].name, q); + players[noplayers].name = strdup(q); + if (players[noplayers].name == NULL) + err(1, NULL); noplayers++; } } -- 2.41.0