summaryrefslogtreecommitdiffstats
path: root/warp/score.c
diff options
context:
space:
mode:
authorkamil <kamil@NetBSD.org>2020-11-09 23:37:05 +0000
committerkamil <kamil@NetBSD.org>2020-11-09 23:37:05 +0000
commita931697f3be302466855163a7e216ffee7766445 (patch)
tree0ac2ab10bd68f8317dcf403536f0d612730ef35c /warp/score.c
parent6d16c3b48f5f1f377e2be346c1189d9f8edac22d (diff)
downloadbsdgames-darwin-a931697f3be302466855163a7e216ffee7766445.tar.gz
bsdgames-darwin-a931697f3be302466855163a7e216ffee7766445.tar.zst
bsdgames-darwin-a931697f3be302466855163a7e216ffee7766445.zip
Add Warp Kit, Version 7.0 by Larry Wall
Warp is a real-time space war game that doesn't get boring very quickly. Read warp.doc and the manual page for more information. games/warp originally distributed with 4.3BSD-Reno, is back to the BSD world via NetBSD. Its remnants were still mentioned in games/Makefile. Larry Wall, the original author and the copyright holder, generously donated the game and copyright to The NetBSD Foundation, Inc. Import the game sources as-is from 4.3BSD-Reno, with the cession of the copyright and license to BSD-2-clause NetBSD-style. Signed-off-by: Larry Wall <larry@wall.org> Signed-off-by: Kamil Rytarowski <kamil@netbsd.org>
Diffstat (limited to 'warp/score.c')
-rw-r--r--warp/score.c727
1 files changed, 727 insertions, 0 deletions
diff --git a/warp/score.c b/warp/score.c
new file mode 100644
index 00000000..ad6b5a14
--- /dev/null
+++ b/warp/score.c
@@ -0,0 +1,727 @@
+/* $Header: /cvsroot/src/games/warp/score.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: score.c,v $
+/* Revision 1.1 2020/11/09 23:37:05 kamil
+/* Add Warp Kit, Version 7.0 by Larry Wall
+/*
+/* Warp is a real-time space war game that doesn't get boring very quickly.
+/* Read warp.doc and the manual page for more information.
+/*
+/* games/warp originally distributed with 4.3BSD-Reno, is back to the BSD
+/* world via NetBSD. Its remnants were still mentioned in games/Makefile.
+/*
+/* Larry Wall, the original author and the copyright holder, generously
+/* donated the game and copyright to The NetBSD Foundation, Inc.
+/*
+/* Import the game sources as-is from 4.3BSD-Reno, with the cession
+/* of the copyright and license to BSD-2-clause NetBSD-style.
+/*
+/* Signed-off-by: Larry Wall <larry@wall.org>
+/* Signed-off-by: Kamil Rytarowski <kamil@netbsd.org>
+/*
+ * Revision 7.0.1.2a 87/07/03 02:13:26 games
+ * Fixed numerous long vs. int bugs in printfs, etc.
+ *
+ * Revision 7.0.1.2 86/10/20 12:06:56 lwall
+ * Made all exits reset tty.
+ *
+ * Revision 7.0.1.1 86/10/16 10:52:47 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:13:14 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "intrp.h"
+#include "object.h"
+#include "play.h"
+#include "sig.h"
+#include "term.h"
+#include "us.h"
+#include "util.h"
+#include "weapon.h"
+#include "INTERN.h"
+#include "score.h"
+
+void
+score_init()
+{
+ Reg1 char *s;
+ Reg2 int i;
+ FILE *savfil;
+
+ if (stat(SAVEDIR,&filestat)) {
+ printf("Cannot access %s\r\n",SAVEDIR);
+ finalize(1);
+ }
+ if (filestat.st_uid != geteuid()) {
+ printf("Warp will not run right without being setuid.\r\n");
+ finalize(1);
+ }
+ if ((filestat.st_mode & 0605) != 0605) {
+ printf("%s is not protected correctly (must be u+rw o+rx).\r\n",SAVEDIR);
+ finalize(1);
+ }
+
+#ifdef SCOREFULL
+ interp(longlognam, sizeof longlognam, "%N");
+ for (i=strlen(longlognam); i<24; i++)
+ longlognam[i] = ' '; /* make sure it is 24 long for strncmp */
+ longlognam[24] = '\0';
+#else
+ interp(longlognam, sizeof longlognam, "%L");
+ for (i=strlen(longlognam); i<8; i++)
+ longlognam[i] = ' '; /* make sure it is 8 long for strncmp */
+ longlognam[8] = '\0';
+#endif
+
+ if (scorespec)
+ wscore();
+
+ Sprintf(savefilename, "save.%s", logname);
+
+ savfil = experimenting ? NULL : fopen(savefilename,"r");
+ if (savfil != NULL && fgets(spbuf,100,savfil) != NULL) {
+ char tmpbuf[80];
+
+ spbuf[strlen(spbuf)-1] = '\0';
+ if (fgets(tmpbuf,80,savfil) != NULL) {
+ int processnum;
+
+ tmpbuf[strlen(tmpbuf)-1] = '\0';
+ printf("You seem to have left a game %s.\r\n",tmpbuf+9);
+ s = index(tmpbuf+9, ',');
+ *s = '\0';
+ processnum = atoi(s+11);
+ if (kill(processnum, SIGINT)) {
+ /* does process not exist? */
+ /* (warp ignores SIGINT) */
+ printf("\r\n\
+That process does not seem to exist anymore, so you'll have to start the\r\n");
+ printf(
+"last wave over.\r\n\n");
+ printf(
+" [type anything to continue]");
+ Fflush(stdout);
+ eat_typeahead();
+ getcmd(tmpbuf);
+ if (*tmpbuf == INTRCH)
+ finalize(0);
+ printf("\r\n");
+ }
+ else {
+ if (strcmp(term+8,tmpbuf+23)) {
+ printf(
+"That is not your current terminal--you are on %s.\r\n", term+5);
+ printf("\r\nYour options:\r\n");
+ printf(" 1) Exit and find the terminal it's running on\r\n");
+ }
+ else {
+ printf("\r\nYour options:\r\n");
+ printf(" 1) Exit and try to foreground it\r\n");
+ }
+ printf(" 2) Let me terminate the other game\r\n\n");
+ printf("What do you want to do? ");
+ Fflush(stdout);
+ eat_typeahead();
+ getcmd(tmpbuf);
+ printf("\r\n");
+ if (*tmpbuf == INTRCH)
+ finalize(0);
+ if (*tmpbuf == '1') {
+ printf(
+"If you don't succeed, come back and do option 2 instead. Good luck.\r\n");
+ finalize(0);
+ }
+ printf(
+"Ok, hang on a few moments \r\n");
+ Fclose(savfil);
+ if (kill(processnum, SIGQUIT)) {
+ printf("Unable to kill process #%d!\r\n",processnum);
+ roundsleep(2);
+ }
+ else {
+#ifdef SIGCONT
+ kill(processnum, SIGCONT);
+#endif
+ for (i=15; i; --i) {
+ sleep(1);
+ if (kill(processnum,SIGINT))
+ /* does process not exist? */
+ /* (warp ignores SIGINT) */
+ break;
+ }
+ didkill++;
+ }
+ savfil = fopen(savefilename,"r");
+ if (savfil != NULL) {
+ Fgets(spbuf,100,savfil);
+ }
+ }
+ }
+ }
+ else
+ savfil = NULL;
+ if (savfil == NULL) {
+ totalscore = smarts = cumsmarts = wave = 0;
+ numents = 5;
+ numbases = 3;
+ }
+ else {
+ totalscore = atol(spbuf+9);
+ smarts = atoi(spbuf+20);
+ cumsmarts = atoi(spbuf+24);
+ numents = atoi(spbuf+30);
+ numbases = atoi(spbuf+33);
+ wave = atoi(spbuf+36);
+ apolspec = (spbuf[40] == 'a');
+ beginner = (spbuf[41] == 'b');
+ crushspec = (spbuf[42] == 'c');
+ gornspec = (spbuf[43] == 'g');
+ massacre = (spbuf[44] == 'm');
+ romspec = (spbuf[45] == 'r');
+ tholspec = (spbuf[46] == 't');
+ lowspeed = (spbuf[47] == 'l') || lowspeed;
+ amoebaspec = (spbuf[48] == '&');
+ Fclose(savfil);
+ }
+
+ if (!ismarts) {
+ ismarts = 1;
+ clear();
+ page(NEWSFILE,FALSE);
+ if (smarts) {
+ printf("\r\nSaved game: SCORE DIFF CUMDIFF ENTERPRISES BASES WAVE");
+ printf("\r\n %7ld %2d %4d %1d %1d %3d",
+ totalscore,smarts,cumsmarts,numents,numbases,wave);
+ }
+ printf("\r\nWould you like instructions? ");
+ Fflush(stdout);
+ eat_typeahead();
+ getcmd(buf);
+ printf("\r\n");
+ if (*buf == INTRCH)
+ finalize(0);
+ if (*buf == 'Y' || *buf == 'y') {
+ page(HELPFILE,FALSE);
+ printf("\r\nWould you like to play easy games for a while? ");
+ Fflush(stdout);
+ eat_typeahead();
+ getcmd(buf);
+ printf("\r\n");
+ if (*buf == 'Y' || *buf == 'y') {
+ beginner = TRUE;
+ lowspeed = TRUE;
+ }
+ }
+ }
+ if (!smarts)
+ smarts = ismarts;
+}
+
+void
+wscore()
+{
+ clear();
+ printf(" TOP WARPISTS\r\n\n");
+ printf("RANK WHO AKA SCORE DIFF CUMDIFF WHEN\r\n");
+ page(SCOREBOARD,TRUE);
+ printf(" [Type anything to continue]");
+ Fflush(stdout);
+ getcmd(spbuf);
+ if (*spbuf == INTRCH)
+ finalize(0);
+ clear();
+ printf(" TOP LOW-SPEED WARPISTS\r\n\n");
+ printf("RANK WHO AKA SCORE DIFF CUMDIFF WHEN\r\n");
+ page(LSCOREBOARD,TRUE);
+ printf(" [Type anything to continue]");
+ Fflush(stdout);
+ getcmd(spbuf);
+ if (*spbuf == INTRCH)
+ finalize(0);
+ clear();
+ printf(" TOP FUNNY WARPISTS\r\n\n");
+ printf("RANK WHO AKA SCORE DIFF CUMDIFF WHEN\r\n");
+ page(FSCOREBOARD,TRUE);
+ printf(" [Type anything to continue]");
+ Fflush(stdout);
+ getcmd(spbuf);
+ if (*spbuf == INTRCH)
+ finalize(0);
+ clear();
+ printf(" GAMES SAVED OR IN PROGRESS\r\n\n");
+ printf("WHO SCORE DF CDF E B WV FLAGS\r\n");
+ resetty();
+ Sprintf(spbuf,"/bin/cat %ssave.*",SAVEDIR);
+#ifndef lint
+ execl("/bin/sh", "sh", "-c", spbuf, 0);
+#endif
+ finalize(1);
+}
+
+
+void
+display_status()
+{
+ Reg1 int tmp;
+ static char *status_names[] = {"Impl", "Warp", "Base", "****" };
+
+ if (oldstatus != status) {
+ Sprintf(spbuf,"%-4s",status_names[status]);
+ mvaddstr(0,0, spbuf);
+ oldstatus = status;
+ }
+ if (ent) {
+ if (ent->energy != oldeenergy) {
+ oldeenergy = ent->energy;
+ Sprintf(spbuf,"%4ld",oldeenergy);
+ mvaddstr(0,8, spbuf);
+ }
+ if (etorp != oldetorp) {
+ Sprintf(spbuf,"%2d",etorp);
+ mvaddstr(0,13, spbuf);
+ oldetorp = etorp;
+ }
+ }
+ else {
+ if (etorp >= 0) {
+ etorp = -1;
+ mvaddstr(0,8,"*******");
+ damage = 0;
+ }
+ }
+ if (base) {
+ if (base->energy != oldbenergy) {
+ oldbenergy = base->energy;
+ Sprintf(spbuf,"%5ld",oldbenergy);
+ mvaddstr(0,19, spbuf);
+ }
+ if (btorp != oldbtorp) {
+ Sprintf(spbuf,"%3d",btorp);
+ mvaddstr(0,25, spbuf);
+ oldbtorp = btorp;
+ }
+ }
+ else {
+ if (btorp >= 0) {
+ btorp = -1;
+ mvaddstr(0,19,"*********");
+ }
+ }
+ if (damage) {
+ if (!olddamage)
+ mvaddstr(0,42,"*** ");
+ if (damage > 1 || !damflag[dam]) {
+ do {
+ if (++dam == MAXDAMAGE)
+ dam = 0;
+ } while (!damflag[dam]);
+ }
+ if (!--damflag[dam]) {
+ olddamage = damage;
+ damage--;
+ Sprintf(spbuf,"%s OK *** ",dammess[dam]);
+ spbuf[15] = '\0';
+ mvaddstr(0,46,spbuf);
+ }
+ else if (dam == NOSHIELDS) {
+ olddamage = damage;
+ tmp = (34 - damflag[dam]) * 3 - rand_mod(3);
+ if (tmp < 0)
+ tmp = 0;
+ Sprintf(spbuf,"%d%% %s *** ",tmp,dammess[dam]);
+ spbuf[15] = '\0';
+ mvaddstr(0,46,spbuf);
+ }
+ else if (dam != lastdam || !olddamage) {
+ olddamage = damage;
+ Sprintf(spbuf,"NO %s *** ",dammess[dam]);
+ spbuf[15] = '\0';
+ mvaddstr(0,46,spbuf);
+ }
+ if (status < 2) {
+ if (dam == NOIMPULSE && !entmode)
+ status = entmode = 1;
+ if (dam == NOWARP && entmode)
+ status = entmode = 0;
+ }
+ tmp = damflag[dam] * damage;
+ Sprintf(spbuf,"%3d.%1d ETR",tmp/10,tmp%10);
+ mvaddstr(0,69,spbuf);
+ lastdam = dam;
+ }
+ else {
+ if (olddamage) {
+ Sprintf(spbuf,"Stars: %-3d Stardate",numstars);
+ mvaddstr(0,42,spbuf);
+ lastdam = -1;
+ olddamage = 0;
+ oldcurscore = -1;
+ }
+ else if (numstars != oldstrs) {
+ Sprintf(spbuf,"%-3d",numstars);
+ mvaddstr(0,49, spbuf);
+ }
+ oldstrs = numstars;
+ }
+ if (numenemies != oldenemies) {
+ Sprintf(spbuf,"%-3d",numenemies);
+ mvaddstr(0,38, spbuf);
+ oldenemies = numenemies;
+ }
+ if (tmp = timer%10) {
+ Sprintf(spbuf,"%1d",tmp);
+ mvaddstr(0,67, spbuf);
+ }
+ else {
+ Sprintf(spbuf,"%5d.%1d",timer/10+smarts*100,tmp);
+ mvaddstr(0,61, spbuf);
+ }
+ if ((!damage || !damflag[dam]) && curscore != oldcurscore) {
+ Sprintf(spbuf,"%9ld",curscore);
+ mvaddstr(0,69, spbuf);
+ oldcurscore = curscore;
+ }
+}
+
+void
+wavescore()
+{
+ double power, effectscore, starscore, pi_over_2;
+ long bonuses;
+ long tmp;
+ FILE *mapfp;
+ int row;
+ double pow();
+#ifndef lint
+ double atan2();
+#endif
+
+ clear();
+ if (curscore > possiblescore)
+ curscore = possiblescore;
+ pi_over_2 = 3.14159265 / 2.0;
+ power = pow((double)inumenemies+ /* total number of enemies */
+ inumroms*2+ /* count roms 3 times */
+ inumgorns+ /* count gorns 2 times */
+ inumthols+ /* count thols 2 times */
+ inumapollos*4+ /* count apollo 5 times */
+ inumcrushes*3+ /* count crushers 4 times */
+ inumamoebas*5 /* count amoebas 6 times */
+ , 0.50) * /* skew it a little */
+ (double)smarts; /* average energy and intelligence */
+ if (inumstars < 350 && inumenemies > 5)
+ power += (350.0 - (double)inumstars) * ((double)inumenemies - 5.0);
+ if (inumstars > 850 && inumenemies > 2)
+ power += ((double)inumstars - 850.0) * ((double)inumenemies - 2.0);
+#ifndef lint
+ effectscore = ((double)curscore / possiblescore) *
+ atan2(power, (double) timer + 1.0) / pi_over_2;
+#else
+ effectscore = pi_over_2;
+#endif
+ if (inumstars)
+ starscore = (double) numstars / (double) inumstars;
+ else
+ starscore = 1.0;
+ wave++;
+ Sprintf(spbuf,"Wave = %d, Difficulty = %d, cumulative difficulty = %d",
+ wave, smarts, cumsmarts);
+ mvaddstr(1, 13+(smarts<10), spbuf);
+ mvaddstr( 4, 68, " BONUS");
+ Sprintf(spbuf,"Efficiency rating: %1.8f (diff=%0.2f,time=%d)",
+ effectscore, power, timer + 1);
+ mvaddstr( 5,5, spbuf);
+ if (effectscore < 0.8)
+ bonuses = tmp = 0;
+ else
+ bonuses = tmp = (long) ((effectscore-0.8) * smarts * 1000);
+ Sprintf(spbuf, "%6ld", tmp);
+ mvaddstr( 5, 68, spbuf);
+ Sprintf(spbuf,"Star save ratio: %1.8f (%d/%d)",
+ starscore, numstars, inumstars);
+ mvaddstr( 6,5, spbuf);
+#ifndef lint
+ bonuses += tmp = (long) (((double)curscore / possiblescore) *
+ (starscore*starscore) * smarts * 20);
+#endif
+ Sprintf(spbuf, "%6ld", tmp);
+ mvaddstr( 6, 68, spbuf);
+ row = 7;
+ if (inuminhab != numinhab) {
+ Sprintf(spbuf, "Inhabited stars depopulated: %5d", inuminhab-numinhab);
+ mvaddstr(row,5, spbuf);
+ bonuses += tmp = (long) (inuminhab-numinhab) * -500;
+ Sprintf(spbuf, "%6ld", tmp);
+ mvaddstr(row, 68, spbuf);
+ row++;
+ }
+ if (inumfriends != numfriends) {
+ Sprintf(spbuf, "Friendly craft destroyed: %5d",
+ inumfriends-numfriends);
+ mvaddstr(row,5, spbuf);
+ bonuses += tmp = (long) (inumfriends-numfriends) * -250;
+ Sprintf(spbuf, "%6ld", tmp);
+ mvaddstr(row, 68, spbuf);
+ row++;
+ }
+ if (deadmudds) {
+ mvaddstr(row,5,"For destroying Harry Mudd:");
+ bonuses += tmp = (long) rand_mod(deadmudds * 20 + 1) - deadmudds*10;
+ Sprintf(spbuf, "%6ld", tmp);
+ mvaddstr(row, 68, spbuf);
+ row++;
+ }
+ if (bombed_out) {
+ mvaddstr(row,5, "For running away from reality:");
+ bonuses += tmp = (long) -possiblescore/2;
+ Sprintf(spbuf, "%6ld", tmp);
+ mvaddstr(row, 68, spbuf);
+ row++;
+ }
+ if (row < 9)
+ row++;
+ Sprintf(spbuf, "Enterprise: %-9s%5d remaining",
+ !ient?"":ent?"saved":"destroyed", numents);
+ mvaddstr(row,5, spbuf);
+ bonuses += tmp = ent && !bombed_out ? (smarts+1)*15 : 0;
+ Sprintf(spbuf, "%6ld", tmp);
+ mvaddstr(row, 68, spbuf);
+ row++;
+ Sprintf(spbuf, "Base: %-9s %5d remaining",
+ !ibase?"":base?"saved":"destroyed", numbases);
+ mvaddstr(row,5, spbuf);
+ bonuses += tmp = base && !bombed_out ? (smarts+1)*10 : 0;
+ Sprintf(spbuf, "%6ld", tmp);
+ mvaddstr(row, 68, spbuf);
+ if (beginner) {
+ mvaddstr(13+(row>11),19, "(Special games count only a tenth as much)");
+ curscore /= 10;
+ bonuses /= 10;
+ }
+ Sprintf(spbuf, "Previous point total:%10ld",lastscore);
+ mvaddstr(15,24, spbuf);
+ Sprintf(spbuf, "Points this round: %10ld",curscore);
+ mvaddstr(16,24, spbuf);
+ Sprintf(spbuf, "Bonuses: %10ld",bonuses);
+ mvaddstr(17,24, spbuf);
+ totalscore = lastscore + curscore + bonuses;
+ Sprintf(spbuf, "New point total: %10ld",totalscore);
+ mvaddstr(18,24, spbuf);
+ if (lastscore / ENTBOUNDARY < totalscore / ENTBOUNDARY) {
+ mvaddstr(row-1,42,"+ 1 new");
+ numents++;
+ }
+ else if (numents>0 &&
+ lastscore / ENTBOUNDARY > totalscore / ENTBOUNDARY) {
+ mvaddstr(row-1,42,"- 1 obsolete");
+ numents--;
+ }
+ if (lastscore / BASEBOUNDARY < totalscore / BASEBOUNDARY) {
+ mvaddstr(row,42,"+ 1 new");
+ numbases++;
+ }
+ else if (numbases>0 &&
+ lastscore / BASEBOUNDARY > totalscore / BASEBOUNDARY) {
+ mvaddstr(row,42,"- 1 obsolete");
+ numbases--;
+ }
+ if (starscore < 0.8 && inumstars > 200 && numstars > 50) {
+ Sprintf(spbuf, "smap.%d",rand_mod(MAPS-PERMMAPS)+PERMMAPS);
+ if ((mapfp = fopen(spbuf,"w")) != NULL) {
+ Reg1 OBJECT *obj;
+
+ fprintf(mapfp,"%d\n",numstars);
+ for (obj = root.next; obj != &root; obj = obj->next) {
+ if (obj->type == Star) {
+ fprintf(mapfp,"%d %d\n",obj->posy,obj->posx);
+ }
+ }
+ Fclose(mapfp);
+ }
+ }
+}
+
+void
+score()
+{
+ char tmp, *retval, cdate[30];
+ Reg1 FILE *logfd;
+ Reg2 FILE *outfd;
+ Reg3 int i;
+ long nowtime, time();
+ char *scoreboard;
+
+ for (i=0; link(LOGFILE, LOCKFILE) == -1 && i<10; i++)
+ sleep(1);
+ nowtime = time((long *)0);
+ strcpy(cdate,ctime(&nowtime));
+ if ((logfd = fopen(LOGFILE,"a")) != NULL) {
+ fprintf(logfd,
+ "%-24s%-9s%7ld%c%2d %4d %s",
+ realname, logname, totalscore, c,smarts, cumsmarts, cdate);
+ Fclose(logfd);
+ }
+ strcpy(cdate+11,cdate+20);
+ if (beginner)
+ scoreboard = FSCOREBOARD;
+ else if (lowspeed)
+ scoreboard = LSCOREBOARD;
+ else
+ scoreboard = SCOREBOARD;
+ if (eaccess(scoreboard,0)) {
+ if ((logfd = fopen(scoreboard,"w")) != NULL)
+ Fclose(logfd);
+ }
+ if ((logfd = fopen(scoreboard,"r")) != NULL &&
+ (outfd = fopen(TMPSCOREBOARD,"w")) != NULL) {
+ for (i=0; i<20; i++) {
+ if ((retval = fgets(buf, 100, logfd)) == NULL)
+ break;
+ if (atol(buf+32) < totalscore)
+ break;
+ if (strnEQ(buf+COMPOFF,COMPNAME,COMPLEN)) {
+ i = 100;
+ break;
+ }
+ fprintf(outfd, "%s", buf);
+ }
+ if (i == 100) {
+ mvaddstr(20,21, "You did not better your previous score");
+ Fclose(outfd);
+ unlink(TMPSCOREBOARD);
+ }
+ else if (i < 20) {
+ fprintf(outfd, "%-24s%-8s%8ld%c %2d %4d %s",
+ realname, logname, totalscore, c,smarts, cumsmarts, cdate);
+ i++;
+ Sprintf(spbuf, " Congratulations--you've placed %d%s",
+ i, i==1?"st":(i==2?"nd":(i==3?"rd":"th")));
+ if (retval != NULL) {
+ if (strnNE(buf+COMPOFF,COMPNAME,COMPLEN)) {
+ fprintf(outfd, "%s", buf);
+ i++;
+ }
+ else
+ strcpy(spbuf,"Congratulations--you've bettered your score");
+ while (i<20) {
+ if (fgets(buf, 100, logfd) == NULL)
+ break;
+ if (strnNE(buf+COMPOFF,COMPNAME,COMPLEN)) {
+ fprintf(outfd, "%s", buf);
+ i++;
+ }
+ }
+ }
+ mvaddstr(20,19, spbuf);
+ Fclose(logfd);
+ Fclose(outfd);
+ while (unlink(scoreboard) == 0)
+ ;
+ link(TMPSCOREBOARD,scoreboard);
+ unlink(TMPSCOREBOARD);
+ logfd = fopen(scoreboard,"r");
+ }
+ else {
+ mvaddstr(20,22,"You did not place within the top 20");
+ Fclose(outfd);
+ }
+ }
+ else {
+ Sprintf(spbuf,"(Cannot access %s file, error %d)",
+ (logfd==NULL?"log":"tmp"),errno);
+ mvaddstr(20,22,spbuf);
+ }
+ move(23,0,0);
+ erase_eol();
+ mvaddstr(23,11,
+ "[Hit space for scoreboard, 'r' for new game, 'q' to quit]");
+ unlink(LOCKFILE);
+ Fflush(stdout);
+ eat_typeahead();
+ do {
+ getcmd(&tmp);
+ } while (tmp != INTRCH && tmp != BREAKCH && !index(" rqQ",tmp));
+ if (index("qQr",tmp)) {
+ justonemoretime = (tmp == 'r');
+ if (logfd != NULL)
+ Fclose(logfd);
+ }
+ else {
+ clear();
+ if (logfd != NULL) {
+ fseek(logfd, 0L, 0);
+ if (beginner)
+ mvaddstr(0,31,"TOP FUNNY WARPISTS");
+ else if (lowspeed)
+ mvaddstr(0,29,"TOP LOW-SPEED WARPISTS");
+ else
+ mvaddstr(0,33,"TOP WARPISTS");
+ mvaddstr(2,0,"RANK WHO AKA SCORE DIFF CUMDIFF WHEN");
+ for (i=1; i<=20; i++) {
+ if (fgets(buf, 100, logfd) == NULL)
+ break;
+ buf[strlen(buf)-1] = '\0';
+ Sprintf(spbuf, " %2d %s", i, buf);
+ mvaddstr(i+2,0, spbuf);
+ }
+ Fclose(logfd);
+ }
+ roundsleep(1);
+ mvaddstr(23,25,"Would you like to play again?");
+ eat_typeahead();
+ do {
+ getcmd(&tmp);
+ } while (tmp != INTRCH && tmp != BREAKCH && !index("nNyY \n\r",tmp));
+ if (tmp == 'n' || tmp == 'N' || tmp == INTRCH || tmp == BREAKCH)
+ justonemoretime = FALSE;
+ }
+
+ smarts = ismarts;
+ totalscore = cumsmarts = wave = 0;
+ numents = 5;
+ numbases = 3;
+ apolspec = FALSE;
+ beginner = FALSE;
+ crushspec = FALSE;
+ gornspec = FALSE;
+ massacre = (ismarts >= 40);
+ romspec = FALSE;
+ tholspec = FALSE;
+}
+
+void
+save_game()
+{
+ FILE *savfil;
+
+ if (experimenting)
+ return;
+ if ((savfil = fopen(savefilename,"w")) == NULL) {
+ resetty();
+ printf("Cannot save game\r\n");
+ finalize(1);
+ }
+ fprintf(savfil, "%-8s %10ld, %2d,%5d,%2d,%2d,%3d %c%c%c%c%c%c%c%c\n",
+ logname, totalscore, smarts, cumsmarts, numents, numbases, wave,
+ apolspec ? 'a' : ' ',
+ beginner ? 'b' : ' ',
+ crushspec ? 'c' : ' ',
+ gornspec ? 'g' : ' ',
+ massacre ? 'm' : ' ',
+ romspec ? 'r' : ' ',
+ tholspec ? 't' : ' ',
+ lowspeed ? 'l' : ' ',
+ amoebaspec ? '&' : ' '
+ );
+ Fclose(savfil);
+ resetty();
+ if (panic)
+ finalize(0);
+ clear();
+ finalize(0);
+}