summaryrefslogtreecommitdiffstats
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
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>
-rw-r--r--warp/COPYRIGHT26
-rw-r--r--warp/EXTERN.h42
-rw-r--r--warp/INTERN.h40
-rw-r--r--warp/Makefile61
-rw-r--r--warp/README116
-rw-r--r--warp/bang.c171
-rw-r--r--warp/bang.h48
-rw-r--r--warp/config.H92
-rw-r--r--warp/config.h149
-rw-r--r--warp/config.h.SH269
-rw-r--r--warp/config.sh128
-rw-r--r--warp/filexp32
-rw-r--r--warp/init.c570
-rw-r--r--warp/init.h27
-rw-r--r--warp/intrp.c590
-rw-r--r--warp/intrp.h41
-rw-r--r--warp/move.c698
-rw-r--r--warp/move.h32
-rw-r--r--warp/object.c100
-rw-r--r--warp/object.h89
-rw-r--r--warp/patchlevel.h1
-rw-r--r--warp/play.c198
-rw-r--r--warp/play.h31
-rw-r--r--warp/score.c727
-rw-r--r--warp/score.h67
-rw-r--r--warp/sig.c243
-rw-r--r--warp/sig.h34
-rw-r--r--warp/sm.c99
-rw-r--r--warp/smap.0621
-rw-r--r--warp/smap.1621
-rw-r--r--warp/smap.2343
-rw-r--r--warp/smap.385
-rw-r--r--warp/smap.4577
-rw-r--r--warp/smap.517
-rw-r--r--warp/smap.6744
-rw-r--r--warp/smap.7178
-rw-r--r--warp/smp.023
-rw-r--r--warp/smp.123
-rw-r--r--warp/smp.223
-rw-r--r--warp/smp.323
-rw-r--r--warp/smp.423
-rw-r--r--warp/smp.523
-rw-r--r--warp/smp.623
-rw-r--r--warp/smp.723
-rw-r--r--warp/term.c832
-rw-r--r--warp/term.h327
-rw-r--r--warp/them.c424
-rw-r--r--warp/them.h29
-rw-r--r--warp/us.c528
-rw-r--r--warp/us.h79
-rw-r--r--warp/util.c344
-rw-r--r--warp/util.h102
-rw-r--r--warp/version.c39
-rw-r--r--warp/version.h27
-rw-r--r--warp/warp.c424
-rw-r--r--warp/warp.doc193
-rw-r--r--warp/warp.h463
-rw-r--r--warp/warp.man133
-rw-r--r--warp/warp.news4
-rw-r--r--warp/weapon.c706
-rw-r--r--warp/weapon.h40
61 files changed, 12785 insertions, 0 deletions
diff --git a/warp/COPYRIGHT b/warp/COPYRIGHT
new file mode 100644
index 00000000..b53450c3
--- /dev/null
+++ b/warp/COPYRIGHT
@@ -0,0 +1,26 @@
+Copyright (c) 2020 The NetBSD Foundation, Inc.
+All rights reserved.
+
+This code is derived from software contributed to The NetBSD Foundation
+by Larry Wall.
+
+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.
+
+THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. 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 FOUNDATION 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.
diff --git a/warp/EXTERN.h b/warp/EXTERN.h
new file mode 100644
index 00000000..fc464a1b
--- /dev/null
+++ b/warp/EXTERN.h
@@ -0,0 +1,42 @@
+/* $Header: /cvsroot/src/games/warp/EXTERN.h,v 1.1 2020/11/09 23:37:05 kamil Exp $
+ *
+ * $Log: EXTERN.h,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.1 86/12/12 16:46:50 lwall
+ * Guarded the undefs.
+ *
+ * Revision 7.0 86/10/08 15:11:31 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#ifdef EXT
+#undef EXT
+#endif
+#define EXT extern
+
+#ifdef INIT
+#undef INIT
+#endif
+#define INIT(x)
+
+#ifdef DOINIT
+#undef DOINIT
+#endif
diff --git a/warp/INTERN.h b/warp/INTERN.h
new file mode 100644
index 00000000..e53a6f44
--- /dev/null
+++ b/warp/INTERN.h
@@ -0,0 +1,40 @@
+/* $Header: /cvsroot/src/games/warp/INTERN.h,v 1.1 2020/11/09 23:37:05 kamil Exp $
+ *
+ * $Log: INTERN.h,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.1 86/12/12 16:51:45 lwall
+ * Guarded the undefs.
+ *
+ * Revision 7.0 86/10/08 15:11:37 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#ifdef EXT
+#undef EXT
+#endif
+#define EXT
+
+#ifdef INIT
+#undef INIT
+#endif
+#define INIT(x) = x
+
+#define DOINIT
diff --git a/warp/Makefile b/warp/Makefile
new file mode 100644
index 00000000..0ae4411d
--- /dev/null
+++ b/warp/Makefile
@@ -0,0 +1,61 @@
+CFLAGS+=-O
+SRCS= bang.c init.c intrp.c move.c object.c play.c score.c sig.c term.c \
+ them.c us.c util.c version.c warp.c weapon.c
+OBJS= bang.o init.o intrp.o move.o object.o play.o score.o sig.o term.o \
+ them.o us.o util.o version.o warp.o weapon.o
+
+warp: ${OBJS}
+ ${CC} ${OBJS} -o $@ -ltermlib -lm
+
+install: warp
+ export PATH || exit 1
+ - mv $(bin)/warp $(bin)/warp.old
+ - if test `pwd` != $(bin); then cp $(public) $(bin); fi
+ - cd $(bin); chmod 755 $(public); chown '$(CHOWNER)' $(public)
+ - chmod 4711 $(bin)/warp
+ - chmod 755 makedir
+ - ./makedir `./filexp $(privlib)`
+ - \
+if test `pwd` != `./filexp $(privlib)`; then \
+cp $(private) `./filexp $(privlib)`; \
+fi
+ - \
+cd `./filexp $(privlib)`; \
+chmod 755 $(private); \
+chown '$(CHOWNER)' . $(private); \
+cp /dev/null save.blurfl
+ - \
+if test ! -f `./filexp $(privlib)/warp.news`; then \
+cp warp.news `./filexp $(privlib)`; \
+fi
+ - \
+if test `pwd` != $(mansrc); then \
+for page in $(manpages); do \
+cp $$page $(mansrc)/`basename $$page .man`.$(manext); \
+done; \
+fi
+
+clean:
+ rm -f warp core ${OBJS}
+
+smap.0: smp.0 sm
+ sm <smp.0 >smap.0
+smap.1: smp.1 sm
+ sm <smp.1 >smap.1
+smap.2: smp.2 sm
+ sm <smp.2 >smap.2
+smap.3: smp.3 sm
+ sm <smp.3 >smap.3
+smap.4: smp.4 sm
+ sm <smp.4 >smap.4
+smap.5: smp.5 sm
+ sm <smp.5 >smap.5
+smap.6: smp.6 sm
+ sm <smp.6 >smap.6
+smap.7: smp.7 sm
+ sm <smp.7 >smap.7
+sm: sm.c
+ ${CC} sm.c -o $@
+
+depend: ${SRCS}
+ mkdep ${SRCS}
diff --git a/warp/README b/warp/README
new file mode 100644
index 00000000..e07ad801
--- /dev/null
+++ b/warp/README
@@ -0,0 +1,116 @@
+Copyright (c) 2020 The NetBSD Foundation, Inc.
+All rights reserved.
+
+This code is derived from software contributed to The NetBSD Foundation
+by Larry Wall.
+
+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.
+
+THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. 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 FOUNDATION 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.
+
+--------------------------------------------------------------------------
+
+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.
+
+Warp will probably not run on V7 systems that don't have a non-blocking read,
+or on machines with a small address space like the PDP-11. Caveat Emptor.
+
+Please read all the directions below before you proceed any further, and
+then follow them carefully. Failure to do so may void your warranty. :-)
+
+After you have unpacked your kit, you should have all the files listed
+in MANIFEST.
+
+ IMPORTANT
+
+You must choose the uid that you want warp to run under, since warp runs
+setuid to protect its files. Choose a uid (not root) that is used only
+by trustworthy persons. If you do your make install as root, the installed
+version will be chowned to this uid. Otherwise, you should login to your
+selected uid before proceeding. The Configure script will ask you which
+uid you want warp to run under.
+
+Installation
+
+1) Run Configure. This will figure out various things about your system.
+ Some things Configure will figure out for itself, other things it will
+ ask you about. It will then proceed to make config.h, config.sh, and
+ Makefile.
+
+ You might possibly have to trim # comments from the front of Configure
+ if your sh doesn't handle them, but all other # comments will be taken
+ care of.
+
+ (If you don't have sh, you'll have to copy the sample file config.H to
+ config.h and edit the config.h to reflect your system's peculiarities.)
+
+2) Glance through config.h to make sure system dependencies are correct.
+ Most of them should have been taken care of by running the Configure script.
+
+ If you have any additional changes to make to the C definitions, they
+ can be done in the Makefile, or in config.h. Bear in mind that they will
+ get undone next time you run Configure.
+
+3) make depend
+
+ This will look for all the includes and modify Makefile accordingly.
+ Configure will offer to do this for you.
+
+4) make
+
+ This will attempt to make warp in the current directory.
+
+5) make install
+
+ This will put warp into a public directory (normally /usr/games).
+ It will also try to put the man pages in a reasonable place. It will not
+ nroff the man page, however. You may need to be root to do this. If
+ you are not root, you must own the directories in question and you should
+ ignore any messages about chown not working.
+
+6) Read the manual entry before running warp.
+
+7) Feel free to edit warp.news.
+
+8) IMPORTANT! Help save the world! Communicate any problems and
+ suggested patches to me, lwall@sdcrdcf.UUCP (Larry Wall), so we can
+ keep the world in sync. If you have a problem, there's someone else
+ out there who either has had or will have the same problem.
+
+ If possible, send in patches such that the patch program will apply them.
+ Context diffs are the best, then normal diffs. Don't send ed scripts--
+ I've probably changed my copy since the version you have.
+
+ Watch for warp patches in comp.sources.bugs. Patches will generally be
+ in a form usable by the patch program. If you are just now bringing up
+ warp and aren't sure how many patches there are, write to me and I'll
+ send any you don't have. Your current patch level is shown in patchlevel.h.
+
+
+NEW FEATURES IN THIS RELEASE
+
+Uses a Configure script for greater portability.
+Space Amoebas!!!
+Pirates
+Friendly Freighters
+Harry Mudd
+Damage
+Keyboard mapping
diff --git a/warp/bang.c b/warp/bang.c
new file mode 100644
index 00000000..fa2cdeac
--- /dev/null
+++ b/warp/bang.c
@@ -0,0 +1,171 @@
+/* $Header: /cvsroot/src/games/warp/bang.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: bang.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.3 86/12/12 16:57:00 lwall
+ * Made circular explosions.
+ *
+ * Revision 7.0.1.2 86/10/20 14:36:02 lwall
+ * Picked some lint.
+ *
+ * Revision 7.0.1.1 86/10/16 10:49:45 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:11:57 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "object.h"
+#include "move.h"
+#include "sig.h"
+#include "term.h"
+#include "them.h"
+#include "INTERN.h"
+#include "bang.h"
+
+void
+bang_init()
+{
+ ;
+}
+
+void
+make_plink(y,x)
+Reg1 int x;
+Reg2 int y;
+{
+ Reg3 OBJECT *obj;
+
+ move(y+1,x*2,0);
+ beg_qwrite();
+ *filler = '@';
+ qwrite();
+ obj = occupant[y][x];
+ if (obj) {
+ if (numamoebas && obj->image == ' ')
+ qaddc(amb[y][x]);
+ else
+ qaddc(obj->image);
+ }
+ else if (numamoebas)
+ qaddc(amb[y][x]);
+ else
+ qaddspace();
+ end_qwrite();
+}
+
+void
+make_blast(y,x,mass,size)
+Reg1 int x;
+Reg2 int y;
+int size;
+long mass;
+{
+ bangy[nxtbang] = y;
+ bangx[nxtbang] = x;
+ bangm[nxtbang] = mass;
+ bangs[nxtbang++] = size;
+ assert(nxtbang <= XSIZE * YSIZE);
+ if (numamoebas && amb[y][x] == '~') {
+ if (mass > 10000)
+ modify_amoeba(y,x,1,'~', 10);
+ else if (mass > 100)
+ modify_amoeba(y,x,1,'~', 5);
+ bangs[nxtbang-1] = 0; /* don't propagate */
+ return;
+ }
+ else if (mass >= 0) {
+ Reg3 OBJECT *obj;
+
+ move(y+1,x*2,0);
+ beg_qwrite();
+ *filler = '@';
+ qwrite();
+ *filler = '#';
+ qwrite();
+ *filler = '@';
+ qwrite();
+ *filler = '#';
+ qwrite();
+ *filler = '@';
+ qwrite();
+ obj = occupant[y][x];
+ if (obj) {
+ if (numamoebas && obj->image == ' ')
+ qaddc(amb[y][x]);
+ else
+ qaddc(obj->image);
+ }
+ else if (numamoebas)
+ qaddc(amb[y][x]);
+ else
+ qaddspace();
+ end_qwrite();
+ }
+}
+
+void
+do_bangs()
+{
+ Reg1 int x;
+ Reg2 int y;
+ Reg3 int i;
+ Reg4 int j;
+ Reg7 int k;
+ Reg5 int lastxy;
+ Reg6 OBJECT *obj;
+
+ /* read blast list and update blast array */
+ assert(nxtbang >= 0 && nxtbang <= XSIZE * YSIZE);
+ for (i=0; i<nxtbang; i++) {
+ if (bangm[i] != 32767)
+ bangm[i] *= 4;
+ lastxy = bangs[i] << 1;
+ if (lastxy >= MAXBDIST)
+ lastxy = MAXBDIST - 1;
+ for (y=bangy[i]-bangs[i],x=bangx[i]-bangs[i],j=lastxy;
+ j>=0;
+ y++,x++,--j) {
+ yblasted[yy[j] = (y+YSIZE00) % YSIZE] |= 1;
+ xblasted[xx[j] = (x+XSIZE00) % XSIZE] |= 1;
+ }
+ blasted = TRUE;
+ for (y=lastxy;y>=0;--y) {
+ for (x=lastxy;x>=0;--x) {
+ if (lastxy > 2) {
+ j = abs(y-bangs[i]);
+ k = abs(x-bangs[i]);
+ if (j < k) /* distance is long + 1/2 short */
+ j += k + k;
+ else
+ j += j + k;
+ if (--j > lastxy)
+ continue;
+ }
+ if (bangm[i] != 32767 ||
+ !(obj=occupant[yy[y]][xx[x]]) || obj->type != Web)
+ blast[yy[y]][xx[x]] += bangm[i];
+ }
+ }
+ }
+}
diff --git a/warp/bang.h b/warp/bang.h
new file mode 100644
index 00000000..0044d7cd
--- /dev/null
+++ b/warp/bang.h
@@ -0,0 +1,48 @@
+/* $Header: /cvsroot/src/games/warp/bang.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: bang.h,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 86/10/08 15:12:03 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+EXT long blast[YSIZE][XSIZE];
+EXT bool blasted;
+EXT bool xblasted[XSIZE];
+EXT bool yblasted[YSIZE];
+
+EXT char bangy[YSIZE*XSIZE];
+EXT char bangx[YSIZE*XSIZE];
+EXT char bangs[YSIZE*XSIZE];
+
+EXT long bangm[YSIZE*XSIZE];
+
+#define MAXBDIST 40
+EXT int xx[MAXBDIST];
+EXT int yy[MAXBDIST];
+
+EXT int nxtbang;
+EXT bool banging;
+
+void make_plink();
+void make_blast();
+void do_bangs();
+void bang_init();
diff --git a/warp/config.H b/warp/config.H
new file mode 100644
index 00000000..23bdf00c
--- /dev/null
+++ b/warp/config.H
@@ -0,0 +1,92 @@
+/* config.h
+ * This file was produced by running the Configure script.
+ *
+ * Feel free to modify any of this as the need arises. Note, however,
+ * that running Configure again will wipe out any changes you've made.
+ */
+
+
+#/*undef EUNICE /* no file linking? */
+#/*undef VMS /* other assorted ickies? */
+
+/* how to cancel an article */
+#define CANCEL "/usr/lib/news/inews -h <%h" /**/
+
+#define FCNTL /* should we include fcntl.h? */
+
+#define FTIMER /* do we have the ftime() routine? */
+
+#define GETHOSTNAME /* do we have a gethostname function? */
+#/*undef DOUNAME /* do we have a uname function? */
+#/*undef PHOSTNAME "hostname" /* how to get host name with popen */
+
+#/*undef GETPWENT /* need we include slow getpwent? */
+
+#define HAVETERMLIB /* do we have termlib-style routines? */
+
+#/*undef index strchr /* cultural */
+#/*undef rindex strrchr /* differences? */
+
+#define IOCTL /* are ioctl args all defined in one place? */
+
+#define NORMSIG /* use signal rather than sigset? */
+
+#/*undef PORTABLE /* do we do extra lookups to start up? */
+
+#/*undef SCOREFULL /* keep scoreboard by fullname? */
+
+#/*undef TERMIO /* is this a termio system? */
+
+#/*undef USENDIR /* include ndir.c? */
+#/*undef LIBNDIR /* include /usr/include/ndir.h? */
+
+#/*undef vfork fork /* is vfork too virtual? */
+
+#/*undef void int /* is void to be avoided? */
+
+#define WHOAMI /* should we include whoami.h? */
+
+#define PASSNAMES /* do names come from the passwd file? */
+ /* (undef to take name from ~/.fullname) */
+#define BERKNAMES /* if so, are they Berkeley format? */
+ /* (that is, ":name,stuff:") */
+#/*undef USGNAMES /* or are they USG format? */
+ /* (that is, ":stuff-name(stuff):") */
+
+/* news library, may use only ~ and %l expansion */
+#define NEWSLIB "/usr/lib/news" /**/
+
+/* default shell--ok to be a slow shell like csh */
+#define PREFSHELL "/bin/csh" /**/
+
+/* warp private library, may use ~ expansion, %x and %l */
+#define PRIVLIB "/a/lwall/src/warp" /**/
+
+/* bits produced by the rand() function */
+#define RANDBITS 31 /**/
+
+/* How many register declarations are paid attention to? */
+
+#define Reg1 register /**/
+#define Reg2 register /**/
+#define Reg3 register /**/
+#define Reg4 register /**/
+#define Reg5 register /**/
+#define Reg6 register /**/
+#define Reg7 /**/
+#define Reg8 /**/
+#define Reg9 /**/
+#define Reg10 /**/
+#define Reg11 /**/
+#define Reg12 /**/
+#define Reg13 /**/
+#define Reg14 /**/
+#define Reg15 /**/
+#define Reg16 /**/
+
+/* root uid */
+#define ROOTID 0 /**/
+
+/* name of the site. May be overridden by gethostname, uname, etc. */
+#define SITENAME "sdcrdcf" /**/
+
diff --git a/warp/config.h b/warp/config.h
new file mode 100644
index 00000000..3d3aad41
--- /dev/null
+++ b/warp/config.h
@@ -0,0 +1,149 @@
+/* RDCHK:
+ * This symbol, if defined, indicates that the rdchk routine is available
+ * to find out if there is input pending on an IO channel. Generally
+ * the routine is used only if FIONREAD and O_NDELAY aren't available.
+ */
+#/*undef RDCHK /**/
+
+/* SCOREFULL:
+ * This symbol, if defined, indicates that any scoreboard kept by the
+ * program should be kept on the basis of the user's full name as opposed
+ * to the user's login name. If the user can change his full name he
+ * can enter multiple scores if this is defined.
+ */
+#/*undef SCOREFULL /**/
+
+/* SIGNEDCHAR:
+ * This symbol, if defined, indicates that characters are a signed type.
+ * If not defined, things declared as signed characters (and that make
+ * use of negative values) should probably be declared as shorts instead.
+ */
+#define SIGNEDCHAR /**/
+
+/* TERMIO:
+ * This symbol, if defined, indicates that the program should include
+ * termio.h rather than sgtty.h. There are also differences in the
+ * ioctl() calls that depend on the value of this symbol.
+ */
+#/*undef TERMIO /**/
+
+/* USENDIR:
+ * This symbol, if defined, indicates that the program should compile
+ * the ndir.c code provided with the package.
+ */
+/* LIBNDIR:
+ * This symbol, if defined, indicates that the program should include the
+ * system's version of ndir.h, rather than the one with this package.
+ */
+#/*undef USENDIR /**/
+#/*undef LIBNDIR /**/
+#define LIBNDIR
+
+/* WHOAMI:
+ * This symbol, if defined, indicates that the program may include
+ * whoami.h.
+ */
+#/*undef WHOAMI /**/
+
+/* HOSTNAME:
+ * This symbol contains name of the host the program is going to run on.
+ * The domain is not kept with hostname, but must be gotten from MYDOMAIN.
+ * The dot comes with MYDOMAIN, and need not be supplied by the program.
+ * If gethostname() or uname() exist, HOSTNAME may be ignored.
+ */
+/* MYDOMAIN:
+ * This symbol contains the domain of the host the program is going to
+ * run on. The domain must be appended to HOSTNAME to form a complete
+ * host name. The dot comes with MYDOMAIN, and need not be supplied by
+ * the program. If the host name is derived from PHOSTNAME, the domain
+ * may or may not already be there, and the program should check.
+ */
+#define HOSTNAME "kazoo" /**/
+#define MYDOMAIN ".uucp" /**/
+
+/* PASSNAMES:
+ * This symbol, if defined, indicates that full names are stored in
+ * the /etc/passwd file.
+ */
+/* BERKNAMES:
+ * This symbol, if defined, indicates that full names are stored in
+ * the /etc/passwd file in Berkeley format (name first thing, everything
+ * up to first comma, with & replaced by capitalized login id, yuck).
+ */
+/* USGNAMES:
+ * This symbol, if defined, indicates that full names are stored in
+ * the /etc/passwd file in USG format (everything after - and before ( is
+ * the name).
+ */
+#define PASSNAMES /* (undef to take name from ~/.fullname) */
+#define BERKNAMES /* (that is, ":name,stuff:") */
+#/*undef USGNAMES /* (that is, ":stuff-name(stuff):") */
+
+/* PREFSHELL:
+ * This symbol contains the full name of the preferred user shell on this
+ * system. Usual values are /bin/csh, /bin/ksh, /bin/sh.
+ */
+#define PREFSHELL "/bin/csh" /**/
+
+/* RANDBITS:
+ * This symbol contains the number of bits of random number the rand()
+ * function produces. Usual values are 15, 16, and 31.
+ */
+#define RANDBITS 15 /**/
+
+/* Reg1:
+ * This symbol, along with Reg2, Reg3, etc. is either the word "register"
+ * or null, depending on whether the C compiler pays attention to this
+ * many register declarations. The intent is that you don't have to
+ * order your register declarations in the order of importance, so you
+ * can freely declare register variables in sub-blocks of code and as
+ * function parameters. Do not use Reg<n> more than once per routine.
+ */
+
+#define Reg1 register /**/
+#define Reg2 register /**/
+#define Reg3 register /**/
+#define Reg4 /**/
+#define Reg5 /**/
+#define Reg6 /**/
+#define Reg7 /**/
+#define Reg8 /**/
+#define Reg9 /**/
+#define Reg10 /**/
+#define Reg11 /**/
+#define Reg12 /**/
+#define Reg13 /**/
+#define Reg14 /**/
+#define Reg15 /**/
+#define Reg16 /**/
+
+/* ROOTID:
+ * This symbol contains the uid of root, normally 0.
+ */
+#define ROOTID 0 /**/
+
+/* VOIDFLAGS:
+ * This symbol indicates how much support of the void type is given by this
+ * compiler. What various bits mean:
+ *
+ * 1 = supports declaration of void
+ * 2 = supports arrays of pointers to functions returning void
+ * 4 = supports comparisons between pointers to void functions and
+ * addresses of void functions
+ *
+ * The package designer should define VOIDUSED to indicate the requirements
+ * of the package. This can be done either by #defining VOIDUSED before
+ * including config.h, or by defining defvoidused in Myinit.U.
+ */
+#ifndef VOIDUSED
+#define VOIDUSED 7
+#endif
+#define VOIDFLAGS 7
+#if (VOIDFLAGS & VOIDUSED) != VOIDUSED
+#define void int /* is void to be avoided? */
+#define M_VOID /* Xenix strikes again */
+#endif
+
+/* warp private library, may use ~ expansion, %x and %l */
+#define PRIVLIB "/usr/games/lib/warp" /**/
+
diff --git a/warp/config.h.SH b/warp/config.h.SH
new file mode 100644
index 00000000..b0a07784
--- /dev/null
+++ b/warp/config.h.SH
@@ -0,0 +1,269 @@
+case $CONFIG in
+'')
+ if test ! -f config.sh; then
+ ln ../config.sh . || \
+ ln ../../config.sh . || \
+ ln ../../../config.sh . || \
+ (echo "Can't find config.sh."; exit 1)
+ echo "Using config.sh from above..."
+ fi
+ . config.sh
+ ;;
+esac
+echo "Extracting config.h (with variable substitutions)"
+cat <<!GROK!THIS! >config.h
+/* config.h
+ * This file was produced by running the config.h.SH script, which
+ * gets its values from config.sh, which is generally produced by
+ * running Configure.
+ *
+ * Feel free to modify any of this as the need arises. Note, however,
+ * that running config.h.SH again will wipe out any changes you've made.
+ * For a more permanent change edit config.sh and rerun config.h.SH.
+ */
+
+
+/* EUNICE:
+ * This symbol, if defined, indicates that the program is being compiled
+ * under the EUNICE package under VMS. The program will need to handle
+ * things like files that don't go away the first time you unlink them,
+ * due to version numbering. It will also need to compensate for lack
+ * of a respectable link() command.
+ */
+/* VMX:
+ * This symbol, if defined, indicates that the program is running under
+ * VMS. It is currently only set in conjunction with the EUNICE symbol.
+ */
+#$d_eunice EUNICE /**/
+#$d_eunice VMS /**/
+
+/* CHARSPRINTF:
+ * This symbol is defined if this system declares "char *sprintf()" in
+ * stdio.h. The trend seems to be to declare it as "int sprintf()". It
+ * is up to the package author to declare sprintf correctly based on the
+ * symbol.
+ */
+#$d_charsprf CHARSPRINTF /**/
+
+/* FCNTL:
+ * This symbol, if defined, indicates to the C program that it should
+ * include fcntl.h.
+ */
+#$d_fcntl FCNTL /**/
+
+/* FTIMER:
+ * This symbol, if defined, indicates that the ftime() routine exists.
+ */
+#$d_ftime FTIMER /**/
+
+/* GETHOSTNAME:
+ * This symbol, if defined, indicates that the C program may use the
+ * gethostname() routine to derive the host name. See also DOUNAME
+ * and PHOSTNAME.
+ */
+/* DOUNAME:
+ * This symbol, if defined, indicates that the C program may use the
+ * uname() routine to derive the host name. See also GETHOSTNAME and
+ * PHOSTNAME.
+ */
+/* PHOSTNAME:
+ * This symbol, if defined, indicates that the C program may use the
+ * contents of PHOSTNAME as a command to feed to the popen() routine
+ * to derive the host name. See also GETHOSTNAME and DOUNAME.
+ */
+#$d_gethname GETHOSTNAME /**/
+#$d_douname DOUNAME /**/
+#$d_phostname PHOSTNAME "$phostname" /**/
+
+/* GETPWENT:
+ * This symbol, if defined, indicates that the getpwent() routine
+ * should be used instead of the getpw() routine.
+ */
+#$d_getpwent GETPWENT /**/
+
+/* HAVETERMLIB:
+ * This symbol, when defined, indicates that termlib-style routines
+ * are available. There is nothing to include.
+ */
+#$d_havetlib HAVETERMLIB /**/
+
+/* index:
+ * This preprocessor symbol is defined, along with rindex, if the system
+ * uses the strchr and strrchr routines instead.
+ */
+/* rindex:
+ * This preprocessor symbol is defined, along with index, if the system
+ * uses the strchr and strrchr routines instead.
+ */
+#$d_index index strchr /* cultural */
+#$d_index rindex strrchr /* differences? */
+
+/* IOCTL:
+ * This symbol, if defined, indicates that sys/ioctl.h exists and should
+ * be included.
+ */
+#$d_ioctl IOCTL /**/
+
+/* NORMSIG:
+ * This symbol, if defined, indicates that normal signal handling routines
+ * should be used, as opposed to the ones in 4.1bsd (sigset, etc.).
+ */
+#$d_normsig NORMSIG /**/
+
+/* PORTABLE:
+ * This symbol, if defined, indicates to the C program that it should
+ * not assume that it is running on the machine it was compiled on.
+ * The program should be prepared to look up the host name, translate
+ * generic filenames, use PATH, etc.
+ */
+#$d_portable PORTABLE /**/
+
+/* RDCHK:
+ * This symbol, if defined, indicates that the rdchk routine is available
+ * to find out if there is input pending on an IO channel. Generally
+ * the routine is used only if FIONREAD and O_NDELAY aren't available.
+ */
+#$d_rdchk RDCHK /**/
+
+/* SCOREFULL:
+ * This symbol, if defined, indicates that any scoreboard kept by the
+ * program should be kept on the basis of the user's full name as opposed
+ * to the user's login name. If the user can change his full name he
+ * can enter multiple scores if this is defined.
+ */
+#$d_scorfl SCOREFULL /**/
+
+/* SIGNEDCHAR:
+ * This symbol, if defined, indicates that characters are a signed type.
+ * If not defined, things declared as signed characters (and that make
+ * use of negative values) should probably be declared as shorts instead.
+ */
+#$d_sgndchr SIGNEDCHAR /**/
+
+/* TERMIO:
+ * This symbol, if defined, indicates that the program should include
+ * termio.h rather than sgtty.h. There are also differences in the
+ * ioctl() calls that depend on the value of this symbol.
+ */
+#$d_termio TERMIO /**/
+
+/* USENDIR:
+ * This symbol, if defined, indicates that the program should compile
+ * the ndir.c code provided with the package.
+ */
+/* LIBNDIR:
+ * This symbol, if defined, indicates that the program should include the
+ * system's version of ndir.h, rather than the one with this package.
+ */
+#$d_usendir USENDIR /**/
+#$d_libndir LIBNDIR /**/
+
+/* WHOAMI:
+ * This symbol, if defined, indicates that the program may include
+ * whoami.h.
+ */
+#$d_whoami WHOAMI /**/
+
+/* HOSTNAME:
+ * This symbol contains name of the host the program is going to run on.
+ * The domain is not kept with hostname, but must be gotten from MYDOMAIN.
+ * The dot comes with MYDOMAIN, and need not be supplied by the program.
+ * If gethostname() or uname() exist, HOSTNAME may be ignored.
+ */
+/* MYDOMAIN:
+ * This symbol contains the domain of the host the program is going to
+ * run on. The domain must be appended to HOSTNAME to form a complete
+ * host name. The dot comes with MYDOMAIN, and need not be supplied by
+ * the program. If the host name is derived from PHOSTNAME, the domain
+ * may or may not already be there, and the program should check.
+ */
+#define HOSTNAME "$hostname" /**/
+#define MYDOMAIN "$mydomain" /**/
+
+/* PASSNAMES:
+ * This symbol, if defined, indicates that full names are stored in
+ * the /etc/passwd file.
+ */
+/* BERKNAMES:
+ * This symbol, if defined, indicates that full names are stored in
+ * the /etc/passwd file in Berkeley format (name first thing, everything
+ * up to first comma, with & replaced by capitalized login id, yuck).
+ */
+/* USGNAMES:
+ * This symbol, if defined, indicates that full names are stored in
+ * the /etc/passwd file in USG format (everything after - and before ( is
+ * the name).
+ */
+#$d_passnames PASSNAMES /* (undef to take name from ~/.fullname) */
+#$d_berknames BERKNAMES /* (that is, ":name,stuff:") */
+#$d_usgnames USGNAMES /* (that is, ":stuff-name(stuff):") */
+
+/* PREFSHELL:
+ * This symbol contains the full name of the preferred user shell on this
+ * system. Usual values are /bin/csh, /bin/ksh, /bin/sh.
+ */
+#define PREFSHELL "$prefshell" /**/
+
+/* RANDBITS:
+ * This symbol contains the number of bits of random number the rand()
+ * function produces. Usual values are 15, 16, and 31.
+ */
+#define RANDBITS $randbits /**/
+
+/* Reg1:
+ * This symbol, along with Reg2, Reg3, etc. is either the word "register"
+ * or null, depending on whether the C compiler pays attention to this
+ * many register declarations. The intent is that you don't have to
+ * order your register declarations in the order of importance, so you
+ * can freely declare register variables in sub-blocks of code and as
+ * function parameters. Do not use Reg<n> more than once per routine.
+ */
+
+#define Reg1 $reg1 /**/
+#define Reg2 $reg2 /**/
+#define Reg3 $reg3 /**/
+#define Reg4 $reg4 /**/
+#define Reg5 $reg5 /**/
+#define Reg6 $reg6 /**/
+#define Reg7 $reg7 /**/
+#define Reg8 $reg8 /**/
+#define Reg9 $reg9 /**/
+#define Reg10 $reg10 /**/
+#define Reg11 $reg11 /**/
+#define Reg12 $reg12 /**/
+#define Reg13 $reg13 /**/
+#define Reg14 $reg14 /**/
+#define Reg15 $reg15 /**/
+#define Reg16 $reg16 /**/
+
+/* ROOTID:
+ * This symbol contains the uid of root, normally 0.
+ */
+#define ROOTID $rootid /**/
+
+/* VOIDFLAGS:
+ * This symbol indicates how much support of the void type is given by this
+ * compiler. What various bits mean:
+ *
+ * 1 = supports declaration of void
+ * 2 = supports arrays of pointers to functions returning void
+ * 4 = supports comparisons between pointers to void functions and
+ * addresses of void functions
+ *
+ * The package designer should define VOIDUSED to indicate the requirements
+ * of the package. This can be done either by #defining VOIDUSED before
+ * including config.h, or by defining defvoidused in Myinit.U.
+ */
+#ifndef VOIDUSED
+#define VOIDUSED $defvoidused
+#endif
+#define VOIDFLAGS $voidflags
+#if (VOIDFLAGS & VOIDUSED) != VOIDUSED
+#$define void int /* is void to be avoided? */
+#$define M_VOID /* Xenix strikes again */
+#endif
+
+/* $package private library, may use ~ expansion, %x and %l */
+#define PRIVLIB "$privlib" /**/
+
+!GROK!THIS!
diff --git a/warp/config.sh b/warp/config.sh
new file mode 100644
index 00000000..68c88418
--- /dev/null
+++ b/warp/config.sh
@@ -0,0 +1,128 @@
+#!/bin/sh
+# config.sh
+# This file was produced by running the Configure script.
+
+d_eunice='/*undef'
+eunicefix=':'
+define='define'
+loclist='
+expr
+sed
+echo
+cat
+rm
+mv
+cp
+tr
+mkdir
+sort
+uniq
+grep
+'
+expr='expr'
+sed='sed'
+echo='echo'
+cat='cat'
+rm='rm'
+mv='mv'
+cp='cp'
+tail=''
+tr='tr'
+mkdir='mkdir'
+sort='sort'
+uniq='uniq'
+grep='grep'
+trylist='
+test
+egrep
+Mcc
+'
+test='/bin/test'
+inews=''
+egrep='/usr/bin/egrep'
+more=''
+pg=''
+Mcc='Mcc'
+vi=''
+mailx=''
+mail=''
+Log='$Log'
+Header='$Header'
+cc='cc'
+contains='grep'
+cpp='cc -E'
+d_charsprf='define'
+d_fcntl='define'
+d_ftime='define'
+d_gethname='define'
+d_douname='/*undef'
+d_phostname='/*undef'
+d_getpwent='/*undef'
+d_havetlib='define'
+termlib='-ltermlib'
+d_index='/*undef'
+d_ioctl='define'
+d_normsig='define'
+jobslib=''
+d_portable='define'
+d_rdchk='/*undef'
+d_scorfl='/*undef'
+d_sgndchr='define'
+d_termio='/*undef'
+d_usendir='/*undef'
+d_libndir='/*undef'
+ndirc=''
+ndiro=''
+d_whoami='/*undef'
+hostname='kazoo'
+phostname='hostname'
+mydomain='.uucp'
+libc='/lib/libc.a'
+libnm='/usr/lib/libtermlib.a'
+mansrc='/usr/man/man6'
+manext='6'
+models='unsplit split'
+split='-i'
+small=''
+medium=''
+large=''
+huge=''
+ccflags=''
+ldflags=''
+n='-n'
+c=''
+nametype='bsd'
+d_passnames='define'
+d_berknames='define'
+d_usgnames='/*undef'
+passcat='cat /etc/passwd'
+package='warp'
+prefshell='/bin/csh'
+randbits='15'
+registers='3'
+reg1='register'
+reg2='register'
+reg3='register'
+reg4=''
+reg5=''
+reg6=''
+reg7=''
+reg8=''
+reg9=''
+reg10=''
+reg11=''
+reg12=''
+reg13=''
+reg14=''
+reg15=''
+reg16=''
+rootid='0'
+spitshell='cat'
+shsharp='true'
+sharpbang='#!'
+startsh='#!/bin/sh'
+voidflags='7'
+bin='/usr/games'
+chowner='daemon'
+privlib='/usr/games/lib/warp'
+CONFIG=true
diff --git a/warp/filexp b/warp/filexp
new file mode 100644
index 00000000..b0d65435
--- /dev/null
+++ b/warp/filexp
@@ -0,0 +1,32 @@
+#!/bin/sh
+: expand filename
+case "$1" in
+ ~/*|~)
+ echo $1 | sed "s|~|${HOME-$LOGDIR}|"
+ ;;
+ ~*)
+ if /bin/test -f /bin/csh; then
+ /bin/csh -f -c "glob $1"
+ echo ""
+ else
+ name=`expr x$1 : '..\([^/]*\)'`
+ dir=`sed -n -e "/^${name}:/{s/^[^:]*:[^:]*:[^:]*:[^:]*:[^:]*:\([^:]*\).*"'$'"/\1/" -e p -e q -e '}' </etc/passwd`
+ if /bin/test ! -d "$dir"; then
+ me=`basename $0`
+ echo "$me: can't locate home directory for: $name" >&2
+ exit 1
+ fi
+ case "$1" in
+ */*)
+ echo $dir/`expr x$1 : '..[^/]*/\(.*\)'`
+ ;;
+ *)
+ echo $dir
+ ;;
+ esac
+ fi
+ ;;
+*)
+ echo $1
+ ;;
+esac
diff --git a/warp/init.c b/warp/init.c
new file mode 100644
index 00000000..b3b15fff
--- /dev/null
+++ b/warp/init.c
@@ -0,0 +1,570 @@
+/* $Header: /cvsroot/src/games/warp/init.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: init.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.4 86/12/12 16:58:03 lwall
+ * Baseline for net release.
+ *
+ * Revision 7.0.1.3 86/10/20 14:35:31 lwall
+ * Picked some lint.
+ *
+ * Revision 7.0.1.2 86/10/17 15:53:30 lwall
+ * Added random walk star fields.
+ *
+ * Revision 7.0.1.1 86/10/16 10:51:19 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:12:10 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "bang.h"
+#include "object.h"
+#include "move.h"
+#include "play.h"
+#include "score.h"
+#include "term.h"
+#include "them.h"
+#include "us.h"
+#include "util.h"
+#include "weapon.h"
+#include "INTERN.h"
+#include "init.h"
+
+void
+initialize()
+{
+ Reg1 int i;
+ Reg2 int x;
+ Reg3 int y;
+ Reg4 int dist;
+ Reg5 int ydist;
+ Reg6 int xdist;
+ long e;
+ int yoff, xoff, ypred, xpred;
+ Reg7 OBJECT *obj;
+ char ch;
+ FILE *mapfp = NULL;
+ bool tmptholspec;
+ int inhabjackpot;
+ long inhenergy;
+ int walksplit = 200;
+ static char *distname[] =
+ {" #"," -"," \\"," /",
+ " |"," *"," `"," '"};
+
+ cloaking = madgorns = FALSE;
+ deados = madfriends = 0;
+ curscore = possiblescore = 0L;
+ yamblast = xamblast = ambsize = 0;
+ if (smarts > 90)
+ massacre = TRUE;
+ scandist = (massacre?20:15);
+ antibase = (smarts>60?1:(smarts>40?2:(smarts>25?4:100)));
+ sm35 = (smarts>35?35:smarts);
+ sm45 = (smarts>45?45:smarts);
+ sm50 = (smarts>50?50:smarts);
+ sm55 = (smarts>55?55:smarts);
+ sm80 = (smarts>80?80:smarts);
+ sm95 = (smarts>95?95:smarts);
+ super = (smarts>50?smarts-50:0);
+ enemshields = 10 + super/2; /* (scaled by 10) 1 @ 50 .. 3 @ 90 */
+ if (smarts>90)
+ enemshields += (smarts-90)*10; /* lay it on thick: ~13 @ 99 */
+ entmax = (smarts>=75?5000:(smarts>=50?4000:(smarts>=40?3000:2000)));
+ basemax = (smarts>=75?20000:(smarts>=50?15000:(smarts>=40?12500:10000)));
+
+ clear();
+ while (root.next != &root) {
+ root.next = root.next->next;
+ free_object(root.next->prev);
+ }
+ root.prev = &root;
+ enemies = movers = NULL;
+ numos = numxes = 0;
+#if defined(vax) && XYSIZEx4 == 3680
+ asm("movc5 $0,_occupant,$0,$3680,_occupant");
+ asm("movc5 $0,_blast,$0,$3680,_blast"); /* 3680 = XYSIZEx4 */
+ asm("movc5 $0,_amb,$32,$920,_amb");
+#else
+ for (y=0;y<YSIZE;y++)
+ for (x=0;x<XSIZE;x++) {
+ occupant[y][x] = 0;
+ blast[y][x] = 0;
+ amb[y][x] = ' ';
+ }
+#endif
+ for (y=0; y<YSIZE; y++)
+ yblasted[y] = 0;
+ for (x=0; x<XSIZE; x++)
+ xblasted[x] = 0;
+ blasted = FALSE;
+ if (!starspec)
+ if (smarts < 15)
+ inumstars = 50 + rand_mod(50);
+ else if (smarts < 50 || smarts > 85)
+ inumstars = exdis(800) + rand_mod(100) + 1;
+ else /* too few stars makes 50..85 too hard */
+ inumstars = exdis(700) + rand_mod(150-super*2) + 50+super*2;
+ tmptholspec = (smarts > 15 && inumstars < 450 && ! rand_mod(90-sm80));
+ if (!klingspec) {
+ inumenemies = rand_mod((smarts+1)/2) + 1;
+ if (massacre || tmptholspec)
+ inumenemies += 10;
+ }
+ if (!friendspec)
+ inumfriends = rand_mod(smarts/8+1);
+ if (!piratespec)
+ inumpirates = rand_mod(inumfriends/2+1);
+ if (inumfriends+inumenemies+inumstars > YSIZE*XSIZE-20)
+ inumstars = YSIZE*XSIZE-20 - inumenemies - inumfriends;
+ if (inumstars < 0) {
+ inumfriends += inumstars;
+ inumstars = 0;
+ }
+ if (inumfriends < 0) {
+ inumenemies += inumfriends;
+ inumfriends = 0;
+ }
+ if (inumenemies < 0)
+ inumenemies = 0;
+ numstars = inumstars;
+ inuminhab = numinhab = 0;
+ inumroms = inumthols = inumgorns = 0;
+ numapollos = apolspec || massacre ? 1 :
+ ((!numstars || rand_mod(2) || smarts < 10) ? 0 : 1);
+ inumapollos = apolloflag = 0;
+ realapollo = NULL;
+ inumcrushes = numcrushes =
+ crushspec||massacre?1:(rand_mod(2000) < inumstars);
+ inumenemies += inumcrushes;
+ inumamoebas = numamoebas = (amoebaspec ? 1 :
+ !rand_mod(inumcrushes?3-massacre:8) ); /* < and & are fun together */
+ inumenemies += inumamoebas;
+ if (!rand_mod(40)) {
+ inhabjackpot = 32767;
+ inumfriends += rand_mod(10);
+ inumpirates += rand_mod(10);
+ }
+ else
+ inhabjackpot = inumpirates;
+ inhenergy = 30000-super*150;
+ if (!rand_mod(10))
+ inhenergy = 50000;
+ if (!rand_mod(4))
+ inhenergy += rand_mod(3500+super*150);
+ numfriends = inumfriends;
+ numpirates = inumpirates;
+ numenemies = inumenemies;
+ deadmudds = 0;
+
+ /* do stars */
+
+stars_again:
+ if (prespec)
+ dist = 4;
+ else if (numstars > 750)
+ dist = 0;
+ else
+ dist = rand_mod(starspec||smarts<=5?3:5);
+ if (debugging) {
+ real_y = real_x = -100;
+ printf("\r\n");
+ }
+ switch (dist) {
+ case 0: /* uniform random */
+ ydist = xdist = 0;
+ if (inumstars < 700 && !rand_mod(3-(inumstars<50))) {
+ ydist = xdist = 6; /* well, maybe not so random */
+ y = rand_mod(YSIZE);
+ x = rand_mod(XSIZE);
+ if (rand_mod(2))
+ walksplit = inumstars/(exdis(40)+1);
+ }
+ if (debugging)
+ printf(" R\r\n");
+ break;
+ case 1: case 2: /* clumped, maybe skewed, maybe superposed */
+ ydist = rand_mod(4);
+ xdist = rand_mod(2);
+ if (debugging)
+ printf("%s\r\n",distname[ydist+4*xdist]);
+ yoff = rand_mod(YSIZE);
+ xoff = rand_mod(XSIZE);
+ if (dist == 2)
+ dist = numstars/2 + exdis(numstars/2) - exdis(numstars/2);
+ else
+ dist = 0;
+ break;
+ case 3: case 4: /* predefined or residual */
+ scenario_again:
+ if (debugging)
+ printf(" P\r\n");
+ dist = 0;
+ Sprintf(spbuf,"smap.%d",
+ (prescene>=0?prescene:rand_mod(MAPS)) );
+ if ((mapfp = fopen(spbuf,"r")) != NULL &&
+ fgets(spbuf,10,mapfp) != NULL ) {
+ inumstars = numstars = atoi(spbuf);
+ if (inumenemies+inumstars > YSIZE*XSIZE-20)
+ inumstars = numstars = YSIZE*XSIZE-20 - inumenemies;
+ ydist = rand_mod(2) + 4; /* flip y axis? */
+ xdist = rand_mod(2) + 4; /* flip x axis? */
+ yoff = rand_mod(YSIZE); /* how much to shift y */
+ xoff = rand_mod(XSIZE); /* how much to shift x */
+ }
+ else {
+ prespec = FALSE;
+ prescene = -1;
+ if (rand_mod(2))
+ goto scenario_again;
+ goto stars_again;
+ }
+ break;
+ }
+ for (i = 1; i <= numstars; i++) {
+ if (dist && i == dist) { /* flip to another skewing? */
+ ydist = rand_mod(4);
+ xdist = rand_mod(2);
+ if (!rand_mod(4)) {
+ ydist = xdist = 6;
+ if (debugging)
+ printf("&\r\n");
+ }
+ else if (debugging)
+ printf("%s\r\n",distname[ydist+4*xdist]);
+ yoff = rand_mod(YSIZE);
+ xoff = rand_mod(XSIZE);
+ dist = 0;
+ }
+ do { /* until an open spot found */
+ switch (xdist) {
+ case 0:
+ x = rand_mod(XSIZE); /* pick from 0..39, uniform */
+ break;
+ case 1: case 2: case 3:
+#ifndef lint
+ x = (int)((((double)(myrand()-HALFRAND)) *
+ ((double)(myrand()-HALFRAND))/RANDRAND)
+ * 20.0) + xoff; /* pick from -20..20, clumped */
+#endif
+ break;
+ case 4:
+ if (fscanf(mapfp,"%d %d\n",&ypred,&xpred) == EOF)
+ ydist = xdist = 0;
+ x = xpred + xoff;
+ break;
+ case 5:
+ if (fscanf(mapfp,"%d %d\n",&ypred,&xpred) == EOF)
+ ydist = xdist = 0;
+ x = -xpred + xoff;
+ break;
+ case 6:
+ x += rand_mod(3) - 1;
+ break;
+ }
+ switch (ydist) {
+ case 0:
+ y = rand_mod(YSIZE);
+ break;
+ case 1:
+#ifndef lint
+ y = (int)((((double)(myrand()-HALFRAND)) *
+ ((double)(myrand()-HALFRAND))/RANDRAND)
+ * 12.0) + yoff; /* pick from -12..12, clumped */
+#endif
+ break;
+ case 2:
+#ifndef lint
+ y = (int)((((double)(myrand()-HALFRAND)) *
+ ((double)(myrand()-HALFRAND))/RANDRAND)
+ * 12.0) + yoff + x*YSIZE/XSIZE;
+ /* clumped & skewed */
+#endif
+ break;
+ case 3:
+#ifndef lint
+ y = (int)((((double)(myrand()-HALFRAND)) *
+ ((double)(myrand()-HALFRAND))/RANDRAND)
+ * 12.0) + yoff - x*YSIZE/XSIZE;
+ /* clumped & skewed */
+#endif
+ break;
+ case 4:
+ y = ypred + yoff;
+ break;
+ case 5:
+ y = -ypred + yoff;
+ break;
+ case 6:
+ y += rand_mod(3) - 1;
+#ifdef lint
+ walksplit = walksplit;
+#endif
+ if (!rand_mod(walksplit)) {
+ y = rand_mod(YSIZE);
+ x = rand_mod(XSIZE);
+ }
+ break;
+ }
+ while (x<0) x += XSIZE00;
+ while (y<0) y += YSIZE00;
+ x %= XSIZE;
+ y %= YSIZE;
+ } while (occupant[y][x]);
+ e = rand_mod(32768);
+ if (--inhabjackpot > 0 || e >= inhenergy) {
+ ch = '@';
+ if (inhabjackpot && e < 10000)
+ e += 10000;
+ inuminhab = ++numinhab;
+ }
+ else {
+ ch = '*';
+ }
+ obj = make_object(Star,ch,y,x,0,0,e+rand_mod(super*100+1),e/4,&root);
+ obj->flags |= STATIC;
+ }
+ if (inumstars > 30 && inhabjackpot <= 0 &&
+ !rand_mod(3 - (inumstars > 400) - (inhenergy > 32768)) ) {
+ int initx;
+ int inity;
+
+ x = initx = obj->posx;
+ y = inity = obj->posy;
+ while (rand_mod(2) && inuminhab < inumstars/2) {
+ for (i=rand_mod(smarts)*2+20; i; i--) {
+ if ((obj = occupant[y][x]) && obj->image == '*') {
+ setimage(obj,'@');
+ if (obj->energy < 10000)
+ obj->energy += 20000; /* the benefits of civilization */
+ inuminhab = ++numinhab;
+ }
+ if (i&15) {
+ y = (y + rand_mod(3) + YSIZE99) % YSIZE;
+ x = (x + rand_mod(3) + XSIZE99) % XSIZE;
+ }
+ else { /* don't wander too far */
+ y = inity;
+ x = initx;
+ }
+ }
+ x = initx = rand_mod(XSIZE);
+ y = inity = rand_mod(YSIZE);
+ }
+ }
+ if (mapfp != NULL)
+ Fclose(mapfp);
+ if (numcrushes) {
+ do {
+ x = rand_mod(XSIZE);
+ y = rand_mod(YSIZE);
+ } while (occupant[y][x]);
+ movers = make_object(Crusher,'<',y,x,0,1,32767L,32768L,&root);
+ possiblescore += 10000;
+ }
+ ient = (numents != 0);
+ if (ient) {
+ do {
+ x = rand_mod(XSIZE);
+ y = rand_mod(YSIZE);
+ } while (occupant[y][x]);
+ e = entmax;
+ ent = make_object(Enterprise,'E',y,x,0,0,e,e/2,&root);
+ if (!movers)
+ movers = ent;
+ }
+ ibase = (numbases != 0);
+ if (ibase) {
+ e = 52-super;
+ do {
+ x = rand_mod(XSIZE);
+ y = rand_mod(YSIZE);
+ } while (occupant[y][x] || lookaround(y,x,Star) * 7 < e--);
+ e = basemax;
+ base = make_object(Base, 'B',y,x,0,0,e,e/4,&root);
+ if (!movers)
+ movers = base;
+ }
+ if (numamoebas) {
+ do {
+ x = rand_mod(XSIZE);
+ y = rand_mod(YSIZE);
+ } while (occupant[y][x]);
+ nuke = make_object(Enemy,'&',y,x,0,0,32767L,
+ (long)entmax+entmax+rand_mod(entmax),&root);
+ possiblescore += 10000;
+ amb[y][x] = '~';
+ if (rand_mod(2))
+ modify_amoeba(y,x,2,'~',(int)rand_mod(smarts<<1));/* just make blob */
+ else {
+ for (i=smarts/10+1; i; i--) {
+ nuke->strategy = rand_mod(256); /* random direction */
+ modify_amoeba(y,x,2,'~',(int)rand_mod(5));
+ modify_amoeba(y,x,2,'~',(int)rand_mod(5));
+ modify_amoeba(y,x,2,'~',(int)rand_mod(5));
+ modify_amoeba(y,x,2,'~',(int)rand_mod(5)); /* extend pseudopod */
+ }
+ }
+ if (!enemies)
+ enemies = nuke;
+ if (!movers)
+ movers = nuke;
+ }
+ if (rand_mod(27-sm50/2) && !romspec && !gornspec)
+ dist = 27-sm50/2;
+ else
+ dist = rand_mod(4) + 1;
+ for (i = 1+inumcrushes+inumamoebas; i <= numenemies; i++) {
+ do {
+ x = rand_mod(XSIZE);
+ y = rand_mod(YSIZE);
+ } while (occupant[y][x]);
+ if (rand_mod(dist)) {
+ if (!tholspec && !tmptholspec && rand_mod((inumstars*3)/sm50+2))
+ ch = 'K';
+ else {
+ ch = 'T';
+ inumthols++;
+ }
+ }
+ else {
+ if (romspec == gornspec)
+ e = 50;
+ else if (gornspec)
+ e = 10;
+ else
+ e = 90;
+ if (rand_mod(100) < e) {
+ ch = 'R';
+ inumroms++;
+ }
+ else {
+ ch = 'G';
+ inumgorns++;
+ }
+ }
+ if (possiblescore > ENTBOUNDARY - 10000)
+ e = (ENTBOUNDARY - possiblescore) / 5;
+ else
+ e = 250 + (sm50-1) * 30 * 20 / numenemies+1;
+#ifndef lint
+ e = exdis((int)e) + e - exdis((int)e);
+ obj = make_object(Enemy,ch,y,x,0,0,
+ e + rand_mod(super*200+2) + 10000*massacre,e/4,&root);
+#endif
+ e /= 4;
+ switch (ch) {
+ case 'K':
+ possiblescore += e;
+ break;
+ case 'T':
+ possiblescore += e*3/2;
+ break;
+ case 'G':
+ possiblescore += e*2;
+ break;
+ case 'R':
+ possiblescore += e*3;
+ obj->flags |= CLOAKS;
+ break;
+ }
+ if (!enemies)
+ enemies = obj;
+ if (!movers)
+ movers = obj;
+ }
+ numgorns = inumgorns;
+ for (i=0; i<numfriends; i++) {
+ do {
+ x = rand_mod(XSIZE);
+ y = rand_mod(YSIZE);
+ } while (occupant[y][x]);
+ e = 250 + (sm50-1) * 30 * 20 / numenemies+1;
+#ifndef lint
+ e = exdis((int)e) + e - exdis((int)e);
+#endif
+ {
+ static char let[] = "QWYUISDHJLZVMFFFFFFFFF";
+
+ dist = rand_mod(20);
+ ch = let[dist];
+ } /* grr, venix doesn't like indexing into string */
+ obj = make_object(Enemy,ch,y,x,0,0,
+ e + rand_mod(super*200+2),e/4,&root);
+ if (numpirates-- > 0) {
+ obj->flags |= PIRATE;
+ if (smarts >= 20 && !rand_mod(10-smarts/10))
+ obj->flags |= CLOAKS;
+ }
+ obj->flags |= FRIENDLY;
+ if (!enemies)
+ enemies = obj;
+ if (!movers)
+ movers = obj;
+ }
+ if (!movers)
+ movers = &root;
+ if (!enemies)
+ enemies = &root;
+ if (ent)
+ mvaddch(ent->posy+1, ent->posx*2, ent->image);
+ if (base)
+ mvaddch(base->posy+1, base->posx*2, base->image);
+ sleep(2);
+ {
+ Reg7 OBJECT *curobj;
+
+ for (curobj = root.next; curobj != &root; curobj = curobj->next) {
+ mvaddch(curobj->posy+1, curobj->posx*2, curobj->image);
+ }
+ }
+
+ for (i=0;i<2;i++) for (y=0;y<3;y++) for (x=0;x<3;x++)
+ isatorp[i][y][x]=0;
+
+ whenok = 0;
+ timer = 0;
+ finish = 0;
+ bombed_out = FALSE;
+ if (ent)
+ entmode = status = 0;
+ else
+ if (base)
+ status = 2;
+ else
+ status = 3;
+
+ Sprintf(spbuf,
+ "%-4s E: %4d %2d B: %5d %3d Enemies: %-3d Stars: %-3d Stardate%5d.%1d %9ld",
+ " ", 0, 0, 0, 0, 0, 0, smarts * 100, 0, 0L);
+ mvaddstr(0,0,spbuf);
+ oldeenergy = oldbenergy = oldcurscore =
+ oldstatus = oldetorp = oldbtorp = oldstrs = oldenemies = -1;
+ /* force everything to fill in */
+ damage = olddamage = 0;
+ for (i=0; i<MAXDAMAGE; i++)
+ damflag[i] = 0;
+ btorp = 500;
+ etorp = 50;
+}
diff --git a/warp/init.h b/warp/init.h
new file mode 100644
index 00000000..207bea88
--- /dev/null
+++ b/warp/init.h
@@ -0,0 +1,27 @@
+/* $Header: /cvsroot/src/games/warp/init.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: init.h,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 86/10/08 15:12:17 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+void initialize();
diff --git a/warp/intrp.c b/warp/intrp.c
new file mode 100644
index 00000000..c134e8a6
--- /dev/null
+++ b/warp/intrp.c
@@ -0,0 +1,590 @@
+/* $Header: /cvsroot/src/games/warp/intrp.c,v 1.1 2020/11/09 23:37:05 kamil Exp $
+ *
+ * Revision 7.0.1.2 86/12/12 16:59:04 lwall
+ * Baseline for net release.
+ *
+ * Revision 7.0.1.1 86/10/16 10:51:43 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:12:19 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "sig.h"
+#include "util.h"
+#include "term.h"
+#include "INTERN.h"
+#include "intrp.h"
+
+/* name of this host */
+ char *hostname;
+
+#ifdef TILDENAME
+static char *tildename = Nullch;
+static char *tildedir = Nullch;
+#endif
+
+char *dointerp();
+char *getrealname();
+#ifdef CONDSUB
+char *skipinterp();
+#endif
+
+static void abort_interp();
+
+void
+intrp_init(tcbuf)
+char *tcbuf;
+{
+ char *getlogin();
+
+ /* get environmental stuff */
+
+ /* get home directory */
+
+ homedir = getenv("HOME");
+ if (homedir == Nullch)
+ homedir = getenv("LOGDIR");
+
+ dotdir = getval("DOTDIR",homedir);
+
+ /* get login name */
+
+ logname = getenv("USER");
+ if (logname == Nullch)
+ logname = getenv("LOGNAME");
+#ifdef GETLOGIN
+ if (logname == Nullch)
+ logname = savestr(getlogin());
+#endif
+
+ /* get the real name of the person (%N) */
+ /* Must be done after logname is read in because BERKNAMES uses that */
+
+ strcpy(tcbuf,getrealname(getuid()));
+ realname = savestr(tcbuf);
+
+ /* name of this host (%H) */
+
+ gethostname(buf,sizeof buf);
+ hostname = savestr(buf);
+ if (index(hostname,'.'))
+ hostname = savestr(hostname);
+ else {
+ char hname[128];
+
+ strcpy(hname,hostname);
+ strcat(hname,MYDOMAIN);
+ hostname=savestr(hname);
+ }
+ warplib = savestr(filexp(WARPLIB));
+
+ if (scorespec) /* that getwd below takes ~1/3 sec. */
+ return; /* and we do not need it for -s */
+ (void) getwd(tcbuf); /* find working directory name */
+ origdir = savestr(tcbuf); /* and remember it */
+}
+
+/* expand filename via %, ~, and $ interpretation */
+/* returns pointer to static area */
+/* Note that there is a 1-deep cache of ~name interpretation */
+
+char *
+filexp(s)
+Reg1 char *s;
+{
+ static char filename[CBUFLEN];
+ char scrbuf[CBUFLEN];
+ Reg2 char *d;
+
+#ifdef DEBUGGING
+ if (debug & DEB_FILEXP)
+ printf("< %s\r\n",s);
+#endif
+ interp(filename, (sizeof filename), s); /* interpret any % escapes */
+#ifdef DEBUGGING
+ if (debug & DEB_FILEXP)
+ printf("%% %s\r\n",filename);
+#endif
+ s = filename;
+ if (*s == '~') { /* does destination start with ~? */
+ if (!*(++s) || *s == '/') {
+ Sprintf(scrbuf,"%s%s",homedir,s);
+ /* swap $HOME for it */
+#ifdef DEBUGGING
+ if (debug & DEB_FILEXP)
+ printf("~ %s\r\n",scrbuf);
+#endif
+ strcpy(filename,scrbuf);
+ }
+ else {
+#ifdef TILDENAME
+ for (d=scrbuf; isalnum(*s); s++,d++)
+ *d = *s;
+ *d = '\0';
+ if (tildedir && strEQ(tildename,scrbuf)) {
+ strcpy(scrbuf,tildedir);
+ strcat(scrbuf, s);
+ strcpy(filename, scrbuf);
+#ifdef DEBUGGING
+ if (debug & DEB_FILEXP)
+ printf("r %s %s\r\n",tildename,tildedir);
+#endif
+ }
+ else {
+ if (tildename) {
+ free(tildename);
+ free(tildedir);
+ }
+ tildedir = Nullch;
+ tildename = savestr(scrbuf);
+ {
+ struct passwd *getpwnam();
+ struct passwd *pwd = getpwnam(tildename);
+
+ Sprintf(scrbuf,"%s%s",pwd->pw_dir,s);
+ tildedir = savestr(pwd->pw_dir);
+ strcpy(filename,scrbuf);
+ endpwent();
+ }
+ }
+#else /* !TILDENAME */
+#ifdef VERBOSE
+ IF(verbose)
+ fputs("~loginname not implemented.\r\n",stdout);
+ ELSE
+#endif
+#ifdef TERSE
+ fputs("~login not impl.\r\n",stdout);
+#endif
+#endif
+ }
+ }
+ else if (*s == '$') { /* starts with some env variable? */
+ d = scrbuf;
+ *d++ = '%';
+ if (s[1] == '{')
+ strcpy(d,s+2);
+ else {
+ *d++ = '{';
+ for (s++; isalnum(*s); s++) *d++ = *s;
+ /* skip over token */
+ *d++ = '}';
+ strcpy(d,s);
+ }
+#ifdef DEBUGGING
+ if (debug & DEB_FILEXP)
+ printf("$ %s\r\n",scrbuf);
+#endif
+ interp(filename, (sizeof filename), scrbuf);
+ /* this might do some extra '%'s but */
+ /* that is how the Mercedes Benz */
+ }
+#ifdef DEBUGGING
+ if (debug & DEB_FILEXP)
+ printf("> %s\r\n",filename);
+#endif
+ return filename;
+}
+
+#ifdef CONDSUB
+/* skip interpolations */
+
+char *
+skipinterp(pattern,stoppers)
+Reg1 char *pattern;
+char *stoppers;
+{
+
+ while (*pattern && (!stoppers || !index(stoppers,*pattern))) {
+#ifdef DEBUGGING
+ if (debug & 8)
+ printf("skipinterp till %s at %s\r\n",stoppers?stoppers:"",pattern);
+#endif
+ if (*pattern == '%' && pattern[1]) {
+ switch (*++pattern) {
+ case '{':
+ for (pattern++; *pattern && *pattern != '}'; pattern++)
+ if (*pattern == '\\')
+ pattern++;
+ break;
+#ifdef CONDSUB
+ case '(': {
+ pattern = skipinterp(pattern+1,"!=");
+ if (!*pattern)
+ goto getout;
+ for (pattern++; *pattern && *pattern != '?'; pattern++)
+ if (*pattern == '\\')
+ pattern++;
+ if (!*pattern)
+ goto getout;
+ pattern = skipinterp(pattern+1,":)");
+ if (*pattern == ':')
+ pattern = skipinterp(pattern+1,")");
+ break;
+ }
+#endif
+#ifdef BACKTICK
+ case '`': {
+ pattern = skipinterp(pattern+1,"`");
+ break;
+ }
+#endif
+#ifdef PROMPTTTY
+ case '"':
+ pattern = skipinterp(pattern+1,"\"");
+ break;
+#endif
+ default:
+ break;
+ }
+ pattern++;
+ }
+ else {
+ if (*pattern == '^' && pattern[1])
+ pattern += 2;
+ else if (*pattern == '\\' && pattern[1])
+ pattern += 2;
+ else
+ pattern++;
+ }
+ }
+getout:
+ return pattern; /* where we left off */
+}
+#endif
+
+/* interpret interpolations */
+
+char *
+dointerp(dest,destsize,pattern,stoppers)
+Reg1 char *dest;
+Reg2 int destsize;
+Reg3 char *pattern;
+char *stoppers;
+{
+ Reg4 char *s;
+ Reg5 int i;
+ char scrbuf[512];
+ bool upper = FALSE;
+ bool lastcomp = FALSE;
+ int metabit = 0;
+
+ while (*pattern && (!stoppers || !index(stoppers,*pattern))) {
+#ifdef DEBUGGING
+ if (debug & 8)
+ printf("dointerp till %s at %s\r\n",stoppers?stoppers:"",pattern);
+#endif
+ if (*pattern == '%' && pattern[1]) {
+ upper = FALSE;
+ lastcomp = FALSE;
+ for (s=Nullch; !s; ) {
+ switch (*++pattern) {
+ case '^':
+ upper = TRUE;
+ break;
+ case '_':
+ lastcomp = TRUE;
+ break;
+ case '{':
+ pattern = cpytill(scrbuf,pattern+1,'}');
+ if (s = index(scrbuf,'-'))
+ *s++ = '\0';
+ else
+ s = nullstr;
+ s = getval(scrbuf,s);
+ break;
+#ifdef CONDSUB
+ case '(': {
+ char rch;
+ bool matched;
+
+ pattern = dointerp(dest,destsize,pattern+1,"!=");
+ rch = *pattern;
+ if (rch == '!')
+ pattern++;
+ if (*pattern != '=')
+ goto getout;
+ pattern = cpytill(scrbuf,pattern+1,'?');
+ if (!*pattern)
+ goto getout;
+ if (*scrbuf == '^' && scrbuf[strlen(scrbuf)-1] == '$') {
+ scrbuf[strlen(scrbuf)-1] = '\0';
+ matched = strEQ(scrbuf+1,dest);
+ }
+ else
+ matched = instr(dest,scrbuf) != Nullch;
+ if (matched==(rch == '=')) {
+ pattern = dointerp(dest,destsize,pattern+1,":)");
+ if (*pattern == ':')
+ pattern = skipinterp(pattern+1,")");
+ }
+ else {
+ pattern = skipinterp(pattern+1,":)");
+ if (*pattern == ':')
+ pattern++;
+ pattern = dointerp(dest,destsize,pattern,")");
+ }
+ s = dest;
+ break;
+ }
+#endif
+#ifdef BACKTICK
+ case '`': {
+ FILE *pipefp, *popen();
+
+ pattern = dointerp(scrbuf,(sizeof scrbuf),pattern+1,"`");
+ pipefp = popen(scrbuf,"r");
+ if (pipefp != Nullfp) {
+ int len;
+
+ len = fread(scrbuf,sizeof(char),(sizeof scrbuf)-1,
+ pipefp);
+ scrbuf[len] = '\0';
+ pclose(pipefp);
+ }
+ else {
+ printf("\r\nCan't run %s\r\n",scrbuf);
+ *scrbuf = '\0';
+ }
+ for (s=scrbuf; *s; s++) {
+ if (*s == '\n') {
+ if (s[1])
+ *s = ' ';
+ else
+ *s = '\0';
+ }
+ }
+ s = scrbuf;
+ break;
+ }
+#endif
+#ifdef PROMPTTTY
+ case '"':
+ pattern = dointerp(scrbuf,(sizeof scrbuf),pattern+1,"\"");
+ fputs(scrbuf,stdout);
+ resetty();
+ gets(scrbuf);
+ crmode();
+ raw();
+ noecho();
+ nonl();
+ s = scrbuf;
+ break;
+#endif
+ case '~':
+ s = homedir;
+ break;
+ case '.':
+ s = dotdir;
+ break;
+ case '$':
+ s = scrbuf;
+ Sprintf(s,"%d",getpid());
+ break;
+ case 'H': /* host name */
+ s = hostname;
+ break;
+ case 'L': /* login id */
+ s = logname;
+ break;
+ case 'N': /* full name */
+ s = getval("NAME",realname);
+ break;
+ case 'O':
+ s = origdir;
+ break;
+ case 'p':
+ s = cwd;
+ break;
+ case 'X': /* warp library */
+ s = warplib;
+ break;
+ default:
+ if (--destsize <= 0)
+ abort_interp();
+ *dest++ = *pattern | metabit;
+ s = nullstr;
+ break;
+ }
+ }
+ if (!s)
+ s = nullstr;
+ pattern++;
+ if (upper || lastcomp) {
+ char *t;
+
+ if (s != scrbuf) {
+ Safecpy(scrbuf,s,(sizeof scrbuf));
+ s = scrbuf;
+ }
+ if (upper || !(t=rindex(s,'/')))
+ t = s;
+ while (*t && !isalpha(*t))
+ t++;
+ if (islower(*t))
+ *t = toupper(*t);
+ }
+ i = metabit; /* maybe get into register */
+ if (s == dest) {
+ while (*dest) {
+ if (--destsize <= 0)
+ abort_interp();
+ *dest++ |= i;
+ }
+ }
+ else {
+ while (*s) {
+ if (--destsize <= 0)
+ abort_interp();
+ *dest++ = *s++ | i;
+ }
+ }
+ }
+ else {
+ if (--destsize <= 0)
+ abort_interp();
+ if (*pattern == '^' && pattern[1]) {
+ ++pattern; /* skip uparrow */
+ i = *pattern; /* get char into a register */
+ if (i == '?')
+ *dest++ = '\177' | metabit;
+ else if (i == '(') {
+ metabit = 0200;
+ destsize++;
+ }
+ else if (i == ')') {
+ metabit = 0;
+ destsize++;
+ }
+ else
+ *dest++ = i & 037 | metabit;
+ pattern++;
+ }
+ else if (*pattern == '\\' && pattern[1]) {
+ ++pattern; /* skip backslash */
+ i = *pattern; /* get char into a register */
+
+ /* this used to be a switch but the if may save space */
+
+ if (i >= '0' && i <= '7') {
+ i = 1;
+ while (i < 01000 && *pattern >= '0' && *pattern <= '7') {
+ i <<= 3;
+ i += *pattern++ - '0';
+ }
+ *dest++ = i & 0377 | metabit;
+ --pattern;
+ }
+ else if (i == 'b')
+ *dest++ = '\b' | metabit;
+ else if (i == 'f')
+ *dest++ = '\f' | metabit;
+ else if (i == 'n')
+ *dest++ = '\n' | metabit;
+ else if (i == 'r')
+ *dest++ = '\r' | metabit;
+ else if (i == 't')
+ *dest++ = '\t' | metabit;
+ else
+ *dest++ = i | metabit;
+ pattern++;
+ }
+ else
+ *dest++ = *pattern++ | metabit;
+ }
+ }
+ *dest = '\0';
+getout:
+ return pattern; /* where we left off */
+}
+
+void
+interp(dest,destsize,pattern)
+char *dest;
+int destsize;
+char *pattern;
+{
+ (void) dointerp(dest,destsize,pattern,Nullch);
+#ifdef DEBUGGING
+ if (debug & DEB_FILEXP)
+ fputs(dest,stdout);
+#endif
+}
+
+/* get the person's real name from /etc/passwd */
+/* (string is overwritten, so it must be copied) */
+
+char *
+getrealname(uid)
+int uid;
+{
+ char *s, *c;
+
+#ifdef PASSNAMES
+ struct passwd *pwd = getpwuid(uid);
+
+ s = pwd->pw_gecos;
+#ifdef BERKNAMES
+#ifdef BERKJUNK
+ while (*s && !isalnum(*s) && *s != '&') s++;
+#endif
+ if ((c = index(s, ',')) != Nullch)
+ *c = '\0';
+ if ((c = index(s, ';')) != Nullch)
+ *c = '\0';
+ s = cpytill(buf,s,'&');
+ if (*s == '&') { /* whoever thought this one up was */
+ c = buf + strlen(buf); /* in the middle of the night */
+ strcat(c,logname); /* before the morning after */
+ strcat(c,s+1);
+ if (islower(*c))
+ *c = toupper(*c); /* gack and double gack */
+ }
+#else
+ if ((c = index(s, '(')) != Nullch)
+ *c = '\0';
+ if ((c = index(s, '-')) != Nullch)
+ s = c;
+ strcpy(buf,tmpbuf);
+#endif
+ endpwent();
+ return buf; /* return something static */
+#else
+ if ((tmpfp=fopen(filexp(FULLNAMEFILE),"r")) != Nullfp) {
+ Fgets(buf,sizeof buf,tmpfp);
+ Fclose(tmpfp);
+ }
+ else {
+ resetty();
+ printf("What is your name? ");
+ Fgets(buf,(sizeof buf),stdin);
+ crmode();
+ raw();
+ noecho();
+ nonl();
+ if (fork())
+ wait(0);
+ else {
+ setuid(getuid());
+ if ((tmpfp = fopen(filexp(FULLNAMEFILE),"w")) == NULL)
+ exit(1);
+ fprintf(tmpfp, "%s\n", buf);
+ Fclose(tmpfp);
+ exit(0);
+ }
+ }
+ buf[strlen(buf)-1] = '\0';
+ return buf;
+#endif
+}
+
+static void
+abort_interp()
+{
+ fputs("\r\n% interp buffer overflow!\r\n",stdout);
+ sig_catcher(0);
+}
diff --git a/warp/intrp.h b/warp/intrp.h
new file mode 100644
index 00000000..4f8afeae
--- /dev/null
+++ b/warp/intrp.h
@@ -0,0 +1,41 @@
+/* $Header: /cvsroot/src/games/warp/intrp.h,v 1.1 2020/11/09 23:37:05 kamil Exp $
+ *
+ * $Log: intrp.h,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.1 86/12/12 16:59:45 lwall
+ * Baseline for net release.
+ *
+ * Revision 7.0 86/10/08 15:12:27 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+EXT char *origdir INIT(Nullch); /* cwd when warp invoked */
+EXT char *homedir INIT(Nullch); /* login directory */
+EXT char *dotdir INIT(Nullch); /* where . files go */
+EXT char *logname INIT(Nullch); /* login id */
+EXT char *hostname; /* host name */
+EXT char *realname INIT(Nullch); /* real name from /etc/passwd */
+
+void intrp_init();
+char *filexp();
+char *dointerp();
+void interp();
+char *getrealname();
diff --git a/warp/move.c b/warp/move.c
new file mode 100644
index 00000000..5c6123ee
--- /dev/null
+++ b/warp/move.c
@@ -0,0 +1,698 @@
+/* $Header: /cvsroot/src/games/warp/move.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: move.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.2 86/10/20 14:37:06 lwall
+ * Picked some lint.
+ *
+ * Revision 7.0.1.1 86/10/16 10:52:09 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:12:40 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "bang.h"
+#include "object.h"
+#include "move.h"
+#include "play.h"
+#include "score.h"
+#include "term.h"
+#include "them.h"
+#include "us.h"
+#include "util.h"
+#include "weapon.h"
+#include "INTERN.h"
+#include "move.h"
+
+void
+move_init()
+{
+ ;
+}
+
+void
+bounce(obj)
+Reg4 OBJECT *obj;
+{
+ Reg1 int x;
+ Reg2 int y;
+ Reg3 int count=0;
+
+ y = (obj->posy - sgn(obj->vely) + YSIZE00) % YSIZE;
+ x = (obj->posx - sgn(obj->velx) + XSIZE00) % XSIZE;
+ while (occupant[y][x]) {
+ y = (y + rand_mod(3) - 1 + YSIZE00) % YSIZE;
+ x = (x + rand_mod(3) - 1 + XSIZE00) % XSIZE;
+ if (++count > 10000) { /* if universe full, get out of it fast */
+ unmake_object(obj);
+ if (ent) unmake_object(ent);
+ if (base) unmake_object(base);
+ finish = 1;
+ return;
+ }
+ }
+ obj->posy = y;
+ obj->posx = x;
+ obj->vely = 0;
+ obj->velx = 0;
+ occupant[y][x] = obj;
+ if (numamoebas && obj->image == ' ')
+ mvaddc(y+1, x*2, amb[y][x]);
+ else
+ mvaddc(y+1, x*2, obj->image);
+}
+
+void
+move_universe()
+{
+ Reg1 OBJECT *curobj;
+ Reg2 int x;
+ Reg3 int y;
+ Reg4 OBJECT *temp;
+ OBJECT *thenext;
+
+ for (curobj = movers; curobj != &root; curobj = curobj->next) {
+ x = curobj->posx;
+ y = curobj->posy;
+ if (curobj == occupant[y][x]) {
+ occupant[y][x] = 0;
+ }
+ else if (curobj->type != Torp && curobj->type != Web) {
+ resetty();
+ abort();
+ }
+ }
+ for (curobj = movers; curobj != &root; curobj = thenext) {
+ thenext = curobj->next;
+ if (curobj->vely || curobj->velx) {
+ y = curobj->posy;
+ x = curobj->posx;
+ if (curobj->image != ' ' &&
+ (!(temp=occupant[y][x]) || temp->image==' ') ) {
+ move(y+1, x*2, numamoebas ? amb[y][x] : ' ');
+ }
+ y = (y + curobj->vely + YSIZE00) % YSIZE;
+ x = (x + curobj->velx + XSIZE00) % XSIZE;
+ if (!(temp=occupant[y][x]) || temp->type != Star ||
+ curobj->type != Torp || curobj->image == '+' ||
+ curobj->image == 'x') {
+ curobj->posy = y;
+ curobj->posx = x;
+ }
+ else {
+ if (curobj->image == '0') {
+ curobj->vely = rand_mod(3)-1;
+ curobj->velx = rand_mod(3)-1;
+ }
+ else
+ curobj->vely = curobj->velx = 0;
+ y = curobj->posy;
+ x = curobj->posx;
+ }
+ }
+ else { /* not moving */
+ y = curobj->posy;
+ x = curobj->posx;
+ if (curobj->type == Torp ||
+ curobj->type == Star ||
+ curobj->type == Web) {
+ curobj->flags |= STATIC;
+ curobj->next->prev = curobj->prev;
+ curobj->prev->next = curobj->next;
+ curobj->prev = movers->prev;
+ curobj->next = movers;
+ movers->prev->next = curobj;
+ movers->prev = curobj;
+ }
+ }
+ if (temp = occupant[y][x]) { /* already occupied? */
+ if (!temp->contend) {
+ if (temp->type == Torp) {
+ if (temp->image == '+')
+ blast[y][x] += 1250;
+ else if (temp->image == 'o' && (base||ent))
+ blast[y][x] += 500+super*20;
+ else if (temp->image == 'O' && (base||ent))
+ blast[y][x] += 5000+super*100;
+ }
+ }
+ yblasted[y] |= 1;
+ xblasted[x] |= 1;
+ blasted = TRUE;
+ curobj->contend = temp;
+ occupant[y][x] = curobj;
+ switch (curobj->type) {
+ case Enemy:
+ if (numamoebas && curobj == nuke && temp->image == '+')
+ blast[y][x] += 80000;
+ else if (temp->type == Enemy)
+ blast[y][x] += 10;
+ else
+ goto defblast;
+ break;
+ case Crusher:
+ if (curobj->velx)
+ blast[y][x] += 100000;
+ else
+ goto defblast;
+ break;
+ case Torp:
+ if (curobj->image == '+')
+ blast[y][x] += (temp==nuke ? 80000 : 1250);
+ else if (curobj->image == 'o')
+ blast[y][x] += 500+super*20;
+ else if (curobj->image == 'O')
+ blast[y][x] += 5000+super*100;
+ goto defblast;
+ case Star:
+ if (temp == ent)
+ goto damshield;
+ goto defblast;
+ case Enterprise:
+ if (temp->type == Star) {
+ damshield:
+ if (!rand_mod(10)) {
+ if (!damflag[NOSHIELDS])
+ damage++;
+ if (damflag[NOSHIELDS] < 100)
+ damflag[NOSHIELDS] += rand_mod(smarts)/5+2;
+ }
+ }
+ goto defblast;
+ default:
+ defblast:
+ blast[y][x] += rand_mod(751)+1;
+ break;
+ }
+ }
+ else {
+ occupant[y][x] = curobj;
+ if (curobj->image != ' ' &&
+ (curobj->velx || curobj->vely ||
+ curobj->type == Torp || curobj->type == Web) ) {
+ mvaddc(y+1, x*2, curobj->image);
+ }
+ if (curobj->type == Crusher && curobj->velx) {
+ blast[y][x] += 100000;
+ yblasted[y] |= 1;
+ xblasted[x] |= 1;
+ blasted = TRUE;
+ }
+ }
+ }
+ if (blasted) {
+ Reg7 int minxblast = -1;
+ Reg8 int maxxblast = -2;
+ Reg5 long tmpblast;
+
+ blasted = numamoebas;
+ for (x=0; x<XSIZE; x++) {
+ if (xblasted[x]) {
+ xblasted[x] = 0;
+ maxxblast = x;
+ if (minxblast < 0)
+ minxblast = x;
+ }
+ }
+ for (y=0; y<YSIZE; y++) {
+ if (yblasted[y]) {
+ yblasted[y] = 0;
+ for (x=minxblast; x<=maxxblast; x++) {
+ tmpblast = blast[y][x];
+ if (numamoebas && amb[y][x] == '~') {
+ if (temp = occupant[y][x]) {
+ if (temp->image == '&')
+ tmpblast >>= 1;
+ else if (temp->type == Web)
+ tmpblast = 100000;
+ else
+ tmpblast += 50 + temp->energy/100;
+ if (tmpblast > 250 && !rand_mod(5+(inumstars>>4)))
+ modify_amoeba(y,x,1,'~',5);
+ }
+ xblasted[x] = 2;
+ yblasted[y] = 2;
+ }
+ if (tmpblast) {
+ Reg6 OBJECT *biggie = 0;
+
+ blast[y][x] = 0;
+ temp = occupant[y][x];
+ if (tmpblast < 0) {
+ if (numamoebas && tmpblast < -1000000 &&
+ amb[y][x] == '~' && temp != nuke) {
+ amb[y][x] = ' ';
+ if (!temp)
+ make_plink(y,x);
+ ambsize--;
+ }
+ tmpblast = 0;
+ }
+ if (temp) {
+ if ((!numamoebas || amb[y][x]==' ') &&
+ tmpblast < 100000)
+ make_plink(y,x);
+ for ( ;temp;
+ temp = curobj->contend,curobj->contend = 0){
+ curobj = temp;
+ switch (curobj->type) {
+ case Enterprise: {
+ long tmp = curobj->energy;
+
+ if (ent->energy>500 || apolloflag & 1)
+ curobj->energy -= tmpblast /
+ ((apolloflag & 1)
+ ? 20
+ : (5+abs(ent->velx)+abs(ent->vely))
+ / ((damflag[NOSHIELDS]>>3)+1)+1);
+ else
+ curobj->energy -= tmpblast;
+ if (rand_mod(1 + tmp - curobj->energy) > 100
+ || ent->energy < (entmax>>1)) {
+ if (debug & 128 ||
+ (damage <= smarts/10 &&
+ !rand_mod(6-smarts/20-massacre) )) {
+ tmp = rand_mod(MAXDAMAGE);
+ if (damflag[tmp]) {
+ if (damflag[tmp] < 60)
+ damflag[tmp] += rand_mod(60);
+ }
+ else {
+ damflag[tmp] =
+ rand_mod(smarts+10)+2;
+ damage++;
+ }
+ }
+ }
+ break;
+ }
+ case Base:
+ if (base->energy > 1000 || apolloflag & 2)
+ curobj->energy -= tmpblast /
+ ((apolloflag & 2)?20:5);
+ else
+ curobj->energy -= tmpblast;
+ break;
+ case Crusher:
+ if (tmpblast > 132767)
+ curobj->energy -= (tmpblast - 100000);
+ else if (tmpblast >= 100000) {
+ curobj->energy += (tmpblast - 100000);
+ if (curobj->energy > 32767)
+ curobj->energy = 32767;
+ }
+ else /* vulnerable while feeding */
+ curobj->energy -= tmpblast;
+ break;
+ case Enemy:
+ curobj->energy -= tmpblast*10/enemshields;
+ break;
+ default:
+ curobj->energy -= tmpblast;
+ break;
+ }
+ if (curobj->energy < 0) { /* killed it? */
+ switch (curobj->image) {
+ case 'A':
+ tmpblast = 100000;
+ make_blast(y,x,8192L,1);
+ numapollos = apolloflag = 0;
+ numstars--;
+ numenemies--;
+ curscore += 5000;
+ deados = 0;
+ break;
+ case 'E': case 'e': case 'C': case 'c':
+ ent = 0;
+ numents--;
+ if (base)
+ status = 2;
+ else
+ status = 3;
+ deados = 0;
+ break;
+ case 'B': case 'b':
+ base = 0;
+ numbases--;
+ if (ent)
+ status = entmode;
+ else
+ status = 3;
+ deados = 0;
+ break;
+ case '&': {
+ int i, xxx, yyy;
+
+ for (i = 0; i < YSIZE; i++)
+ yblasted[i] &= 1;
+ for (i = 0; i < XSIZE; i++)
+ xblasted[i] &= 1;
+ numamoebas = 0; /* ignore amb[][] now */
+ for (yyy = 0; yyy < YSIZE; yyy++) {
+ for (xxx = 0; xxx < XSIZE; xxx++) {
+ if (amb[yyy][xxx] == '~' &&
+ !occupant[yyy][xxx]) {
+ mvaddch(yyy+1,xxx*2,' ');
+ }
+ }
+ }
+ numenemies--;
+ curscore += 10000;
+ if (curobj == enemies)
+ enemies = curobj->next;
+ deados = 0;
+ break;
+ }
+ case '<': case '>': {
+ int i;
+
+ numenemies--;
+ numcrushes = 0;
+ curscore += 10000;
+ if (curobj == movers)
+ movers = curobj->next;
+ if (curobj == enemies)
+ enemies = curobj->next;
+ deados = 0;
+
+ tmpblast = 100000;
+ make_blast(y,(x+XSIZE00)%XSIZE,10000L,0);
+ if (curobj->image == '<') {
+ for (i=XSIZE00; i<=XSIZE01; i++)
+ make_blast(y,(x+i)%XSIZE,
+ 10000L,0);
+ for (i=XSIZE00; i<=XSIZE02; i++)
+ make_blast(y,(x+i)%XSIZE,
+ 10000L,0);
+ make_blast(y,(x+XSIZE03)%XSIZE,
+ 10000L,1);
+ for (i=XSIZE00; i<=XSIZE08; i++)
+ make_blast(y,(x+i)%XSIZE,
+ 10000L,0);
+ }
+ else {
+ for (i=XSIZE00; i>=XSIZE99; i--)
+ make_blast(y,(x+i)%XSIZE,
+ 10000L,0);
+ for (i=XSIZE00; i>=XSIZE98; i--)
+ make_blast(y,(x+i)%XSIZE,
+ 10000L,0);
+ make_blast(y,(x+XSIZE97)%XSIZE,
+ 10000L,1);
+ for (i=XSIZE00; i>=XSIZE92; i--)
+ make_blast(y,(x+i)%XSIZE,
+ 10000L,0);
+ }
+ }
+ break;
+ case 'K':
+ numenemies--;
+ curscore += curobj->mass;
+ if (curobj == enemies)
+ enemies = curobj->next;
+ deados = 0;
+ break;
+ case 'T':
+ numenemies--;
+ curscore += curobj->mass*3/2;
+ if (curobj == enemies)
+ enemies = curobj->next;
+ deados = 0;
+ break;
+ case 'R': case ' ': case 'P':
+ numenemies--;
+ if (curobj->flags & PIRATE)
+ curscore += curobj->mass;
+ else
+ curscore += curobj->mass*3;
+ if (curobj == enemies)
+ enemies = curobj->next;
+ deados = 0;
+ break;
+ case 'G':
+ numenemies--;
+ numgorns--;
+ tmpblast = 100000;
+ if (madgorns)
+ curscore += curobj->mass/2;
+ else
+ curscore += curobj->mass*2;
+ if (curobj == enemies)
+ enemies = curobj->next;
+ {
+ int xxx,yyy;
+
+ for (xxx = -1; xxx<=1; xxx++)
+ for (yyy = -1; yyy<=1; yyy++)
+ if (rand_mod(2+massacre))
+ fire_torp(curobj,
+ yyy,xxx);
+ }
+ deados = 0;
+ break;
+ case '@':
+ numinhab--;
+ /* FALL THROUGH */
+ case '*':
+ banging = TRUE;
+ numstars--;
+ break;
+ case '|': case '-': case '/': case '\\':
+ tmpblast = 100000;
+ make_blast(y,x,curobj->mass,1);
+ banging = TRUE;
+ deados = 0;
+ break;
+ case 'x':
+ curscore += 10;
+ deados = 0;
+ break;
+ case 'X':
+ curscore += 100;
+ numxes--;
+ deados = 0;
+ break;
+ case '0':
+ curscore += 35;
+ numos--;
+ deados += 3;
+ break;
+ case 'o':
+ curscore += 100;
+ numos--;
+ deados++;
+ break;
+ case 'O':
+ curscore += 200;
+ numos--;
+ deados += 2;
+ break;
+ case 'M':
+ deadmudds++;
+ inumfriends--;
+ numfriends--;
+ if (curobj == enemies)
+ enemies = curobj->next;
+ break;
+ case 'Q': case 'W': case 'Y': case 'U':
+ case 'I': case 'S': case 'D': case 'H':
+ case 'J': case 'L': case 'Z': case 'V':
+ case 'F':
+ numfriends--;
+ if (curobj == enemies)
+ enemies = curobj->next;
+ if (inumfriends < 10)
+ madfriends += 500;
+ else
+ madfriends += 10000/inumfriends;
+ break;
+ }
+ if (tmpblast < 100000)
+ make_blast(y,x,curobj->mass,1);
+ unmake_object(curobj);
+ }
+ else { /* didn't kill anything */
+ if (!biggie)
+ biggie = curobj;
+ else {
+ if (biggie->mass > curobj->mass)
+ bounce(curobj);
+ else {
+ bounce(biggie);
+ biggie = curobj;
+ }
+ }
+ }
+ }
+ if (biggie) {
+ occupant[y][x] = biggie;
+ if (numamoebas && biggie->image == ' ')
+ mvaddch(y+1,x*2, amb[y][x]);
+ else
+ mvaddch(y+1,x*2, biggie->image);
+ }
+ else {
+ occupant[y][x] = 0;
+ mvaddch(y+1, x*2, numamoebas ? amb[y][x] : ' ');
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+ do_bangs();
+ if (numcrushes && movers->type == Crusher)
+ movers->vely = 0;
+ if (curobj = base) {
+ char ch;
+
+ curobj->velx = 0;
+ curobj->vely = 0;
+ curobj->energy += 25*lookaround(curobj->posy,curobj->posx,Star);
+ if (curobj->energy > basemax)
+ curobj->energy = basemax;
+ if (curobj->energy >= 1000)
+ ch = 'B';
+ else
+ ch = 'b';
+ if (ch != curobj->image) {
+ setimage(curobj, ch);
+ }
+ }
+ if (curobj = ent) {
+ char ch;
+
+ if (entmode == 0) {
+ curobj->velx = 0;
+ curobj->vely = 0;
+ }
+ if (base && !cloaking && !curobj->velx && !curobj->vely &&
+ lookfor(curobj->posy,curobj->posx,Base)) {
+ int tmp;
+
+#ifdef lint
+ tmp = 0;
+#else
+ tmp = (int) (base->energy - 1000 < entmax - curobj->energy ?
+ base->energy - 1000 : entmax - curobj->energy);
+#endif
+ if (tmp < 0)
+ tmp = 0;
+ curobj->energy += tmp;
+ base->energy -= tmp;
+ tmp = (btorp < 50 - etorp ?
+ btorp : 50 - etorp);
+ etorp += tmp;
+ btorp -= tmp;
+ if (damage) {
+ tmp = rand_mod(MAXDAMAGE);
+ if (damflag[tmp] > 5) {
+ damflag[tmp] = rand_mod(5)+1;
+ }
+ }
+ }
+ if (curobj->energy >= 500 && (!damage || !damflag[NOSHIELDS]))
+ ch = cloaked?'C':'E';
+ else
+ ch = cloaked?'c':'e';
+ if (ch != curobj->image) {
+ setimage(curobj, ch);
+ }
+ }
+}
+
+int
+lookaround(y, x, what)
+Reg1 int y;
+Reg2 int x;
+Reg4 char what;
+{
+ Reg3 OBJECT *obj;
+ Reg5 int count=0;
+ Reg6 int xp;
+ Reg7 int xm;
+
+ if ((obj=occupant[y][xp=(x+XSIZE01)%XSIZE])&&obj->type == what) /* 0, 1 */
+ count++;
+ if ((obj=occupant[y][xm=(x+XSIZE99)%XSIZE])&&obj->type == what) /* 0, -1 */
+ count++;
+ if ((obj=occupant[y=(y+YSIZE99)%YSIZE][xp])&&obj->type == what) /* -1, 1 */
+ count++;
+ if ((obj=occupant[y][x])&&obj->type == what) /* -1, 0 */
+ count++;
+ if ((obj=occupant[y][xm])&&obj->type == what) /* -1, -1 */
+ count++;
+ if ((obj=occupant[y=(y+2)%YSIZE][xp])&&obj->type == what) /* 1, 1 */
+ count++;
+ if ((obj=occupant[y][x])&&obj->type == what) /* 1, 0 */
+ count++;
+ if ((obj=occupant[y][xm])&&obj->type == what) /* 1, -1 */
+ count++;
+ return (count);
+}
+
+int
+lookfor(y, x, what)
+Reg1 int y;
+Reg2 int x;
+Reg4 char what;
+{
+ Reg3 OBJECT *obj;
+ Reg5 int xp;
+ Reg6 int xm;
+
+ if ((obj=occupant[y][xp=(x+XSIZE01)%XSIZE])&&obj->type == what ||/* 0, 1 */
+ (obj=occupant[y][xm=(x+XSIZE99)%XSIZE])&&obj->type == what ||/* 0, -1 */
+ (obj=occupant[y=(y+YSIZE99)%YSIZE][xp])&&obj->type == what ||/* -1, 1 */
+ (obj=occupant[y][x])&&obj->type == what ||/* -1, 0 */
+ (obj=occupant[y][xm])&&obj->type == what ||/* -1,-1 */
+ (obj=occupant[y=(y+2)%YSIZE][xp])&&obj->type == what ||/* 1, 1 */
+ (obj=occupant[y][x])&&obj->type == what ||/* 1, 0 */
+ (obj=occupant[y][xm])&&obj->type == what) /* 1, -1 */
+ return(1);
+ return (0);
+}
+
+OBJECT*
+lookimg(y, x, what)
+Reg1 int y;
+Reg2 int x;
+Reg4 char what;
+{
+ Reg3 OBJECT *obj;
+ Reg5 int xp;
+ Reg6 int xm;
+
+ if ((obj=occupant[y][xp=(x+XSIZE01)%XSIZE])&&obj->image==what ||/* 0, 1 */
+ (obj=occupant[y][xm=(x+XSIZE99)%XSIZE])&&obj->image==what ||/* 0, -1 */
+ (obj=occupant[y=(y+YSIZE99)%YSIZE][xp])&&obj->image==what ||/* -1, 1 */
+ (obj=occupant[y][x])&&obj->image==what ||/* -1, 0 */
+ (obj=occupant[y][xm])&&obj->image==what ||/* -1,-1 */
+ (obj=occupant[y=(y+2)%YSIZE][xp])&&obj->image==what ||/* 1, 1 */
+ (obj=occupant[y][x])&&obj->image==what ||/* 1, 0 */
+ (obj=occupant[y][xm])&&obj->image==what) /* 1, -1 */
+ return obj;
+ return Null(OBJECT*);
+}
diff --git a/warp/move.h b/warp/move.h
new file mode 100644
index 00000000..cd9379ce
--- /dev/null
+++ b/warp/move.h
@@ -0,0 +1,32 @@
+/* $Header: /cvsroot/src/games/warp/move.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: move.h,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 86/10/08 15:12:46 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+void bounce();
+void move_universe();
+int lookaround();
+int lookfor();
+OBJECT *lookimg();
+void move_init();
diff --git a/warp/object.c b/warp/object.c
new file mode 100644
index 00000000..e2108d5e
--- /dev/null
+++ b/warp/object.c
@@ -0,0 +1,100 @@
+/* $Header: /cvsroot/src/games/warp/object.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: object.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 86/10/08 15:12:55 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "INTERN.h"
+#include "object.h"
+
+void
+object_init()
+{
+ ;
+}
+
+OBJECT *
+make_object(typ, img, py, px, vy, vx, energ, mas, where)
+char typ;
+char img;
+int px, py, vx, vy;
+long energ, mas;
+OBJECT *where;
+{
+ Reg1 OBJECT *obj;
+
+ if (free_root.next == &free_root)
+#ifndef lint
+ obj = (OBJECT *) malloc(sizeof root);
+#else
+ obj = Null(OBJECT*);
+#endif
+ else {
+ obj = free_root.next;
+ free_root.next = obj->next;
+ obj->next->prev = &free_root;
+ }
+ obj->type = typ;
+ obj->image = img;
+ obj->next = where;
+ obj->prev = where->prev;
+ where->prev = obj;
+ obj->prev->next = obj;
+ obj->velx = vx;
+ obj->vely = vy;
+ obj->contend = 0;
+ obj->strategy = 0;
+ obj->flags = 0;
+ obj->posx = px;
+ obj->posy = py;
+ if (typ != Torp && typ != Web) {
+ occupant[py][px] = obj;
+ }
+ obj->energy = energ;
+ obj->mass = mas;
+ return(obj);
+}
+
+void
+unmake_object(curobj)
+Reg1 OBJECT *curobj;
+{
+ curobj->prev->next = curobj->next;
+ curobj->next->prev = curobj->prev;
+ if (curobj == movers) {
+ movers = curobj->next;
+ }
+ free_object(curobj);
+}
+
+void
+free_object(curobj)
+Reg1 OBJECT *curobj;
+{
+ curobj->next = free_root.next;
+ curobj->prev = &free_root;
+ free_root.next->prev = curobj;
+ free_root.next = curobj;
+}
diff --git a/warp/object.h b/warp/object.h
new file mode 100644
index 00000000..619ec764
--- /dev/null
+++ b/warp/object.h
@@ -0,0 +1,89 @@
+/* $Header: /cvsroot/src/games/warp/object.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: object.h,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.2 86/12/12 17:01:38 lwall
+ * Baseline for net release.
+ *
+ * Revision 7.0.1.1 86/10/16 10:52:30 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:13:04 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#define Root 0
+#define Base 1
+#define Enterprise 2
+#define Star 3
+#define Torp 4
+#define Enemy 5
+#define Web 6
+#define Crusher 7
+
+typedef struct object {
+ char posx, posy;
+#ifdef SIGNEDCHAR
+ char velx, vely;
+#else
+ short velx, vely;
+#endif
+ struct object *next, *prev, *contend;
+ long energy;
+ long mass;
+ char type;
+ char image;
+ char strategy;
+ char flags;
+} OBJECT;
+
+#define PIRATE 1 /* we may mutiny */
+#define FRIENDLY 2 /* we aren't really an enemy, for now */
+#define STATIC 4 /* we are not in the movers list at the moment */
+#define COUNTDOWN 8 /* we are counting down for something */
+#define CLOAKS 16 /* we can cloak */
+
+#ifdef DOINIT
+OBJECT root = {0, 0, 0, 0, &root, &root, 0, 0, 0, Root, '?', 0, 0};
+#else
+EXT OBJECT root;
+#endif
+
+#ifdef DOINIT
+OBJECT free_root = {0, 0, 0, 0, &free_root, &free_root, 0, 0, 0, Root, '?', 0, 0};
+#else
+EXT OBJECT free_root;
+#endif
+
+EXT OBJECT *ent;
+EXT OBJECT *base;
+EXT OBJECT *enemies;
+EXT OBJECT *movers;
+EXT OBJECT *realapollo;
+EXT OBJECT *nuke;
+
+EXT OBJECT *occupant[YSIZE][XSIZE];
+
+OBJECT *make_object();
+
+void unmake_object();
+void free_object();
+void object_init();
diff --git a/warp/patchlevel.h b/warp/patchlevel.h
new file mode 100644
index 00000000..558d48cd
--- /dev/null
+++ b/warp/patchlevel.h
@@ -0,0 +1 @@
+#define PATCHLEVEL 3
diff --git a/warp/play.c b/warp/play.c
new file mode 100644
index 00000000..1397f7b9
--- /dev/null
+++ b/warp/play.c
@@ -0,0 +1,198 @@
+/* $Header: /cvsroot/src/games/warp/play.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: play.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.1 86/10/16 10:52:39 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:13:09 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "bang.h"
+#include "score.h"
+#include "object.h"
+#include "move.h"
+#include "term.h"
+#include "them.h"
+#include "us.h"
+#include "util.h"
+#include "weapon.h"
+#include "INTERN.h"
+#include "play.h"
+
+void
+play_init()
+{
+ ;
+}
+
+void
+play()
+{
+ bool done = FALSE;
+ Reg1 OBJECT *curobj;
+ Reg2 OBJECT *to;
+ Reg3 int i;
+ Reg4 int x;
+ Reg5 int y;
+
+ display_status();
+#ifdef TIOCOUTQ
+ while (output_pending() > charsperhalfsec)
+ sleep(1); /* allow buffers to empty */
+#endif
+ sleep(3);
+ do {
+ timer++;
+ nxtbang = 0;
+ banging = FALSE;
+ display_status();
+#ifdef TIOCOUTQ
+ while (output_pending() > charsperhalfsec)
+ sleep(1);
+#endif
+ if (lowspeed)
+ roundsleep(2);
+ else
+ roundsleep(1);
+ if (ent) {
+ evely = ent->vely;
+ evelx = ent->velx;
+ if (cloaking && ent->energy >= 250 && !damflag[NOCLOAKING]) {
+ if (!rand_mod(300)) {
+ damage++;
+ damflag[NOCLOAKING] = rand_mod(smarts+1)+2;
+ }
+ ent->energy -= ent->energy/40;
+ }
+ else
+ cloaking = FALSE;
+ cloaked = cloaking;
+ }
+ if (base) {
+ bvely = base->vely;
+ bvelx = base->velx;
+ }
+ get_commands(&done);
+ if (done)
+ break;
+ their_smarts();
+ apolloflag = 0;
+ if (ent) {
+ if (numapollos) {
+ if (numstars) {
+ if (realapollo) {
+ if (lookfor(realapollo->posy,realapollo->posx,
+ Enterprise)) {
+ apolloflag = 1;
+ }
+ }
+ else if (lookfor(root.next->posy,root.next->posx,
+ Enterprise)) {
+ apolloflag = 1;
+ realapollo = root.next;
+ mvaddch(realapollo->posy+1,realapollo->posx*2,
+ 'A');
+ realapollo->image = 'A';
+ realapollo->mass = 6000;
+ inumapollos = 1;
+ numenemies++;
+ inumenemies++;
+ possiblescore += 5000;
+ }
+ if (apolloflag) {
+ if (blast[realapollo->posy][realapollo->posx] <= 32000)
+ evely = evelx = 0;
+ realapollo->energy = 32000;
+ }
+ }
+ else
+ numapollos = 0;
+ }
+ ent->vely = evely;
+ ent->velx = evelx;
+ }
+ if (base) {
+ if (numapollos) {
+ if (numstars) {
+ if (realapollo) {
+ if (lookfor(realapollo->posy,realapollo->posx,
+ Base)) {
+ apolloflag |= 2;
+ }
+ }
+ else if (lookfor(root.next->posy,root.next->posx,
+ Base)) {
+ apolloflag |= 2;
+ realapollo = root.next;
+ mvaddch(realapollo->posy+1,realapollo->posx*2,
+ 'A');
+ realapollo->image = 'A';
+ realapollo->mass = 6000;
+ inumapollos = 1;
+ numenemies++;
+ inumenemies++;
+ possiblescore += 5000;
+ }
+ if (apolloflag & 2) {
+ if (blast[realapollo->posy][realapollo->posx] <= 32000)
+ bvely = bvelx = 0;
+ realapollo->energy = 32000;
+ }
+ }
+ else
+ numapollos = 0;
+ }
+ base->vely = bvely;
+ base->velx = bvelx;
+ }
+ if (aretorps) {
+ aretorps = 0;
+ for (i=0;i<2;i++) for (y=0;y<3;y++) for (x=0;x<3;x++) {
+ if (curobj = isatorp[i][y][x]) {
+ to = occupant[(curobj->posy+curobj->vely+YSIZE00)%YSIZE]
+ [(curobj->posx+curobj->velx+XSIZE00)%XSIZE];
+ if (to && !to->vely && !to->velx) {
+ unmake_object(curobj);
+ if (i)
+ btorp++;
+ else
+ etorp++;
+ }
+ isatorp[i][y][x]=0;
+ }
+ }
+ }
+ move_universe();
+ if (finish) {
+ finish--;
+ if (!finish && (!(numenemies || numos) || (!ent && !base))) {
+ done = TRUE;
+ timer -= 5;
+ }
+ }
+ else if (!banging && (!(numenemies || numos) || (!ent && !base)))
+ finish = 5;
+ } while (!done);
+}
diff --git a/warp/play.h b/warp/play.h
new file mode 100644
index 00000000..06813cb7
--- /dev/null
+++ b/warp/play.h
@@ -0,0 +1,31 @@
+/* $Header: /cvsroot/src/games/warp/play.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: play.h,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 86/10/08 15:13:12 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+EXT int finish INIT(0);
+EXT int timer;
+
+void play();
+void play_init();
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);
+}
diff --git a/warp/score.h b/warp/score.h
new file mode 100644
index 00000000..bd5871d8
--- /dev/null
+++ b/warp/score.h
@@ -0,0 +1,67 @@
+/* $Header: /cvsroot/src/games/warp/score.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: score.h,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 86/10/08 15:13:21 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#define ENTBOUNDARY 100000 /* point boundary across which a new E is
+ awarded */
+
+#define BASEBOUNDARY 250000 /* point boundary across which a new B is
+ awarded */
+
+EXT int oldstatus;
+EXT int oldetorp;
+EXT int oldbtorp;
+EXT int oldstrs;
+EXT int oldenemies;
+
+EXT long totalscore;
+EXT long lastscore INIT(0);
+EXT long curscore;
+EXT long possiblescore;
+EXT long oldeenergy;
+EXT long oldbenergy;
+EXT long oldcurscore;
+
+EXT char savefilename[40];
+
+#ifdef SCOREFULL
+#define COMPOFF 0
+#define COMPNAME longlognam
+#define COMPLEN 24
+#else
+#define COMPOFF 24
+#define COMPNAME longlognam
+#define COMPLEN 8
+#endif
+EXT char longlognam[128];
+
+EXT char c INIT(' ');
+
+void score_init();
+void wscore();
+void display_status();
+void wavescore();
+void score();
+void save_game();
diff --git a/warp/sig.c b/warp/sig.c
new file mode 100644
index 00000000..a4cb1735
--- /dev/null
+++ b/warp/sig.c
@@ -0,0 +1,243 @@
+/* $Header: /cvsroot/src/games/warp/sig.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: sig.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.1a 87/07/03 01:47:11 games
+ * Changed sigsetmask to use sigmask instead of calculating it (incorrectly)
+ * by hand.
+ *
+ * Revision 7.0.1.1 86/12/12 17:02:44 lwall
+ * Baseline for net release.
+ *
+ * Revision 7.0 86/10/08 15:13:24 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "play.h"
+#include "score.h"
+#include "term.h"
+#include "util.h"
+#include "INTERN.h"
+#include "sig.h"
+
+void
+sig_init()
+{
+#ifdef lint
+ ;
+#else
+ sigignore(SIGINT); /* for inquiry of existence via kill call */
+#ifdef SIGTTOU
+ sigignore(SIGTTOU);
+#endif
+
+ sigset(SIGHUP, sig_catcher);
+ if (!debugging) {
+ sigset(SIGQUIT, sig_catcher);
+ sigset(SIGILL, sig_catcher);
+ sigset(SIGFPE, sig_catcher);
+ sigset(SIGBUS, sig_catcher);
+ sigset(SIGSEGV, sig_catcher);
+ sigset(SIGSYS, sig_catcher);
+ sigset(SIGTERM, sig_catcher);
+ }
+#ifdef SIGXCPU
+ sigset(SIGXCPU, sig_catcher);
+#endif
+#ifdef SIGCONT
+ sigset(SIGCONT, cont_catcher);
+#endif
+#ifdef SIGTSTP
+ sigset(SIGTSTP, stop_catcher);
+ sigset(SIGSTOP, stop_catcher);
+#endif
+#endif /* lint */
+}
+
+#ifdef SIGTSTP
+void
+cont_catcher()
+{
+#ifndef lint
+ sigset(SIGCONT,cont_catcher);
+#endif
+ savetty();
+ crmode();
+ raw();
+ noecho();
+ nonl();
+}
+#endif
+
+void
+mytstp()
+{
+ resetty();
+#ifdef SIGTSTP
+ kill(0,SIGTSTP);
+#else
+ if (fork())
+ wait(0);
+ else {
+ char *shell = getenv("SHELL");
+
+ setuid(getuid());
+ if (!*shell)
+ shell = "/bin/sh";
+ execl(shell,shell,0);
+ exit(1);
+ }
+#endif
+ rewrite();
+}
+
+void /* very much void */
+finalize(status)
+int status;
+{
+ if (bizarre)
+ resetty();
+ if (status < 0) {
+ chdir("/usr/tmp");
+ sigset(SIGILL,SIG_DFL);
+ abort();
+ }
+ exit(status);
+}
+
+/* come here on signal other than interrupt, stop, or cont */
+
+void
+sig_catcher(signo)
+{
+#ifdef VERBOSE
+ static char *signame[] = {
+ "",
+ "HUP",
+ "INT",
+ "QUIT",
+ "ILL",
+ "TRAP",
+ "IOT",
+ "EMT",
+ "FPE",
+ "KILL",
+ "BUS",
+ "SEGV",
+ "SYS",
+ "PIPE",
+ "ALRM",
+ "TERM",
+ "???"
+#ifdef SIGTSTP
+ ,"STOP",
+ "TSTP",
+ "CONT",
+ "CHLD",
+ "TTIN",
+ "TTOU",
+ "TINT",
+ "XCPU",
+ "XFSZ"
+#ifdef SIGPROF
+ ,"VTALARM",
+ "PROF"
+#endif
+#endif
+ };
+#endif
+
+#ifdef SIGTTOU
+#ifndef lint
+ sigignore(SIGTTOU);
+#endif /* lint */
+#endif
+#ifdef DEBUGGING
+ if (debug) {
+ printf("\r\nSIG%s--game not saved in debug\r\n",signame[signo]);
+ finalize(-1);
+ }
+#endif
+ panic++;
+ if (panic >= 2) {
+ if (panic >= 3)
+ abort();
+ chdir(SAVEDIR);
+ kill(0,SIGIOT);
+ }
+ (void) sigset(SIGILL,SIG_DFL);
+ if (signo == SIGHUP && (timer < 10 || didkill))
+ signo = SIGQUIT;
+ if (signo == SIGQUIT) { /* can't let them bomb out without penalty */
+ if (smarts < 20)
+ smarts += 4;
+ else if (smarts < 35)
+ smarts += 2;
+ else
+ smarts++;
+ totalscore -= possiblescore / 2;
+ }
+ save_game();
+ if (signo != SIGHUP && signo != SIGQUIT)
+#ifdef VERBOSE
+ IF(verbose)
+ printf("\r\nCaught %s%s--%s\r\n",
+ signo ? "a SIG" : "an internal error", signame[signo],
+ experimenting ? "game saved" : "bye bye");
+ ELSE
+#endif
+#ifdef TERSE
+ printf("\r\nSignal %d--bye bye\r\n",signo);
+#endif
+ switch (signo) {
+ case SIGBUS:
+ case SIGILL:
+ case SIGSEGV:
+ finalize(-signo);
+ }
+ finalize(1); /* and blow up */
+}
+
+#ifdef SIGTSTP
+/* come here on stop signal */
+
+void
+stop_catcher()
+{
+ if (!waiting) {
+ resetty(); /* this is the point of all this */
+#ifdef DEBUGGING
+ if (debug)
+ write(2,"stop_catcher\r\n",13);
+#endif
+ sigset(SIGTSTP,SIG_DFL); /* enable stop */
+#ifdef BSD42
+ sigsetmask(sigblock(0L) & ~sigmask(SIGTSTP));
+#endif
+ kill(0,SIGTSTP); /* and do the stop */
+ }
+#ifndef lint
+ sigset(SIGTSTP,stop_catcher); /* unenable the stop */
+#endif
+}
+#endif
diff --git a/warp/sig.h b/warp/sig.h
new file mode 100644
index 00000000..610ece13
--- /dev/null
+++ b/warp/sig.h
@@ -0,0 +1,34 @@
+/* $Header: /cvsroot/src/games/warp/sig.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: sig.h,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 86/10/08 15:13:32 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+void sig_catcher();
+#ifdef SIGTSTP
+void cont_catcher();
+void stop_catcher();
+#endif
+void mytstp();
+void sig_init();
+void finalize();
diff --git a/warp/sm.c b/warp/sm.c
new file mode 100644
index 00000000..992cebbc
--- /dev/null
+++ b/warp/sm.c
@@ -0,0 +1,99 @@
+/* $Header: /cvsroot/src/games/warp/sm.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: sm.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 86/10/08 15:13:35 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include <stdio.h>
+#include <ctype.h>
+#include "config.h"
+
+main()
+{
+ char screen[23][90], buf[10];
+ Reg1 int y;
+ Reg2 int x;
+ int tmpy, tmpx;
+
+ for (x=0; x<79; x++)
+ screen[0][x] = ' ';
+ screen[0][79] = '\0';
+
+ fgets(screen[0],90,stdin);
+ if (isdigit(screen[0][0])) {
+ int numstars = atoi(screen[0]);
+
+ for (y=0; y<23; y++) {
+ for (x=0; x<79; x++)
+ screen[y][x] = ' ';
+ screen[y][79] = '\0';
+ }
+
+ for ( ; numstars; numstars--) {
+ scanf("%d %d\n",&tmpy,&tmpx);
+ y = tmpy;
+ x = tmpx;
+ screen[y][x+x] = '*';
+ }
+
+ for (y=0; y<23; y++) {
+ printf("%s\n",screen[y]);
+ }
+ }
+ else {
+ Reg3 int numstars = 0;
+
+ for (y=1; y<23; y++) {
+ for (x=0; x<79; x++)
+ screen[y][x] = ' ';
+ screen[y][79] = '\0';
+ }
+
+ for (y=1; y<23; y++) {
+ fgets(screen[y],90,stdin);
+ }
+
+ for (y=0; y<23; y++) {
+ for (x=0; x<80; x += 2) {
+ if (screen[y][x] == '*') {
+ numstars++;
+ }
+ else if (screen[y][x] == '\t' || screen[y][x+1] == '\t') {
+ fprintf(stderr,"Cannot have tabs in starmap--please expand.\n");
+ exit(1);
+ }
+ }
+ }
+
+ printf("%d\n",numstars);
+
+ for (y=0; y<23; y++) {
+ for (x=0; x<80; x += 2) {
+ if (screen[y][x] == '*') {
+ printf("%d %d\n",y,x/2);
+ }
+ }
+ }
+ }
+ exit(0);
+}
diff --git a/warp/smap.0 b/warp/smap.0
new file mode 100644
index 00000000..c67896f0
--- /dev/null
+++ b/warp/smap.0
@@ -0,0 +1,621 @@
+620
+0 0
+0 2
+0 4
+0 6
+0 8
+0 10
+0 12
+0 14
+0 16
+0 18
+0 20
+0 22
+0 24
+0 26
+0 28
+0 30
+0 32
+0 34
+0 36
+0 38
+1 0
+1 1
+1 2
+1 3
+1 4
+1 5
+1 6
+1 7
+1 8
+1 9
+1 10
+1 11
+1 12
+1 13
+1 14
+1 15
+1 16
+1 17
+1 18
+1 19
+1 20
+1 21
+1 22
+1 23
+1 24
+1 25
+1 26
+1 27
+1 28
+1 29
+1 30
+1 31
+1 32
+1 33
+1 34
+1 35
+1 36
+1 37
+1 38
+1 39
+2 0
+2 2
+2 4
+2 6
+2 8
+2 10
+2 12
+2 14
+2 16
+2 18
+2 20
+2 22
+2 24
+2 26
+2 28
+2 30
+2 32
+2 34
+2 36
+2 38
+3 0
+3 1
+3 2
+3 3
+3 4
+3 5
+3 6
+3 7
+3 8
+3 9
+3 10
+3 11
+3 12
+3 13
+3 14
+3 15
+3 16
+3 17
+3 18
+3 19
+3 20
+3 21
+3 22
+3 23
+3 24
+3 25
+3 26
+3 27
+3 28
+3 29
+3 30
+3 31
+3 32
+3 33
+3 34
+3 35
+3 36
+3 37
+3 38
+3 39
+4 0
+4 2
+4 4
+4 6
+4 8
+4 10
+4 12
+4 14
+4 16
+4 18
+4 20
+4 22
+4 24
+4 26
+4 28
+4 30
+4 32
+4 34
+4 36
+4 38
+5 0
+5 2
+5 4
+5 6
+5 8
+5 10
+5 12
+5 14
+5 16
+5 18
+5 20
+5 22
+5 24
+5 26
+5 28
+5 30
+5 32
+5 34
+5 36
+5 38
+6 0
+6 2
+6 4
+6 6
+6 8
+6 10
+6 12
+6 14
+6 16
+6 18
+6 20
+6 22
+6 24
+6 26
+6 28
+6 30
+6 32
+6 34
+6 36
+6 38
+7 0
+7 1
+7 2
+7 3
+7 4
+7 5
+7 6
+7 7
+7 8
+7 9
+7 10
+7 11
+7 12
+7 13
+7 14
+7 15
+7 16
+7 17
+7 18
+7 19
+7 20
+7 21
+7 22
+7 23
+7 24
+7 25
+7 26
+7 27
+7 28
+7 29
+7 30
+7 31
+7 32
+7 33
+7 34
+7 35
+7 36
+7 37
+7 38
+7 39
+8 0
+8 2
+8 4
+8 6
+8 8
+8 10
+8 12
+8 14
+8 16
+8 18
+8 20
+8 22
+8 24
+8 26
+8 28
+8 30
+8 32
+8 34
+8 36
+8 38
+9 0
+9 1
+9 2
+9 3
+9 4
+9 5
+9 6
+9 7
+9 8
+9 9
+9 10
+9 11
+9 12
+9 13
+9 14
+9 15
+9 16
+9 17
+9 18
+9 19
+9 20
+9 21
+9 22
+9 23
+9 24
+9 25
+9 26
+9 27
+9 28
+9 29
+9 30
+9 31
+9 32
+9 33
+9 34
+9 35
+9 36
+9 37
+9 38
+9 39
+10 0
+10 2
+10 4
+10 6
+10 8
+10 10
+10 12
+10 14
+10 16
+10 18
+10 20
+10 22
+10 24
+10 26
+10 28
+10 30
+10 32
+10 34
+10 36
+10 38
+11 0
+11 2
+11 4
+11 6
+11 8
+11 10
+11 12
+11 14
+11 16
+11 18
+11 20
+11 22
+11 24
+11 26
+11 28
+11 30
+11 32
+11 34
+11 36
+11 38
+12 0
+12 1
+12 2
+12 3
+12 4
+12 5
+12 6
+12 7
+12 8
+12 9
+12 10
+12 11
+12 12
+12 13
+12 14
+12 15
+12 16
+12 17
+12 18
+12 19
+12 20
+12 21
+12 22
+12 23
+12 24
+12 25
+12 26
+12 27
+12 28
+12 29
+12 30
+12 31
+12 32
+12 33
+12 34
+12 35
+12 36
+12 37
+12 38
+12 39
+13 0
+13 2
+13 4
+13 6
+13 8
+13 10
+13 12
+13 14
+13 16
+13 18
+13 20
+13 22
+13 24
+13 26
+13 28
+13 30
+13 32
+13 34
+13 36
+13 38
+14 0
+14 2
+14 4
+14 6
+14 8
+14 10
+14 12
+14 14
+14 16
+14 18
+14 20
+14 22
+14 24
+14 26
+14 28
+14 30
+14 32
+14 34
+14 36
+14 38
+15 0
+15 2
+15 4
+15 6
+15 8
+15 10
+15 12
+15 14
+15 16
+15 18
+15 20
+15 22
+15 24
+15 26
+15 28
+15 30
+15 32
+15 34
+15 36
+15 38
+16 0
+16 2
+16 4
+16 6
+16 8
+16 10
+16 12
+16 14
+16 16
+16 18
+16 20
+16 22
+16 24
+16 26
+16 28
+16 30
+16 32
+16 34
+16 36
+16 38
+17 0
+17 2
+17 4
+17 6
+17 8
+17 10
+17 12
+17 14
+17 16
+17 18
+17 20
+17 22
+17 24
+17 26
+17 28
+17 30
+17 32
+17 34
+17 36
+17 38
+18 0
+18 1
+18 2
+18 3
+18 4
+18 5
+18 6
+18 7
+18 8
+18 9
+18 10
+18 11
+18 12
+18 13
+18 14
+18 15
+18 16
+18 17
+18 18
+18 19
+18 20
+18 21
+18 22
+18 23
+18 24
+18 25
+18 26
+18 27
+18 28
+18 29
+18 30
+18 31
+18 32
+18 33
+18 34
+18 35
+18 36
+18 37
+18 38
+18 39
+19 0
+19 1
+19 2
+19 3
+19 4
+19 5
+19 6
+19 7
+19 8
+19 9
+19 10
+19 11
+19 12
+19 13
+19 14
+19 15
+19 16
+19 17
+19 18
+19 19
+19 20
+19 21
+19 22
+19 23
+19 24
+19 25
+19 26
+19 27
+19 28
+19 29
+19 30
+19 31
+19 32
+19 33
+19 34
+19 35
+19 36
+19 37
+19 38
+19 39
+20 0
+20 2
+20 4
+20 6
+20 8
+20 10
+20 12
+20 14
+20 16
+20 18
+20 20
+20 22
+20 24
+20 26
+20 28
+20 30
+20 32
+20 34
+20 36
+20 38
+21 0
+21 2
+21 4
+21 6
+21 8
+21 10
+21 12
+21 14
+21 16
+21 18
+21 20
+21 22
+21 24
+21 26
+21 28
+21 30
+21 32
+21 34
+21 36
+21 38
+22 0
+22 1
+22 2
+22 3
+22 4
+22 5
+22 6
+22 7
+22 8
+22 9
+22 10
+22 11
+22 12
+22 13
+22 14
+22 15
+22 16
+22 17
+22 18
+22 19
+22 20
+22 21
+22 22
+22 23
+22 24
+22 25
+22 26
+22 27
+22 28
+22 29
+22 30
+22 31
+22 32
+22 33
+22 34
+22 35
+22 36
+22 37
+22 38
+22 39
diff --git a/warp/smap.1 b/warp/smap.1
new file mode 100644
index 00000000..0b0e5c60
--- /dev/null
+++ b/warp/smap.1
@@ -0,0 +1,621 @@
+620
+0 1
+0 3
+0 5
+0 7
+0 9
+0 11
+0 13
+0 15
+0 17
+0 19
+0 21
+0 23
+0 25
+0 27
+0 29
+0 31
+0 33
+0 35
+0 37
+0 39
+1 1
+1 3
+1 5
+1 7
+1 9
+1 11
+1 13
+1 15
+1 17
+1 19
+1 21
+1 23
+1 25
+1 27
+1 29
+1 31
+1 33
+1 35
+1 37
+1 39
+2 1
+2 3
+2 5
+2 7
+2 9
+2 11
+2 13
+2 15
+2 17
+2 19
+2 21
+2 23
+2 25
+2 27
+2 29
+2 31
+2 33
+2 35
+2 37
+2 39
+3 0
+3 2
+3 4
+3 6
+3 8
+3 10
+3 12
+3 14
+3 16
+3 18
+3 20
+3 22
+3 24
+3 26
+3 28
+3 30
+3 32
+3 34
+3 36
+3 38
+4 0
+4 2
+4 4
+4 6
+4 8
+4 10
+4 12
+4 14
+4 16
+4 18
+4 20
+4 22
+4 24
+4 26
+4 28
+4 30
+4 32
+4 34
+4 36
+4 38
+5 0
+5 2
+5 4
+5 6
+5 8
+5 10
+5 12
+5 14
+5 16
+5 18
+5 20
+5 22
+5 24
+5 26
+5 28
+5 30
+5 32
+5 34
+5 36
+5 38
+6 0
+6 2
+6 4
+6 6
+6 8
+6 10
+6 12
+6 14
+6 16
+6 18
+6 20
+6 22
+6 24
+6 26
+6 28
+6 30
+6 32
+6 34
+6 36
+6 38
+7 0
+7 1
+7 2
+7 3
+7 4
+7 5
+7 6
+7 7
+7 8
+7 9
+7 10
+7 11
+7 12
+7 13
+7 14
+7 15
+7 16
+7 17
+7 18
+7 19
+7 20
+7 21
+7 22
+7 23
+7 24
+7 25
+7 26
+7 27
+7 28
+7 29
+7 30
+7 31
+7 32
+7 33
+7 34
+7 35
+7 36
+7 37
+7 38
+7 39
+8 0
+8 1
+8 2
+8 3
+8 4
+8 5
+8 6
+8 7
+8 8
+8 9
+8 10
+8 11
+8 12
+8 13
+8 14
+8 15
+8 16
+8 17
+8 18
+8 19
+8 20
+8 21
+8 22
+8 23
+8 24
+8 25
+8 26
+8 27
+8 28
+8 29
+8 30
+8 31
+8 32
+8 33
+8 34
+8 35
+8 36
+8 37
+8 38
+8 39
+9 0
+9 1
+9 2
+9 3
+9 4
+9 5
+9 6
+9 7
+9 8
+9 9
+9 10
+9 11
+9 12
+9 13
+9 14
+9 15
+9 16
+9 17
+9 18
+9 19
+9 20
+9 21
+9 22
+9 23
+9 24
+9 25
+9 26
+9 27
+9 28
+9 29
+9 30
+9 31
+9 32
+9 33
+9 34
+9 35
+9 36
+9 37
+9 38
+9 39
+10 0
+10 1
+10 2
+10 3
+10 4
+10 5
+10 6
+10 7
+10 8
+10 9
+10 10
+10 11
+10 12
+10 13
+10 14
+10 15
+10 16
+10 17
+10 18
+10 19
+10 20
+10 21
+10 22
+10 23
+10 24
+10 25
+10 26
+10 27
+10 28
+10 29
+10 30
+10 31
+10 32
+10 33
+10 34
+10 35
+10 36
+10 37
+10 38
+10 39
+11 1
+11 3
+11 5
+11 7
+11 9
+11 11
+11 13
+11 15
+11 17
+11 19
+11 21
+11 23
+11 25
+11 27
+11 29
+11 31
+11 33
+11 35
+11 37
+11 39
+12 0
+12 1
+12 2
+12 3
+12 4
+12 5
+12 6
+12 7
+12 8
+12 9
+12 10
+12 11
+12 12
+12 13
+12 14
+12 15
+12 16
+12 17
+12 18
+12 19
+12 20
+12 21
+12 22
+12 23
+12 24
+12 25
+12 26
+12 27
+12 28
+12 29
+12 30
+12 31
+12 32
+12 33
+12 34
+12 35
+12 36
+12 37
+12 38
+12 39
+13 0
+13 1
+13 2
+13 3
+13 4
+13 5
+13 6
+13 7
+13 8
+13 9
+13 10
+13 11
+13 12
+13 13
+13 14
+13 15
+13 16
+13 17
+13 18
+13 19
+13 20
+13 21
+13 22
+13 23
+13 24
+13 25
+13 26
+13 27
+13 28
+13 29
+13 30
+13 31
+13 32
+13 33
+13 34
+13 35
+13 36
+13 37
+13 38
+13 39
+14 0
+14 1
+14 2
+14 3
+14 4
+14 5
+14 6
+14 7
+14 8
+14 9
+14 10
+14 11
+14 12
+14 13
+14 14
+14 15
+14 16
+14 17
+14 18
+14 19
+14 20
+14 21
+14 22
+14 23
+14 24
+14 25
+14 26
+14 27
+14 28
+14 29
+14 30
+14 31
+14 32
+14 33
+14 34
+14 35
+14 36
+14 37
+14 38
+14 39
+15 0
+15 1
+15 2
+15 3
+15 4
+15 5
+15 6
+15 7
+15 8
+15 9
+15 10
+15 11
+15 12
+15 13
+15 14
+15 15
+15 16
+15 17
+15 18
+15 19
+15 20
+15 21
+15 22
+15 23
+15 24
+15 25
+15 26
+15 27
+15 28
+15 29
+15 30
+15 31
+15 32
+15 33
+15 34
+15 35
+15 36
+15 37
+15 38
+15 39
+16 0
+16 2
+16 4
+16 6
+16 8
+16 10
+16 12
+16 14
+16 16
+16 18
+16 20
+16 22
+16 24
+16 26
+16 28
+16 30
+16 32
+16 34
+16 36
+16 38
+17 0
+17 2
+17 4
+17 6
+17 8
+17 10
+17 12
+17 14
+17 16
+17 18
+17 20
+17 22
+17 24
+17 26
+17 28
+17 30
+17 32
+17 34
+17 36
+17 38
+18 0
+18 2
+18 4
+18 6
+18 8
+18 10
+18 12
+18 14
+18 16
+18 18
+18 20
+18 22
+18 24
+18 26
+18 28
+18 30
+18 32
+18 34
+18 36
+18 38
+19 0
+19 2
+19 4
+19 6
+19 8
+19 10
+19 12
+19 14
+19 16
+19 18
+19 20
+19 22
+19 24
+19 26
+19 28
+19 30
+19 32
+19 34
+19 36
+19 38
+20 1
+20 3
+20 5
+20 7
+20 9
+20 11
+20 13
+20 15
+20 17
+20 19
+20 21
+20 23
+20 25
+20 27
+20 29
+20 31
+20 33
+20 35
+20 37
+20 39
+21 1
+21 3
+21 5
+21 7
+21 9
+21 11
+21 13
+21 15
+21 17
+21 19
+21 21
+21 23
+21 25
+21 27
+21 29
+21 31
+21 33
+21 35
+21 37
+21 39
+22 1
+22 3
+22 5
+22 7
+22 9
+22 11
+22 13
+22 15
+22 17
+22 19
+22 21
+22 23
+22 25
+22 27
+22 29
+22 31
+22 33
+22 35
+22 37
+22 39
diff --git a/warp/smap.2 b/warp/smap.2
new file mode 100644
index 00000000..5b570902
--- /dev/null
+++ b/warp/smap.2
@@ -0,0 +1,343 @@
+342
+0 0
+0 1
+0 2
+0 3
+0 4
+0 5
+0 6
+0 7
+0 8
+0 9
+0 10
+0 11
+0 12
+0 13
+0 14
+0 15
+0 16
+0 17
+0 18
+0 19
+0 20
+0 21
+0 22
+0 23
+0 24
+0 25
+0 26
+0 27
+0 28
+0 29
+0 30
+0 31
+0 32
+0 33
+0 34
+0 35
+0 36
+0 37
+0 38
+0 39
+1 0
+1 2
+1 3
+1 4
+1 5
+1 7
+2 0
+2 1
+2 2
+2 3
+2 4
+2 5
+2 6
+2 7
+2 8
+2 9
+2 10
+2 11
+2 12
+2 13
+2 14
+2 15
+2 16
+2 17
+2 18
+2 19
+2 20
+2 21
+2 22
+2 23
+2 24
+2 25
+2 26
+2 27
+2 28
+2 29
+2 30
+2 31
+2 32
+2 33
+2 34
+2 35
+2 36
+2 37
+2 38
+2 39
+3 0
+3 1
+3 2
+3 3
+3 4
+3 5
+3 6
+3 7
+3 8
+3 9
+3 10
+3 11
+3 12
+3 13
+3 14
+3 15
+3 16
+3 17
+3 18
+3 19
+3 20
+3 21
+3 22
+3 23
+3 24
+3 25
+3 26
+3 27
+3 28
+3 29
+3 30
+3 31
+3 32
+3 33
+3 34
+3 35
+3 36
+3 37
+3 38
+3 39
+4 0
+4 1
+4 2
+4 3
+4 4
+4 5
+4 6
+4 7
+4 8
+4 9
+4 10
+4 11
+4 12
+4 13
+4 14
+4 15
+4 16
+4 17
+4 18
+4 19
+4 20
+4 21
+4 22
+4 23
+4 24
+4 25
+4 26
+4 27
+4 28
+4 29
+4 30
+4 31
+4 32
+4 33
+4 34
+4 35
+4 36
+4 37
+4 38
+4 39
+5 0
+5 1
+5 2
+5 3
+5 4
+5 5
+5 6
+5 7
+5 8
+5 9
+5 10
+5 11
+5 12
+5 13
+5 14
+5 15
+5 16
+5 17
+5 18
+5 19
+5 20
+5 21
+5 22
+5 23
+5 24
+5 25
+5 26
+5 27
+5 28
+5 29
+5 30
+5 31
+5 32
+5 33
+5 34
+5 35
+5 36
+5 37
+5 38
+5 39
+6 0
+6 2
+6 3
+6 4
+6 5
+6 7
+7 0
+7 1
+7 2
+7 3
+7 4
+7 5
+7 6
+7 7
+7 8
+7 9
+7 10
+7 11
+7 12
+7 13
+7 14
+7 15
+7 16
+7 17
+7 18
+7 19
+7 20
+7 21
+7 22
+7 23
+7 24
+7 25
+7 26
+7 27
+7 28
+7 29
+7 30
+7 31
+7 32
+7 33
+7 34
+7 35
+7 36
+7 37
+7 38
+7 39
+8 0
+8 2
+8 3
+8 4
+8 5
+8 7
+9 0
+9 2
+9 3
+9 4
+9 5
+9 7
+10 0
+10 2
+10 3
+10 4
+10 5
+10 7
+11 0
+11 2
+11 3
+11 4
+11 5
+11 7
+12 0
+12 2
+12 3
+12 4
+12 5
+12 7
+13 0
+13 2
+13 3
+13 4
+13 5
+13 7
+14 0
+14 2
+14 3
+14 4
+14 5
+14 7
+15 0
+15 2
+15 3
+15 4
+15 5
+15 7
+16 0
+16 2
+16 3
+16 4
+16 5
+16 7
+17 0
+17 2
+17 3
+17 4
+17 5
+17 7
+18 0
+18 2
+18 3
+18 4
+18 5
+18 7
+19 0
+19 2
+19 3
+19 4
+19 5
+19 7
+20 0
+20 2
+20 3
+20 4
+20 5
+20 7
+21 0
+21 2
+21 3
+21 4
+21 5
+21 7
+22 0
+22 2
+22 3
+22 4
+22 5
+22 7
diff --git a/warp/smap.3 b/warp/smap.3
new file mode 100644
index 00000000..35cd03a0
--- /dev/null
+++ b/warp/smap.3
@@ -0,0 +1,85 @@
+84
+0 4
+0 5
+0 6
+0 7
+1 2
+1 3
+1 4
+1 7
+1 8
+1 9
+2 1
+2 2
+2 3
+2 5
+2 6
+2 8
+2 9
+2 10
+3 1
+3 2
+3 4
+3 5
+3 6
+3 7
+3 9
+3 10
+4 0
+4 1
+4 3
+4 4
+4 7
+4 8
+4 10
+4 11
+5 0
+5 2
+5 3
+5 5
+5 6
+5 8
+5 9
+5 11
+6 0
+6 2
+6 3
+6 5
+6 6
+6 8
+6 9
+6 11
+7 0
+7 1
+7 3
+7 4
+7 7
+7 8
+7 10
+7 11
+8 1
+8 2
+8 4
+8 5
+8 6
+8 7
+8 9
+8 10
+9 1
+9 2
+9 3
+9 5
+9 6
+9 8
+9 9
+9 10
+10 2
+10 3
+10 4
+10 7
+10 8
+10 9
+11 4
+11 5
+11 6
+11 7
diff --git a/warp/smap.4 b/warp/smap.4
new file mode 100644
index 00000000..1b3684b5
--- /dev/null
+++ b/warp/smap.4
@@ -0,0 +1,577 @@
+576
+0 0
+0 1
+0 2
+0 3
+0 5
+0 6
+0 7
+0 8
+0 10
+0 11
+0 12
+0 13
+0 15
+0 16
+0 17
+0 18
+0 20
+0 21
+0 22
+0 23
+0 25
+0 26
+0 27
+0 28
+0 30
+0 31
+0 32
+0 33
+0 35
+0 36
+0 37
+0 38
+1 0
+1 1
+1 2
+1 3
+1 5
+1 6
+1 7
+1 8
+1 10
+1 11
+1 12
+1 13
+1 15
+1 16
+1 17
+1 18
+1 20
+1 21
+1 22
+1 23
+1 25
+1 26
+1 27
+1 28
+1 30
+1 31
+1 32
+1 33
+1 35
+1 36
+1 37
+1 38
+2 0
+2 1
+2 2
+2 3
+2 5
+2 6
+2 7
+2 8
+2 10
+2 11
+2 12
+2 13
+2 15
+2 16
+2 17
+2 18
+2 20
+2 21
+2 22
+2 23
+2 25
+2 26
+2 27
+2 28
+2 30
+2 31
+2 32
+2 33
+2 35
+2 36
+2 37
+2 38
+3 0
+3 1
+3 2
+3 3
+3 5
+3 6
+3 7
+3 8
+3 10
+3 11
+3 12
+3 13
+3 15
+3 16
+3 17
+3 18
+3 20
+3 21
+3 22
+3 23
+3 25
+3 26
+3 27
+3 28
+3 30
+3 31
+3 32
+3 33
+3 35
+3 36
+3 37
+3 38
+5 0
+5 1
+5 2
+5 3
+5 5
+5 6
+5 7
+5 8
+5 10
+5 11
+5 12
+5 13
+5 15
+5 16
+5 17
+5 18
+5 20
+5 21
+5 22
+5 23
+5 25
+5 26
+5 27
+5 28
+5 30
+5 31
+5 32
+5 33
+5 35
+5 36
+5 37
+5 38
+6 0
+6 1
+6 2
+6 3
+6 5
+6 6
+6 7
+6 8
+6 10
+6 11
+6 12
+6 13
+6 15
+6 16
+6 17
+6 18
+6 20
+6 21
+6 22
+6 23
+6 25
+6 26
+6 27
+6 28
+6 30
+6 31
+6 32
+6 33
+6 35
+6 36
+6 37
+6 38
+7 0
+7 1
+7 2
+7 3
+7 5
+7 6
+7 7
+7 8
+7 10
+7 11
+7 12
+7 13
+7 15
+7 16
+7 17
+7 18
+7 20
+7 21
+7 22
+7 23
+7 25
+7 26
+7 27
+7 28
+7 30
+7 31
+7 32
+7 33
+7 35
+7 36
+7 37
+7 38
+8 0
+8 1
+8 2
+8 3
+8 5
+8 6
+8 7
+8 8
+8 10
+8 11
+8 12
+8 13
+8 15
+8 16
+8 17
+8 18
+8 20
+8 21
+8 22
+8 23
+8 25
+8 26
+8 27
+8 28
+8 30
+8 31
+8 32
+8 33
+8 35
+8 36
+8 37
+8 38
+10 0
+10 1
+10 2
+10 3
+10 5
+10 6
+10 7
+10 8
+10 10
+10 11
+10 12
+10 13
+10 15
+10 16
+10 17
+10 18
+10 20
+10 21
+10 22
+10 23
+10 25
+10 26
+10 27
+10 28
+10 30
+10 31
+10 32
+10 33
+10 35
+10 36
+10 37
+10 38
+11 0
+11 1
+11 2
+11 3
+11 5
+11 6
+11 7
+11 8
+11 10
+11 11
+11 12
+11 13
+11 15
+11 16
+11 17
+11 18
+11 20
+11 21
+11 22
+11 23
+11 25
+11 26
+11 27
+11 28
+11 30
+11 31
+11 32
+11 33
+11 35
+11 36
+11 37
+11 38
+12 0
+12 1
+12 2
+12 3
+12 5
+12 6
+12 7
+12 8
+12 10
+12 11
+12 12
+12 13
+12 15
+12 16
+12 17
+12 18
+12 20
+12 21
+12 22
+12 23
+12 25
+12 26
+12 27
+12 28
+12 30
+12 31
+12 32
+12 33
+12 35
+12 36
+12 37
+12 38
+14 0
+14 1
+14 2
+14 3
+14 5
+14 6
+14 7
+14 8
+14 10
+14 11
+14 12
+14 13
+14 15
+14 16
+14 17
+14 18
+14 20
+14 21
+14 22
+14 23
+14 25
+14 26
+14 27
+14 28
+14 30
+14 31
+14 32
+14 33
+14 35
+14 36
+14 37
+14 38
+15 0
+15 1
+15 2
+15 3
+15 5
+15 6
+15 7
+15 8
+15 10
+15 11
+15 12
+15 13
+15 15
+15 16
+15 17
+15 18
+15 20
+15 21
+15 22
+15 23
+15 25
+15 26
+15 27
+15 28
+15 30
+15 31
+15 32
+15 33
+15 35
+15 36
+15 37
+15 38
+16 0
+16 1
+16 2
+16 3
+16 5
+16 6
+16 7
+16 8
+16 10
+16 11
+16 12
+16 13
+16 15
+16 16
+16 17
+16 18
+16 20
+16 21
+16 22
+16 23
+16 25
+16 26
+16 27
+16 28
+16 30
+16 31
+16 32
+16 33
+16 35
+16 36
+16 37
+16 38
+17 0
+17 1
+17 2
+17 3
+17 5
+17 6
+17 7
+17 8
+17 10
+17 11
+17 12
+17 13
+17 15
+17 16
+17 17
+17 18
+17 20
+17 21
+17 22
+17 23
+17 25
+17 26
+17 27
+17 28
+17 30
+17 31
+17 32
+17 33
+17 35
+17 36
+17 37
+17 38
+19 0
+19 1
+19 2
+19 3
+19 5
+19 6
+19 7
+19 8
+19 10
+19 11
+19 12
+19 13
+19 15
+19 16
+19 17
+19 18
+19 20
+19 21
+19 22
+19 23
+19 25
+19 26
+19 27
+19 28
+19 30
+19 31
+19 32
+19 33
+19 35
+19 36
+19 37
+19 38
+20 0
+20 1
+20 2
+20 3
+20 5
+20 6
+20 7
+20 8
+20 10
+20 11
+20 12
+20 13
+20 15
+20 16
+20 17
+20 18
+20 20
+20 21
+20 22
+20 23
+20 25
+20 26
+20 27
+20 28
+20 30
+20 31
+20 32
+20 33
+20 35
+20 36
+20 37
+20 38
+21 0
+21 1
+21 2
+21 3
+21 5
+21 6
+21 7
+21 8
+21 10
+21 11
+21 12
+21 13
+21 15
+21 16
+21 17
+21 18
+21 20
+21 21
+21 22
+21 23
+21 25
+21 26
+21 27
+21 28
+21 30
+21 31
+21 32
+21 33
+21 35
+21 36
+21 37
+21 38
diff --git a/warp/smap.5 b/warp/smap.5
new file mode 100644
index 00000000..6cbbfc83
--- /dev/null
+++ b/warp/smap.5
@@ -0,0 +1,17 @@
+16
+0 0
+0 1
+0 2
+1 0
+1 2
+2 0
+2 1
+2 2
+11 20
+11 21
+11 22
+12 20
+12 22
+13 20
+13 21
+13 22
diff --git a/warp/smap.6 b/warp/smap.6
new file mode 100644
index 00000000..73218bfd
--- /dev/null
+++ b/warp/smap.6
@@ -0,0 +1,744 @@
+743
+0 3
+0 4
+0 5
+0 6
+0 7
+0 8
+0 9
+0 10
+0 11
+0 12
+0 13
+0 14
+0 15
+0 16
+0 17
+0 18
+0 19
+0 20
+0 21
+0 22
+0 23
+0 24
+0 25
+0 26
+0 27
+0 28
+0 29
+0 30
+0 31
+0 32
+0 33
+0 34
+0 35
+0 36
+1 7
+1 8
+1 9
+1 10
+1 11
+1 12
+1 13
+1 14
+1 15
+1 16
+1 17
+1 18
+1 19
+1 20
+1 21
+1 22
+1 23
+1 24
+1 25
+1 26
+1 27
+1 28
+1 29
+1 30
+1 31
+1 32
+1 33
+1 34
+1 35
+1 36
+1 37
+1 38
+1 39
+2 0
+2 1
+2 2
+2 10
+2 11
+2 12
+2 13
+2 14
+2 15
+2 16
+2 17
+2 18
+2 19
+2 20
+2 21
+2 22
+2 23
+2 24
+2 25
+2 26
+2 27
+2 28
+2 29
+2 30
+2 31
+2 32
+2 33
+2 34
+2 35
+2 36
+2 37
+2 38
+2 39
+3 0
+3 1
+3 2
+3 3
+3 4
+3 5
+3 12
+3 13
+3 14
+3 15
+3 16
+3 17
+3 18
+3 19
+3 20
+3 21
+3 22
+3 28
+3 29
+3 30
+3 31
+3 32
+3 33
+3 34
+3 35
+3 36
+3 37
+3 38
+3 39
+4 0
+4 1
+4 2
+4 3
+4 4
+4 5
+4 6
+4 7
+4 8
+4 13
+4 14
+4 15
+4 16
+4 17
+4 18
+4 19
+4 20
+4 30
+4 31
+4 32
+4 33
+4 34
+4 35
+4 36
+4 37
+4 38
+4 39
+5 0
+5 1
+5 2
+5 3
+5 4
+5 5
+5 6
+5 7
+5 8
+5 9
+5 13
+5 14
+5 15
+5 16
+5 17
+5 18
+5 19
+5 24
+5 25
+5 26
+5 30
+5 31
+5 32
+5 33
+5 34
+5 35
+5 36
+5 37
+5 38
+5 39
+6 0
+6 1
+6 2
+6 3
+6 4
+6 5
+6 6
+6 7
+6 8
+6 9
+6 13
+6 14
+6 15
+6 16
+6 17
+6 18
+6 22
+6 23
+6 24
+6 25
+6 26
+6 27
+6 28
+6 31
+6 32
+6 33
+6 34
+6 35
+6 36
+6 37
+6 38
+6 39
+7 0
+7 1
+7 2
+7 3
+7 4
+7 5
+7 6
+7 7
+7 8
+7 13
+7 14
+7 15
+7 16
+7 17
+7 18
+7 21
+7 22
+7 23
+7 24
+7 25
+7 26
+7 27
+7 28
+7 32
+7 33
+7 34
+7 35
+7 36
+7 37
+7 38
+7 39
+8 0
+8 1
+8 2
+8 3
+8 4
+8 5
+8 6
+8 7
+8 8
+8 12
+8 13
+8 14
+8 15
+8 16
+8 17
+8 18
+8 20
+8 21
+8 22
+8 23
+8 24
+8 25
+8 26
+8 27
+8 28
+8 32
+8 33
+8 34
+8 35
+8 36
+8 37
+8 38
+8 39
+9 0
+9 1
+9 2
+9 3
+9 4
+9 5
+9 6
+9 7
+9 11
+9 12
+9 13
+9 14
+9 15
+9 16
+9 17
+9 18
+9 20
+9 21
+9 22
+9 23
+9 24
+9 25
+9 26
+9 27
+9 28
+9 29
+9 34
+9 35
+9 36
+9 37
+9 38
+9 39
+10 0
+10 1
+10 2
+10 3
+10 4
+10 5
+10 10
+10 11
+10 12
+10 13
+10 14
+10 15
+10 16
+10 17
+10 18
+10 20
+10 21
+10 22
+10 23
+10 24
+10 25
+10 26
+10 27
+10 28
+10 29
+10 30
+10 34
+10 35
+10 36
+10 37
+10 38
+10 39
+11 0
+11 1
+11 2
+11 3
+11 4
+11 8
+11 9
+11 10
+11 11
+11 12
+11 13
+11 14
+11 15
+11 16
+11 17
+11 18
+11 20
+11 21
+11 22
+11 23
+11 24
+11 25
+11 26
+11 27
+11 28
+11 29
+11 30
+11 31
+11 34
+11 35
+11 36
+11 37
+11 38
+11 39
+12 0
+12 1
+12 2
+12 3
+12 4
+12 7
+12 8
+12 9
+12 10
+12 11
+12 12
+12 13
+12 14
+12 18
+12 20
+12 21
+12 22
+12 23
+12 24
+12 25
+12 26
+12 27
+12 28
+12 29
+12 30
+12 31
+12 34
+12 35
+12 36
+12 37
+12 38
+12 39
+13 0
+13 1
+13 2
+13 3
+13 4
+13 7
+13 8
+13 9
+13 10
+13 11
+13 12
+13 13
+13 18
+13 20
+13 21
+13 22
+13 23
+13 24
+13 25
+13 26
+13 27
+13 28
+13 29
+13 30
+13 34
+13 35
+13 36
+13 37
+13 38
+13 39
+14 0
+14 1
+14 2
+14 3
+14 4
+14 7
+14 8
+14 9
+14 10
+14 11
+14 12
+14 18
+14 20
+14 21
+14 22
+14 23
+14 24
+14 25
+14 26
+14 27
+14 28
+14 29
+14 33
+14 34
+14 35
+14 36
+14 37
+14 38
+14 39
+15 0
+15 1
+15 2
+15 3
+15 4
+15 5
+15 8
+15 9
+15 10
+15 11
+15 14
+15 15
+15 16
+15 20
+15 21
+15 22
+15 23
+15 24
+15 25
+15 26
+15 27
+15 28
+15 29
+15 32
+15 33
+15 34
+15 35
+15 36
+15 37
+15 38
+15 39
+16 0
+16 1
+16 2
+16 3
+16 4
+16 5
+16 6
+16 13
+16 14
+16 15
+16 16
+16 20
+16 21
+16 22
+16 23
+16 24
+16 25
+16 26
+16 27
+16 28
+16 33
+16 34
+16 35
+16 36
+16 37
+16 38
+16 39
+17 0
+17 1
+17 2
+17 3
+17 4
+17 5
+17 6
+17 7
+17 8
+17 9
+17 10
+17 11
+17 12
+17 13
+17 14
+17 15
+17 16
+17 17
+17 18
+17 19
+17 20
+17 21
+17 22
+17 23
+17 24
+17 25
+17 26
+17 27
+17 31
+17 32
+17 33
+17 34
+17 35
+17 36
+17 37
+17 38
+17 39
+18 0
+18 1
+18 2
+18 3
+18 4
+18 5
+18 6
+18 7
+18 8
+18 9
+18 10
+18 11
+18 12
+18 13
+18 14
+18 15
+18 16
+18 17
+18 18
+18 19
+18 20
+18 21
+18 22
+18 23
+18 24
+18 25
+18 26
+18 27
+18 31
+18 32
+18 33
+18 34
+18 35
+18 36
+18 37
+18 38
+18 39
+19 0
+19 1
+19 2
+19 3
+19 4
+19 5
+19 6
+19 7
+19 8
+19 9
+19 10
+19 11
+19 12
+19 13
+19 14
+19 15
+19 16
+19 17
+19 18
+19 19
+19 20
+19 21
+19 22
+19 23
+19 24
+19 25
+19 26
+19 27
+19 31
+19 32
+19 33
+19 34
+19 35
+19 36
+19 37
+19 38
+19 39
+20 0
+20 1
+20 2
+20 3
+20 4
+20 5
+20 6
+20 7
+20 8
+20 9
+20 10
+20 11
+20 12
+20 13
+20 14
+20 15
+20 16
+20 17
+20 18
+20 19
+20 20
+20 21
+20 22
+20 23
+20 24
+20 25
+20 26
+20 27
+20 33
+20 34
+20 35
+20 36
+20 37
+20 38
+20 39
+21 0
+21 1
+21 2
+21 3
+21 4
+21 5
+21 6
+21 7
+21 8
+21 9
+21 10
+21 11
+21 12
+21 13
+21 14
+21 15
+21 16
+21 17
+21 18
+21 19
+21 20
+21 21
+21 22
+21 23
+21 24
+21 25
+21 26
+21 27
+21 28
+21 38
+21 39
+22 0
+22 1
+22 2
+22 3
+22 4
+22 5
+22 6
+22 7
+22 8
+22 9
+22 10
+22 11
+22 12
+22 13
+22 14
+22 15
+22 16
+22 17
+22 18
+22 19
+22 20
+22 21
+22 22
+22 23
+22 24
+22 25
+22 26
+22 27
+22 28
+22 29
+22 30
+22 31
+22 32
+22 33
+22 34
+22 35
+22 36
diff --git a/warp/smap.7 b/warp/smap.7
new file mode 100644
index 00000000..c72d1bab
--- /dev/null
+++ b/warp/smap.7
@@ -0,0 +1,178 @@
+177
+0 0
+0 1
+0 2
+0 37
+0 38
+0 39
+1 0
+1 1
+1 2
+1 3
+1 4
+1 5
+1 6
+2 3
+2 4
+2 5
+2 6
+2 7
+2 8
+2 9
+3 6
+3 7
+3 8
+3 9
+3 10
+3 11
+3 23
+3 24
+3 25
+3 26
+3 27
+4 9
+4 10
+4 11
+4 12
+4 21
+4 22
+4 23
+4 24
+4 25
+4 26
+4 27
+4 28
+4 29
+5 10
+5 11
+5 12
+5 20
+5 21
+5 22
+5 23
+5 27
+5 28
+5 29
+6 10
+6 11
+6 12
+6 19
+6 20
+6 21
+6 29
+6 30
+7 9
+7 10
+7 11
+7 12
+7 19
+7 20
+7 29
+7 30
+7 31
+8 9
+8 10
+8 11
+8 19
+8 29
+8 30
+8 31
+9 8
+9 9
+9 10
+9 19
+9 30
+9 31
+9 32
+9 33
+10 6
+10 7
+10 8
+10 9
+10 19
+10 31
+10 32
+10 33
+11 5
+11 6
+11 7
+11 19
+11 32
+11 33
+12 5
+12 6
+12 15
+12 16
+12 17
+12 19
+12 32
+12 33
+13 5
+13 6
+13 14
+13 15
+13 16
+13 17
+13 19
+13 31
+13 32
+13 33
+14 5
+14 6
+14 13
+14 14
+14 15
+14 16
+14 17
+14 19
+14 30
+14 31
+14 32
+15 6
+15 7
+15 12
+15 13
+15 17
+15 18
+15 19
+15 30
+15 31
+16 7
+16 8
+16 9
+16 10
+16 11
+16 12
+16 17
+16 18
+16 19
+16 29
+16 30
+16 31
+16 32
+17 28
+17 29
+17 30
+18 28
+18 29
+18 30
+19 28
+19 29
+19 30
+20 28
+20 29
+20 30
+20 31
+20 32
+21 29
+21 30
+21 31
+21 32
+21 33
+21 34
+21 35
+21 36
+21 37
+22 37
+22 38
+22 39
diff --git a/warp/smp.0 b/warp/smp.0
new file mode 100644
index 00000000..13e075fc
--- /dev/null
+++ b/warp/smp.0
@@ -0,0 +1,23 @@
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
diff --git a/warp/smp.1 b/warp/smp.1
new file mode 100644
index 00000000..ac822ad2
--- /dev/null
+++ b/warp/smp.1
@@ -0,0 +1,23 @@
+ * * * * * * * * * * * * * * * * * * * *
+ * * * * * * * * * * * * * * * * * * * *
+ * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+ * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * *
+ * * * * * * * * * * * * * * * * * * * *
+ * * * * * * * * * * * * * * * * * * * *
+ * * * * * * * * * * * * * * * * * * * *
diff --git a/warp/smp.2 b/warp/smp.2
new file mode 100644
index 00000000..4ad56ac0
--- /dev/null
+++ b/warp/smp.2
@@ -0,0 +1,23 @@
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
+* * * * * *
diff --git a/warp/smp.3 b/warp/smp.3
new file mode 100644
index 00000000..58feef94
--- /dev/null
+++ b/warp/smp.3
@@ -0,0 +1,23 @@
+ * * * *
+ * * * * * *
+ * * * * * * * *
+ * * * * * * * *
+* * * * * * * *
+* * * * * * * *
+* * * * * * * *
+* * * * * * * *
+ * * * * * * * *
+ * * * * * * * *
+ * * * * * *
+ * * * *
+
+
+
+
+
+
+
+
+
+
+
diff --git a/warp/smp.4 b/warp/smp.4
new file mode 100644
index 00000000..21f3ca9b
--- /dev/null
+++ b/warp/smp.4
@@ -0,0 +1,23 @@
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+
diff --git a/warp/smp.5 b/warp/smp.5
new file mode 100644
index 00000000..7d8948f4
--- /dev/null
+++ b/warp/smp.5
@@ -0,0 +1,23 @@
+* * *
+* *
+* * *
+
+
+
+
+
+
+
+
+ * * *
+ * *
+ * * *
+
+
+
+
+
+
+
+
+
diff --git a/warp/smp.6 b/warp/smp.6
new file mode 100644
index 00000000..268c051c
--- /dev/null
+++ b/warp/smp.6
@@ -0,0 +1,23 @@
+ * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+ * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
diff --git a/warp/smp.7 b/warp/smp.7
new file mode 100644
index 00000000..8c67dea4
--- /dev/null
+++ b/warp/smp.7
@@ -0,0 +1,23 @@
+* * * * * *
+* * * * * * *
+ * * * * * * *
+ * * * * * * * * * * *
+ * * * * * * * * * * * * *
+ * * * * * * * * * *
+ * * * * * * * *
+ * * * * * * * * *
+ * * * * * * *
+ * * * * * * * *
+ * * * * * * * *
+ * * * * * *
+ * * * * * * * *
+ * * * * * * * * * *
+ * * * * * * * * * * *
+ * * * * * * * * *
+ * * * * * * * * * * * * *
+ * * *
+ * * *
+ * * *
+ * * * * *
+ * * * * * * * * *
+ * * *
diff --git a/warp/term.c b/warp/term.c
new file mode 100644
index 00000000..a90a434a
--- /dev/null
+++ b/warp/term.c
@@ -0,0 +1,832 @@
+/* $Header: /cvsroot/src/games/warp/term.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: term.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.2 86/12/12 17:04:09 lwall
+ * Baseline for net release.
+ *
+ * Revision 7.0.1.1 86/10/16 10:53:20 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:14:02 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "bang.h"
+#include "intrp.h"
+#include "object.h"
+#include "play.h"
+#include "score.h"
+#include "sig.h"
+#include "us.h"
+#include "util.h"
+#include "weapon.h"
+#include "INTERN.h"
+#include "term.h"
+
+int typeahead = FALSE;
+
+char tcarea[TCSIZE]; /* area for "compiled" termcap strings */
+
+/* guarantee capability pointer != Nullch */
+/* (I believe terminfo will ignore the &tmpaddr argument.) */
+
+#define Tgetstr(key) ((tstr = tgetstr(key,&tmpaddr)) ? tstr : nullstr)
+
+#ifdef PUSHBACK
+struct keymap {
+ char km_type[128];
+ union km_union {
+ struct keymap *km_km;
+ char *km_str;
+ } km_ptr[128];
+};
+
+#define KM_NOTHIN 0
+#define KM_STRING 1
+#define KM_KEYMAP 2
+#define KM_BOGUS 3
+
+#define KM_TMASK 3
+#define KM_GSHIFT 4
+#define KM_GMASK 7
+
+typedef struct keymap KEYMAP;
+
+KEYMAP *topmap INIT(Null(KEYMAP*));
+
+void mac_init();
+KEYMAP *newkeymap();
+void pushstring();
+#endif
+
+/* terminal initialization */
+
+void
+term_init()
+{
+ savetty(); /* remember current tty state */
+
+#ifdef TERMIO
+ ospeed = _tty.c_cflag & CBAUD; /* for tputs() */
+ ERASECH = _tty.c_cc[VERASE]; /* for finish_command() */
+ KILLCH = _tty.c_cc[VKILL]; /* for finish_command() */
+#else
+ ospeed = _tty.sg_ospeed; /* for tputs() */
+ ERASECH = _tty.sg_erase; /* for finish_command() */
+ KILLCH = _tty.sg_kill; /* for finish_command() */
+#endif
+
+ /* The following could be a table but I can't be sure that there isn't */
+ /* some degree of sparsity out there in the world. */
+
+ switch (ospeed) { /* 1 second of padding */
+#ifdef BEXTA
+ case BEXTA: just_a_sec = 1920; break;
+#else
+#ifdef B19200
+ case B19200: just_a_sec = 1920; break;
+#endif
+#endif
+ case B9600: just_a_sec = 960; break;
+ case B4800: just_a_sec = 480; break;
+ case B2400: just_a_sec = 240; break;
+ case B1800: just_a_sec = 180; break;
+ case B1200: just_a_sec = 120; break;
+ case B600: just_a_sec = 60; break;
+ case B300: just_a_sec = 30; break;
+ /* do I really have to type the rest of this??? */
+ case B200: just_a_sec = 20; break;
+ case B150: just_a_sec = 15; break;
+ case B134: just_a_sec = 13; break;
+ case B110: just_a_sec = 11; break;
+ case B75: just_a_sec = 8; break;
+ case B50: just_a_sec = 5; break;
+ default: just_a_sec = 960; break;
+ /* if we are running detached I */
+ } /* don't want to know about it! */
+}
+
+/* set terminal characteristics */
+
+void
+term_set(tcbuf)
+char *tcbuf; /* temp area for "uncompiled" termcap entry */
+{
+ char *tmpaddr; /* must not be register */
+ Reg1 char *tstr;
+ char *tgetstr();
+ char *s;
+ int retval;
+
+#ifdef PENDING
+#ifndef FIONREAD
+#ifndef RDCHK
+ /* do no delay reads on something that always gets closed on exit */
+
+ devtty = open("/dev/tty",0);
+ if (devtty < 0) {
+ printf(cantopen,"/dev/tty");
+ finalize(1);
+ }
+ fcntl(devtty,F_SETFL,O_NDELAY);
+#endif
+#endif
+#endif
+
+ /* get all that good termcap stuff */
+
+ retval = tgetent(tcbuf,getenv("TERM")); /* get termcap entry */
+ if (retval < 1) {
+#ifdef VERBOSE
+ printf("No termcap %s found.\n", retval ? "file" : "entry");
+#else
+ fputs("Termcap botch\n",stdout);
+#endif
+ finalize(1);
+ }
+ tmpaddr = tcarea; /* set up strange tgetstr pointer */
+ s = Tgetstr("pc"); /* get pad character */
+ PC = *s; /* get it where tputs wants it */
+ if (!tgetflag("bs")) { /* is backspace not used? */
+ BC = Tgetstr("bc"); /* find out what is */
+ if (BC == nullstr) /* terminfo grok's 'bs' but not 'bc' */
+ BC = Tgetstr("le");
+ } else
+ BC = "\b"; /* make a backspace handy */
+ UP = Tgetstr("up"); /* move up a line */
+ ND = Tgetstr("nd"); /* non-destructive move cursor right */
+ DO = Tgetstr("do"); /* move cursor down */
+ if (!*DO)
+ DO = Tgetstr("nl");
+ CL = Tgetstr("cl"); /* get clear string */
+ CE = Tgetstr("ce"); /* clear to end of line string */
+ CM = Tgetstr("cm"); /* cursor motion - PWP */
+ HO = Tgetstr("ho"); /* home cursor if no CM - PWP */
+ CD = Tgetstr("cd"); /* clear to end of display - PWP */
+ SO = Tgetstr("so"); /* begin standout */
+ SE = Tgetstr("se"); /* end standout */
+ if ((SG = tgetnum("sg"))<0)
+ SG = 0; /* blanks left by SG, SE */
+ US = Tgetstr("us"); /* start underline */
+ UE = Tgetstr("ue"); /* end underline */
+ if ((UG = tgetnum("ug"))<0)
+ UG = 0; /* blanks left by US, UE */
+ if (*US)
+ UC = nullstr; /* UC must not be NULL */
+ else
+ UC = Tgetstr("uc"); /* underline a character */
+ if (!*US && !*UC) { /* no underline mode? */
+ US = SO; /* substitute standout mode */
+ UE = SE;
+ UG = SG;
+ }
+ LINES = tgetnum("li"); /* lines per page */
+ COLS = tgetnum("co"); /* columns on page */
+ AM = tgetflag("am"); /* terminal wraps automatically? */
+ XN = tgetflag("xn"); /* then eats next newline? */
+ VB = Tgetstr("vb");
+ if (!*VB)
+ VB = "\007";
+ CR = Tgetstr("cr");
+ if (!*CR) {
+ if (tgetflag("nc") && *UP) {
+ CR = safemalloc((MEM_SIZE)strlen(UP)+2);
+ Sprintf(CR,"%s\r",UP);
+ }
+ else
+ CR = "\r";
+ }
+ if (LINES <= 0)
+ LINES = 24;
+ if (COLS <= 0)
+ COLS = 80;
+
+ BCsize = comp_tc(bsptr,BC,1);
+ BC = bsptr;
+
+ if (!*ND) /* not defined? */
+ NDsize = 1000; /* force cursor addressing */
+ else {
+ NDsize = comp_tc(cmbuffer,ND,1);
+ myND = malloc((unsigned)NDsize);
+ movc3(NDsize,cmbuffer,myND);
+ if (debugging) {
+ int scr;
+
+ printf("ND");
+ for (scr=0; scr<NDsize; scr++)
+ printf(" %d",myND[scr]);
+ printf("\n");
+ }
+ }
+
+ if (!*UP) /* not defined? */
+ UPsize = 1000; /* force cursor addressing */
+ else {
+ UPsize = comp_tc(cmbuffer,UP,1);
+ myUP = malloc((unsigned)UPsize);
+ movc3(UPsize,cmbuffer,myUP);
+ if (debugging) {
+ int scr;
+
+ printf("UP");
+ for (scr=0; scr<UPsize; scr++)
+ printf(" %d",myUP[scr]);
+ printf("\n");
+ }
+ }
+
+ if (!*DO) { /* not defined? */
+ myDO = DO = "\n"; /* assume a newline */
+ DOsize = 1;
+ }
+ else {
+ DOsize = comp_tc(cmbuffer,DO,1);
+ myDO = malloc((unsigned)DOsize);
+ movc3(DOsize,cmbuffer,myDO);
+ if (debugging) {
+ int scr;
+
+ printf("DO");
+ for (scr=0; scr<DOsize; scr++)
+ printf(" %d",myDO[scr]);
+ printf("\n");
+ }
+ }
+ if (debugging)
+ Fgets(cmbuffer,(sizeof cmbuffer),stdin);
+
+ CMsize = comp_tc(cmbuffer,tgoto(CM,20,20),0);
+ if (PC != '\0') {
+ char *p;
+
+ for (p=filler+(sizeof filler)-1;!*p;--p)
+ *p = PC;
+ }
+ charsperhalfsec = ospeed >= B9600 ? 480 :
+ ospeed == B4800 ? 240 :
+ ospeed == B2400 ? 120 :
+ ospeed == B1200 ? 60 :
+ ospeed == B600 ? 30 :
+ /* speed is 300 (?) */ 15;
+
+ gfillen = ospeed >= B9600 ? (sizeof filler) :
+ ospeed == B4800 ? 13 :
+ ospeed == B2400 ? 7 :
+ ospeed == B1200 ? 4 :
+ 1+BCsize;
+ if (ospeed < B2400)
+ lowspeed = TRUE;
+
+ strcpy(term,ttyname(2));
+
+ if (!*CM || !BCsize)
+ no_can_do("dumb");
+ if (!scorespec && (LINES < 24 || COLS < 80))
+ no_can_do("puny");
+
+ crmode();
+ raw();
+ noecho(); /* turn off echo */
+ nonl();
+
+#ifdef PUSHBACK
+ mac_init(tcbuf);
+#endif
+}
+
+#ifdef PUSHBACK
+void
+mac_init(tcbuf)
+char *tcbuf;
+{
+ char tmpbuf[1024];
+
+ tmpfp = fopen(filexp(getval("WARPMACRO",WARPMACRO)),"r");
+ if (tmpfp != Nullfp) {
+ while (fgets(tcbuf,1024,tmpfp) != Nullch) {
+ mac_line(tcbuf,tmpbuf,(sizeof tmpbuf));
+ }
+ Fclose(tmpfp);
+ }
+}
+
+void
+mac_line(line,tmpbuf,tbsize)
+char *line;
+char *tmpbuf;
+int tbsize;
+{
+ Reg1 char *s;
+ Reg2 char *m;
+ Reg3 KEYMAP *curmap;
+ Reg4 int ch;
+ Reg5 int garbage = 0;
+ static char override[] = "\r\nkeymap overrides string\r\n";
+
+ if (topmap == Null(KEYMAP*))
+ topmap = newkeymap();
+ if (*line == '#' || *line == '\n')
+ return;
+ if (line[ch = strlen(line)-1] == '\n')
+ line[ch] = '\0';
+ m = dointerp(tmpbuf,tbsize,line," \t");
+ if (!*m)
+ return;
+ while (*m == ' ' || *m == '\t') m++;
+ for (s=tmpbuf,curmap=topmap; *s; s++) {
+ ch = *s & 0177;
+ if (s[1] == '+' && isdigit(s[2])) {
+ s += 2;
+ garbage = (*s & KM_GMASK) << KM_GSHIFT;
+ }
+ else
+ garbage = 0;
+ if (s[1]) {
+ if ((curmap->km_type[ch] & KM_TMASK) == KM_STRING) {
+ puts(override);
+ free(curmap->km_ptr[ch].km_str);
+ curmap->km_ptr[ch].km_str = Nullch;
+ }
+ curmap->km_type[ch] = KM_KEYMAP + garbage;
+ if (curmap->km_ptr[ch].km_km == Null(KEYMAP*))
+ curmap->km_ptr[ch].km_km = newkeymap();
+ curmap = curmap->km_ptr[ch].km_km;
+ }
+ else {
+ if ((curmap->km_type[ch] & KM_TMASK) == KM_KEYMAP)
+ puts(override);
+ else {
+ curmap->km_type[ch] = KM_STRING + garbage;
+ curmap->km_ptr[ch].km_str = savestr(m);
+ }
+ }
+ }
+}
+
+KEYMAP*
+newkeymap()
+{
+ Reg1 int i;
+ Reg2 KEYMAP *map;
+
+#ifndef lint
+ map = (KEYMAP*)safemalloc(sizeof(KEYMAP));
+#else
+ map = Null(KEYMAP*);
+#endif /* lint */
+ for (i=127; i>=0; --i) {
+ map->km_ptr[i].km_km = Null(KEYMAP*);
+ map->km_type[i] = KM_NOTHIN;
+ }
+ return map;
+}
+
+#endif
+
+/* print out a file, stopping at form feeds */
+
+void
+page(filename,num)
+char *filename;
+bool num;
+{
+ int linenum = 1;
+
+ tmpfp = fopen(filename,"r");
+ if (tmpfp != NULL) {
+ while (fgets(spbuf,(sizeof spbuf),tmpfp) != NULL) {
+ if (*spbuf == '\f') {
+ printf("[Type anything to continue] ");
+ Fflush(stdout);
+ getcmd(spbuf);
+ printf("\r\n");
+ if (*spbuf == INTRCH)
+ finalize(0);
+ if (*spbuf == 'q' || *spbuf == 'Q')
+ break;
+ }
+ else {
+ if (num)
+ printf("%3d %s\r",linenum++,spbuf);
+ else
+ printf("%s\r",spbuf);
+ }
+ }
+ Fclose(tmpfp);
+ }
+}
+
+void
+move(y, x, chadd)
+int y, x;
+int chadd;
+{
+ Reg1 int ydist;
+ Reg2 int xdist;
+ Reg3 int i;
+ Reg4 char *s;
+
+ ydist = y - real_y;
+ xdist = x - real_x;
+ i = ydist * (ydist < 0 ? -UPsize : DOsize) +
+ xdist * (xdist < 0 ? -BCsize : NDsize);
+ beg_qwrite();
+ if (i <= CMsize) {
+ if (ydist < 0)
+ for (; ydist; ydist++)
+ for (i=UPsize,s=myUP; i; i--)
+ qaddch(*s++);
+ else
+ for (; ydist; ydist--)
+ for (i=DOsize,s=myDO; i; i--)
+ qaddch(*s++);
+ if (xdist < 0)
+ for (; xdist; xdist++)
+ for (i=BCsize,s=BC; i; i--)
+ qaddch(*s++);
+ else
+ for (; xdist; xdist--)
+ for (i=NDsize,s=myND; i; i--)
+ qaddch(*s++);
+ }
+ else {
+ tputs(tgoto(CM,x,y),0,cmstore);
+ }
+ real_y = y;
+ real_x = x;
+ if (chadd) {
+ qaddch(chadd);
+ }
+ if (maxcmstring != cmbuffer)
+ end_qwrite();
+}
+
+void
+do_tc(s,l)
+char *s;
+int l;
+{
+ beg_qwrite();
+ tputs(s,l,cmstore);
+ end_qwrite();
+}
+
+int
+comp_tc(dest,s,l)
+char *dest;
+char *s;
+int l;
+{
+ maxcmstring = dest;
+ tputs(s,l,cmstore);
+ return(maxcmstring-dest);
+}
+
+void
+helper()
+{
+ clear();
+ mvaddstr(0,4,"h or 4 left");
+ mvaddstr(1,4,"j or 2 down Use with SHIFT to fire torpedoes.");
+ mvaddstr(2,4,"k or 8 up Use with CTRL or FUNCT to fire");
+ mvaddstr(3,4,"l or 6 right phasers or turbolasers.");
+ mvaddstr(4,4,"b or 1 down and left Use preceded by 'a' or 'r' for");
+ mvaddstr(5,4,"n or 3 down and right attractors or repulsors.");
+ mvaddstr(6,4,"y or 7 up and left Use normally for E or B motion.");
+ mvaddstr(7,4,"u or 9 up and right");
+ mvaddstr(8,4,"");
+ mvaddstr(9,4,"del or % fire photon torpedoes in every (reasonable) direction.");
+ mvaddstr(10,4,"s stop all torpedoes.");
+ mvaddstr(11,4,"S or 0 stop the Enterprise when in warp mode.");
+ mvaddstr(12,4,"d/D destruct all torpedoes/current vessel.");
+ mvaddstr(13,4,"i/w switch to Enterprise & put into impulse/warp mode.");
+ mvaddstr(14,4,"c/v switch to Enterprise & make cloaked/visible.");
+ mvaddstr(15,4,"p switch to Base.");
+ mvaddstr(16,4,"o toggle to other vessel (from E to B, or vice versa.)");
+ mvaddstr(17,4,"z zap (suppress) blasts near Enterprise next cycle");
+ mvaddstr(18,4,"");
+ mvaddstr(19,4,"^R refresh the screen. ^Z suspend the game.");
+ mvaddstr(20,4,"q exit this round (if you haven't typed q within 10 cycles).");
+ mvaddstr(21,4,"Q exit this game.");
+ mvaddstr(22,4,"");
+ mvaddstr(23,4," [Hit space to continue]");
+ Fflush(stdout);
+ do {
+ getcmd(spbuf);
+ } while (*spbuf != ' ');
+ rewrite();
+
+}
+
+void
+rewrite()
+{
+ Reg1 int x;
+ Reg2 int y;
+ Reg3 OBJECT *obj;
+
+ clear();
+ for (y=0; y<YSIZE; y++) {
+ for (x=0; x<XSIZE; x++) {
+ if (numamoebas && amb[y][x] != ' ')
+ mvaddc(y+1,x*2,amb[y][x]);
+ if (obj=occupant[y][x]) {
+ if (obj->image != ' ')
+ mvaddc(y+1,x*2,obj->image);
+ }
+ }
+ }
+ Sprintf(spbuf,
+ "%-4s E: %4d %2d B: %5d %3d Enemies: %-3d Stars: %-3d Stardate%5d.%1d %9ld",
+ " ", 0, 0, 0, 0, 0, 0, timer/10+smarts*100, timer%10, 0L);
+ mvaddstr(0,0,spbuf);
+ oldeenergy = oldbenergy = oldcurscore =
+ oldstatus = oldetorp = oldbtorp = oldstrs = oldenemies = -1;
+ /* force everything to fill in */
+ if (damage)
+ olddamage = 0;
+ if (!ent)
+ etorp = 0;
+ if (!base)
+ btorp = 0;
+ display_status();
+}
+
+char
+cmstore(ch)
+Reg1 char ch;
+{
+ *maxcmstring++ = ch;
+}
+
+/* discard any characters typed ahead */
+
+void
+eat_typeahead()
+{
+#ifdef PUSHBACK
+ if (!typeahead && nextin==nextout) /* cancel only keyboard stuff */
+#else
+ if (!typeahead)
+#endif
+ {
+#ifdef PENDING
+ while (input_pending())
+ Read_tty(buf,sizeof(buf));
+#else /* this is probably v7, with no rdchk() */
+ ioctl(_tty_ch,TIOCSETP,&_tty);
+#endif
+ }
+}
+
+void
+settle_down()
+{
+ dingaling();
+ Fflush(stdout);
+ sleep(1);
+#ifdef PUSHBACK
+ nextout = nextin; /* empty circlebuf */
+#endif
+ eat_typeahead();
+}
+
+#ifdef PUSHBACK
+/* read a character from the terminal, with multi-character pushback */
+
+int
+read_tty(addr,size)
+char *addr;
+int size; /* ignored for now */
+{
+#ifdef lint
+ size = size;
+#endif
+ if (nextout != nextin) {
+ *addr = circlebuf[nextout++];
+ nextout %= PUSHSIZE;
+ return 1;
+ }
+ else {
+ size = read(0,addr,1);
+ if (size < 0)
+ sig_catcher(SIGHUP);
+ if (metakey) {
+ if (*addr & 0200) {
+ pushchar(*addr & 0177);
+ *addr = '\001';
+ }
+ }
+ else
+ *addr &= 0177;
+ return 1;
+ }
+}
+
+#ifdef PENDING
+#ifndef FIONREAD
+#ifndef RDCHK
+int
+circfill()
+{
+ Reg1 int howmany;
+ Reg2 int i;
+
+ assert (nextin == nextout);
+ howmany = read(devtty,circlebuf+nextin,metakey?1:PUSHSIZE-nextin);
+ if (howmany > 0) {
+ if (metakey) {
+ if (circlebuf[nextin] & 0200) {
+ circlebuf[nextin] &= 0177;
+ pushchar('\001');
+ }
+ }
+ else
+ for (i = howmany+nextin-1; i >= nextin; i--)
+ circlebuf[i] &= 0177;
+ nextin += howmany;
+ nextin %= PUSHSIZE; /* may end up 1 if metakey */
+ }
+ return howmany;
+}
+#endif /* RDCHK */
+#endif /* FIONREAD */
+#endif /* PENDING */
+
+void
+pushchar(ch)
+char ch;
+{
+ nextout--;
+ if (nextout < 0)
+ nextout = PUSHSIZE - 1;
+ if (nextout == nextin) {
+ fputs("\r\npushback buffer overflow\r\n",stdout);
+ sig_catcher(0);
+ }
+ circlebuf[nextout] = ch;
+}
+
+#else /* PUSHBACK */
+#ifndef read_tty
+/* read a character from the terminal, with hacks for O_NDELAY reads */
+
+int
+read_tty(addr,size)
+char *addr;
+int size;
+{
+ if (is_input) {
+ *addr = pending_ch;
+ is_input = FALSE;
+ return 1;
+ }
+ else {
+ size = read(0,addr,size);
+ if (size < 0)
+ sig_catcher(SIGHUP);
+ if (metakey) {
+ if (*addr & 0200) {
+ pending_ch = *addr & 0177;
+ is_input = TRUE;
+ *addr = '\001';
+ }
+ }
+ else
+ *addr &= 0177;
+ return size;
+ }
+}
+#endif /* read_tty */
+#endif /* PUSHBACK */
+
+int
+read_nd(buff, siz)
+char *buff;
+int siz;
+{
+ if (!input_pending())
+ return 0;
+
+ getcmd(buff);
+ return 1;
+}
+
+/* get a character into a buffer */
+
+void
+getcmd(whatbuf)
+Reg3 char *whatbuf;
+{
+#ifdef PUSHBACK
+ Reg1 KEYMAP *curmap;
+ Reg2 int i;
+ bool no_macros;
+ int times = 0; /* loop detector */
+ char scrchar;
+
+tryagain:
+ curmap = topmap;
+/* no_macros = (whatbuf != buf && nextin == nextout); */
+ no_macros = FALSE;
+#endif
+ for (;;) {
+ errno = 0;
+ if (read_tty(whatbuf,1) < 0 && !errno)
+ errno = EINTR;
+#ifdef read_tty
+ if (metakey) {
+ if (*whatbuf & 0200) {
+ *what_buf &= 037; /* punt and hope they don't notice */
+ }
+ }
+ else
+ *whatbuf &= 0177;
+#endif /* read_tty */
+ if (errno && errno != EINTR) {
+ perror(readerr);
+ sig_catcher(0);
+ }
+#ifdef PUSHBACK
+ if (*whatbuf & 0200 || no_macros) {
+ *whatbuf &= 0177;
+ goto got_canonical;
+ }
+ if (curmap == Null(KEYMAP*))
+ goto got_canonical;
+ for (i = (curmap->km_type[*whatbuf] >> KM_GSHIFT) & KM_GMASK; i; --i){
+ Read_tty(&scrchar,1);
+ }
+ switch (curmap->km_type[*whatbuf] & KM_TMASK) {
+ case KM_NOTHIN: /* no entry? */
+ if (curmap == topmap) /* unmapped canonical */
+ goto got_canonical;
+ settle_down();
+ goto tryagain;
+ case KM_KEYMAP: /* another keymap? */
+ curmap = curmap->km_ptr[*whatbuf].km_km;
+ assert(curmap != Null(KEYMAP*));
+ break;
+ case KM_STRING: /* a string? */
+ pushstring(curmap->km_ptr[*whatbuf].km_str);
+ if (++times > 20) { /* loop? */
+ fputs("\r\nmacro loop?\r\n",stdout);
+ settle_down();
+ }
+ no_macros = FALSE;
+ goto tryagain;
+ }
+#else
+ *whatbuf &= 0177;
+ break;
+#endif
+ }
+
+got_canonical:
+#ifndef TERMIO
+ if (*whatbuf == '\r')
+ *whatbuf = '\n';
+#endif
+ if (whatbuf == buf)
+ whatbuf[1] = FINISHCMD; /* tell finish_command to work */
+}
+
+#ifdef PUSHBACK
+void
+pushstring(str)
+char *str;
+{
+ Reg1 int i;
+ char tmpbuf[PUSHSIZE];
+ Reg2 char *s = tmpbuf;
+
+ assert(str != Nullch);
+ interp(s,PUSHSIZE,str);
+ for (i = strlen(s)-1; i >= 0; --i) {
+ s[i] ^= 0200;
+ pushchar(s[i]);
+ }
+}
+#endif
diff --git a/warp/term.h b/warp/term.h
new file mode 100644
index 00000000..cd304456
--- /dev/null
+++ b/warp/term.h
@@ -0,0 +1,327 @@
+/* $Header: /cvsroot/src/games/warp/term.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: term.h,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.2 86/12/12 17:05:15 lwall
+ * Baseline for net release.
+ *
+ * Revision 7.0.1.1 86/10/16 10:53:33 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:14:07 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+/* warp will still work without the following, but may get ahead at low speed */
+#ifdef TIOCOUTQ /* chars left in output queue */
+#define output_pending() (ioctl(1, TIOCOUTQ, &iocount),iocount)
+#endif
+
+/* If some of the following look something like curses calls, it is because
+ * warp used to use curses but doesn't now. Warp was neither as efficient nor
+ * as portable with curses, and since the program had to cheat on curses all
+ * over the place anyway, we ripped it out.
+ */
+#define setimage(of,to) (mvaddch(of->posy+1,of->posx*2,of->image=(to)))
+
+#define mvaddch(y,x,ch) move((y),(x),(ch))
+/* #define addch(ch) (tmpchr=(ch), write(1,&tmpchr,1), real_x++) */
+#define mvaddc(y,x,ch) move((y),(x),(ch))
+#define addc(ch) (write(1,&(ch),1), real_x++)
+#define addspace() (write(1," ",1), real_x++)
+#define mvaddstr(y,x,s) (move((y),(x),0), tmpstr = (s), \
+ tmplen = strlen(tmpstr), write(1, tmpstr, tmplen), real_x += tmplen)
+
+EXT int tmplen;
+EXT char *tmpstr;
+/* EXT char tmpchr; */
+
+/* The following macros are like the pseudo-curses macros above, but do
+ * certain amount of controlled output buffering.
+ *
+ * NOTE: a beg_qwrite()..end_qwrite() sequence must NOT contain a cursor
+ * movement (move), because the move() routine uses beg_qwrite()..end_qwrite()
+ * itself.
+ */
+
+#define beg_qwrite() (maxcmstring = cmbuffer)
+#ifdef vax
+#define qwrite() asm("movc3 _gfillen,_filler,*_maxcmstring"); maxcmstring += gfillen
+#else
+#define qwrite() (movc3(gfillen,filler,maxcmstring), maxcmstring += gfillen)
+#endif
+#define qaddc(ch) (*maxcmstring++ = (ch), real_x++)
+#define qaddch(ch) (*maxcmstring++ = (ch), real_x++)
+#define qaddspace() (*maxcmstring++ = ' ', real_x++)
+#define end_qwrite() (write(1,cmbuffer,maxcmstring-cmbuffer))
+
+/* setting a ??size to infinity forces cursor addressing in that direction */
+
+EXT int CMsize;
+EXT int BCsize INIT(1);
+EXT int DOsize INIT(1000);
+EXT int UPsize INIT(1000);
+EXT int NDsize INIT(1000);
+
+EXT int charsperhalfsec;
+
+EXT int real_y INIT(-100);
+EXT int real_x INIT(-100);
+
+#ifdef DOINIT
+char filler[] = {0,'\b',0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0};
+#else
+EXT char filler[];
+#endif
+
+EXT char *bsptr INIT(filler+1);
+
+EXT char term[12];
+
+EXT char gfillen INIT(25);
+
+EXT char *maxcmstring;
+EXT char cmbuffer[512];
+
+#define BREAKCH '\0'
+
+EXT char INTRCH INIT('\03');
+
+#ifdef PUSHBACK
+ EXT char circlebuf[PUSHSIZE];
+ EXT int nextin INIT(0);
+ EXT int nextout INIT(0);
+# ifdef PENDING
+# ifdef FIONREAD
+ EXT long iocount INIT(0);
+# ifndef lint
+# define input_pending() (nextin!=nextout || \
+(ioctl(0, FIONREAD, &iocount),(int)iocount))
+# else
+# define input_pending() bizarre
+# endif /* lint */
+# else /* FIONREAD */
+ int circfill();
+# ifdef RDCHK
+# ifndef lint
+# define input_pending() rdchk(0)
+# else /* lint */
+# define input_pending() bizarre
+# endif /* lint */
+# else /* RDCHK */
+# ifndef O_NDELAY /* assert O_NDELAY */
+ ??? PENDING isn't defined correctly in warp.h
+# endif
+ EXT int devtty INIT(0);
+# ifndef lint
+# define input_pending() (nextin!=nextout || circfill())
+# else
+# define input_pending() bizarre
+# endif /* lint */
+# endif /* RDCHK */
+# endif /* FIONREAD */
+# else /* PENDING */
+ ??? warp won't work without PENDING
+# ifndef lint
+# define input_pending() (nextin!=nextout)
+# else
+# define input_pending() bizarre
+# endif /* lint */
+# endif /* PENDING */
+#else /* PUSHBACK */
+# ifdef PENDING
+# ifdef FIONREAD /* must have FIONREAD or O_NDELAY for input_pending() */
+# define read_tty(addr,size) read(0,addr,size)
+# ifndef lint
+# define input_pending() (ioctl(0, FIONREAD, &iocount), \
+(int)iocount)
+# else
+# define input_pending() bizarre
+# endif /* lint */
+ EXT long iocount INIT(0);
+# else /* FIONREAD */
+# ifdef RDCHK /* actually, they can have rdchk() too */
+# define read_tty(addr,size) read(0,addr,size)
+# ifndef lint
+# define input_pending() rdchk(0)
+# else /* lint */
+# define input_pending() bizarre
+# endif /* lint */
+# else /* RDCHK */
+# ifndef O_NDELAY /* assert O_NDELAY */
+ ??? PENDING isn't defined correctly in warp.h
+# endif
+ EXT int devtty INIT(0);
+ EXT bool is_input INIT(FALSE);
+ EXT char pending_ch INIT(0);
+# ifndef lint
+# define input_pending() (is_input || \
+(is_input=read(devtty,&pending_ch,1)))
+# else
+# define input_pending() bizarre
+# endif /* lint */
+# endif /* RDCHK */
+# endif /* FIONREAD */
+# else /* PENDING */
+ ??? warp won't work without PENDING
+# define read_tty(addr,size) read(0,addr,size)
+# define input_pending() (FALSE)
+# endif /* PENDING */
+#endif /* PUSHBACK */
+
+/* stuff wanted by terminal mode diddling routines */
+
+#ifdef TERMIO
+EXT struct termio _tty, _oldtty;
+#else
+EXT struct sgttyb _tty;
+EXT int _res_flg INIT(0);
+#endif
+
+EXT int _tty_ch INIT(2);
+EXT bool bizarre INIT(FALSE); /* do we need to restore terminal? */
+
+/* terminal mode diddling routines */
+
+#ifdef TERMIO
+
+#define raw() ((bizarre=1),_tty.c_lflag &=~ISIG,_tty.c_cc[VMIN] = 1,ioctl(_tty_ch,TCSETAF,&_tty))
+#define noraw() ((bizarre=1),_tty.c_lflag |= ISIG,_tty.c_cc[VEOF] = CEOF,ioctl(_tty_ch,TCSETAF,&_tty))
+#define crmode() ((bizarre=1),_tty.c_lflag &=~ICANON,_tty.c_cc[VMIN] = 1,ioctl(_tty_ch,TCSETAF,&_tty))
+#define nocrmode() ((bizarre=1),_tty.c_lflag |= ICANON,_tty.c_cc[VEOF] = CEOF,ioctl(_tty_ch,TCSETAF,&_tty))
+#define echo() ((bizarre=1),_tty.c_lflag |= ECHO, ioctl(_tty_ch, TCSETAW, &_tty))
+#define noecho() ((bizarre=1),_tty.c_lflag &=~ECHO, ioctl(_tty_ch, TCSETAW, &_tty))
+#define nl() ((bizarre=1),_tty.c_iflag |= ICRNL,_tty.c_oflag |= ONLCR,ioctl(_tty_ch, TCSETAW, &_tty))
+#define nonl() ((bizarre=1),_tty.c_iflag &=~ICRNL,_tty.c_oflag &=~ONLCR,ioctl(_tty_ch, TCSETAW, &_tty))
+#define savetty() (ioctl(_tty_ch, TCGETA, &_oldtty),ioctl(_tty_ch, TCGETA, &_tty))
+#define resetty() ((bizarre=0),ioctl(_tty_ch, TCSETAF, &_oldtty))
+#define unflush_output()
+
+#else
+
+#define raw() ((bizarre=1),_tty.sg_flags|=RAW, stty(_tty_ch,&_tty))
+#define noraw() ((bizarre=1),_tty.sg_flags&=~RAW,stty(_tty_ch,&_tty))
+#define crmode() ((bizarre=1),_tty.sg_flags |= CBREAK, stty(_tty_ch,&_tty))
+#define nocrmode() ((bizarre=1),_tty.sg_flags &= ~CBREAK,stty(_tty_ch,&_tty))
+#define echo() ((bizarre=1),_tty.sg_flags |= ECHO, stty(_tty_ch, &_tty))
+#define noecho() ((bizarre=1),_tty.sg_flags &= ~ECHO, stty(_tty_ch, &_tty))
+#define nl() ((bizarre=1),_tty.sg_flags |= CRMOD,stty(_tty_ch, &_tty))
+#define nonl() ((bizarre=1),_tty.sg_flags &= ~CRMOD, stty(_tty_ch, &_tty))
+#define savetty() (gtty(_tty_ch, &_tty), _res_flg = _tty.sg_flags)
+#define resetty() ((bizarre=0),_tty.sg_flags = _res_flg, stty(_tty_ch, &_tty))
+#endif /* TERMIO */
+
+#ifdef TIOCSTI
+#ifdef lint
+#define forceme(c) ioctl(_tty_ch,TIOCSTI,Null(long*)) /* ghad! */
+#else
+#define forceme(c) ioctl(_tty_ch,TIOCSTI,c) /* pass character in " " */
+#endif /* lint */
+#else
+#define forceme(c)
+#endif
+
+/* termcap stuff */
+
+/*
+ * NOTE: if you don't have termlib you'll have to define these strings,
+ * the tputs routine, and the tgoto routine.
+ * The tgoto routine simply produces a cursor addressing string for a given
+ * x and y. The 1st argument is a generic string to be interpreted.
+ * If you are hardwiring it you might just ignore the 1st argument.
+ * The tputs routine interprets any leading number as a padding factor, possibly
+ * scaled by the number of lines (2nd argument), puts out the string (1st arg)
+ * and the padding using the routine specified as the 3rd argument.
+ */
+
+#ifdef HAVETERMLIB
+EXT char *BC INIT(Nullch); /* backspace character */
+EXT char *UP INIT(Nullch); /* move cursor up one line */
+EXT char *myUP;
+EXT char *ND INIT(Nullch); /* non-destructive cursor right */
+EXT char *myND;
+EXT char *DO INIT(Nullch); /* move cursor down one line */
+EXT char *myDO;
+EXT char *CR INIT(Nullch); /* get to left margin, somehow */
+EXT char *VB INIT(Nullch); /* visible bell */
+EXT char *CL INIT(Nullch); /* home and clear screen */
+EXT char *CE INIT(Nullch); /* clear to end of line */
+EXT char *CM INIT(Nullch); /* cursor motion -- PWP */
+EXT char *HO INIT(Nullch); /* home cursor -- PWP */
+EXT char *CD INIT(Nullch); /* clear to end of display -- PWP */
+EXT char *SO INIT(Nullch); /* begin standout mode */
+EXT char *SE INIT(Nullch); /* end standout mode */
+EXT int SG INIT(0); /* blanks left by SO and SE */
+EXT char *US INIT(Nullch); /* start underline mode */
+EXT char *UE INIT(Nullch); /* end underline mode */
+EXT char *UC INIT(Nullch); /* underline a character, if that's how it's done */
+EXT int UG INIT(0); /* blanks left by US and UE */
+EXT bool AM INIT(FALSE); /* does terminal have automatic margins? */
+EXT bool XN INIT(FALSE); /* does it eat 1st newline after automatic wrap? */
+EXT char PC INIT(0); /* pad character for use by tputs() */
+EXT short ospeed INIT(0); /* terminal output speed, for use by tputs() */
+EXT int LINES INIT(0), COLS INIT(0); /* size of screen */
+EXT int just_a_sec INIT(960); /* 1 sec at current baud rate */
+ /* (number of nulls) */
+EXT char ERASECH; /* rubout character */
+EXT char KILLCH; /* line delete character */
+
+/* define a few handy macros */
+
+#define clear() (do_tc(CL,LINES),real_y=real_x=0)
+#define erase_eol() do_tc(CE,1)
+#define backspace() (do_tc(BC,0),real_x--)
+#define clear_rest() do_tc(CD,LINES)
+#define underline() do_tc(US,1)
+#define un_underline() do_tc(UE,1)
+#define underchar() do_tc(UC,0)
+#define standout() do_tc(SO,1)
+#define un_standout() do_tc(SE,1)
+#define up_line() do_tc(UP,1)
+#define carriage_return() do_tc(CR,1)
+#define dingaling() do_tc(VB,1)
+#else
+ ???????? /* up to you */
+#endif
+
+void term_init();
+void term_set();
+#ifdef PUSHBACK
+void pushchar();
+void mac_init();
+void mac_line();
+#endif
+void eat_typeahead();
+void settle_down();
+#ifndef read_tty
+ int read_tty();
+#endif
+void getcmd();
+
+int read_nd();
+void page();
+void move();
+void do_tc();
+int comp_tc();
+void helper();
+void rewrite();
+char cmstore();
+
diff --git a/warp/them.c b/warp/them.c
new file mode 100644
index 00000000..da52e04f
--- /dev/null
+++ b/warp/them.c
@@ -0,0 +1,424 @@
+/* $Header: /cvsroot/src/games/warp/them.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: them.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.5 86/12/12 17:05:41 lwall
+ * Baseline for net release.
+ *
+ * Revision 7.0.1.4 86/10/20 12:32:38 lwall
+ * Wasn't clearing FRIENDLY flag on pirate creation.
+ *
+ * Revision 7.0.1.3 86/10/20 12:15:33 lwall
+ * Was trying to create pirates from cloaked pirates.
+ *
+ * Revision 7.0.1.2 86/10/17 10:03:44 lwall
+ * Fixed Romulan writing spaces while cloaked.
+ *
+ * Revision 7.0.1.1 86/10/16 10:53:39 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:14:15 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "bang.h"
+#include "object.h"
+#include "move.h"
+#include "score.h"
+#include "term.h"
+#include "us.h"
+#include "util.h"
+#include "weapon.h"
+#include "INTERN.h"
+#include "them.h"
+
+void
+them_init()
+{
+ ;
+}
+
+void
+their_smarts()
+{
+ Reg1 OBJECT *curkl;
+ Reg2 OBJECT *obj;
+ Reg3 int prob;
+ Reg4 int count;
+ Reg5 int y;
+ Reg6 int x;
+
+ if (numcrushes && (obj=movers)->type == Crusher) {
+ if (numamoebas) {
+ y = obj->posy;
+ x = (obj->posx+(obj->image=='<'?1:-1)+XSIZE00)%XSIZE;
+ if (amb[y][x] == '~') {
+ obj->velx = 0; /* stop and munch amoeba */
+ modify_amoeba(y,x,1,' ',(int)rand_mod(5+ambsize/10)+1);
+ if (occupant[y][x] == nuke) /* except go for nucleus */
+ obj->velx = (obj->image=='<' ? 1 : -1);
+ }
+ else if (!obj->velx) {
+ if (!rand_mod(4))
+ obj->image = rand_mod(2) ? '<' : '>';
+ obj->velx = obj->image == '<' ? 1 : -1;
+ }
+ }
+ obj->vely += (rand_mod(222) - 111) / 100;
+ if (!(rand_mod(100))) {
+ setimage(obj, (obj->velx *= -1) < 0 ? '>' : '<');
+ }
+ }
+ if (numamoebas) {
+ if (!rand_mod(3))
+ nuke->velx = nuke->vely = 0;
+ if (nuke->strategy && ambsize < 90 && !rand_mod(200-smarts))
+ modify_amoeba(0,0,0,'~',(int)rand_mod(10));
+ if (ambsize > 200 || (ambsize > 100 && !rand_mod(15)))
+ modify_amoeba(yamblast,xamblast,2,' ',(ambsize-100)/5);
+ }
+ for (curkl = enemies; curkl->type == Enemy; curkl = curkl->next) {
+ if ((curkl->flags & (CLOAKS|FRIENDLY)) == CLOAKS &&
+ (curkl->image != ' ') &&
+ (curkl->energy > 300 || massacre) ) {
+ setimage(curkl, ' ');
+ }
+ if (madgorns)
+ prob = 3;
+ else if (curkl->vely || curkl->velx)
+ prob = massacre?10:20;
+ else if ((curkl->flags & (PIRATE|FRIENDLY)) == PIRATE) {
+ /* pirates want to sit sometimes */
+ if (curkl->strategy) {
+ if ((obj = lookimg(curkl->posy, curkl->posx, '@')) ||
+ (obj = lookimg(curkl->posy, curkl->posx, 'B')) ) {
+ make_plink(obj->posy, obj->posx);
+ if (!--curkl->strategy) { /* clock ran down */
+ if (obj->image == '@') {
+ obj->image = '*';
+ numinhab--;
+ if (obj->flags & STATIC)
+ mvaddch(obj->posy+1,obj->posx*2,obj->image);
+ if (curkl->energy < 20000)
+ curkl->energy += 5000;
+ }
+ prob = 2; /* our work here is done */
+ }
+ else if (obj->image == 'B') {
+ btorp -= rand_mod(50);
+ if (btorp < 0)
+ btorp = 0;
+ obj->energy -= rand_mod(500);
+ if (obj->energy < 0)
+ obj->energy = 0;
+ prob = 10000; /* stay here */
+ }
+ else
+ prob = 10000;
+ }
+ else { /* it went away--go elsewhere */
+ prob = 4;
+ curkl->strategy = 0;
+ }
+ }
+ else if (lookimg(curkl->posy, curkl->posx, '@') ||
+ lookimg(curkl->posy, curkl->posx, 'B')) {
+ curkl->strategy = rand_mod(15)+5;
+ prob = 10000;
+ }
+ else
+ prob = 4;
+ }
+ else if (curkl->image == 'M') { /* Mudd wants to sit sometimes */
+ if ((obj = lookimg(curkl->posy, curkl->posx, 'E')) ||
+ (obj = lookimg(curkl->posy, curkl->posx, 'B')) ) {
+ if (obj->image == 'B') {
+ btorp -= rand_mod(40);
+ if (btorp < 0)
+ btorp = 0;
+ obj->energy -= rand_mod(100);
+ if (obj->energy < 0)
+ obj->energy = 0;
+ }
+ else if (!obj->vely && !obj->velx) {
+ etorp -= rand_mod(10);
+ if (etorp < 0)
+ etorp = 0;
+ obj->energy -= rand_mod(20);
+ if (obj->energy < 0)
+ obj->energy = 0;
+ }
+ prob = 10000; /* stay here */
+ }
+ else /* it went away--go elsewhere */
+ prob = 4;
+ }
+ else if (curkl->flags & FRIENDLY) {
+ if (curkl->energy < 10000 &&
+ lookimg(curkl->posy, curkl->posx, '@') ) {
+ curkl->energy += 100;
+ prob = 20; /* do some loading */
+ }
+ else
+ prob = 4;
+ }
+ else if (curkl->image == '&') {
+ if (curkl->flags & COUNTDOWN) {
+ if (curkl->strategy)
+ curkl->strategy--;
+ else
+ curkl->flags &= ~COUNTDOWN;
+ prob = 100; /* someone's feeding us, so sit still */
+ }
+ else
+ prob = 4;
+ }
+ else
+ prob = 4; /* don't sit still too long */
+ count = 11;
+ for (;;) {
+ if (--count <= 0) /* no opening, just ram something */
+ break;
+
+#ifdef lint
+ prob = prob;
+#endif
+ if (!(rand_mod(prob))) /* turn randomly occasionally */
+ goto accell;
+
+ y=(curkl->posy+curkl->vely+YSIZE00)%YSIZE; /* find prospective */
+ x=(curkl->posx+curkl->velx+XSIZE00)%XSIZE; /* new position */
+
+ if (numamoebas) {
+ if (curkl == nuke) {
+ if (amb[y][x] != '~')
+ goto accell; /* never move nucleus from protoplasm */
+ }
+ else {
+ if (amb[y][x] == '~' && rand_mod(2)) {
+ yamblast = y;
+ xamblast = x;
+ goto accell;
+ }
+ }
+ }
+
+ obj = occupant[y][x];
+ if (!obj) break; /* is anyone there? */
+
+ switch (obj->type) {
+ case Star:
+ if (obj->image == '@' && (curkl->flags & PIRATE)) {
+ if (curkl->image != 'P' && curkl->image != ' ') {
+ if (curkl->flags & FRIENDLY) {
+ curkl->flags &= ~FRIENDLY;
+ curkl->energy += 1000;
+ possiblescore += curkl->mass;
+ inumfriends--;
+ numfriends--;
+ inumenemies++;
+ numenemies++;
+ }
+ curkl->image = 'P';
+ }
+ break; /* go ahead and ram the star */
+ }
+ goto accell; /* try not to ram stars */
+ case Torp:
+ if (!obj->vely && !obj->velx && (rand_mod(100) <= smarts) &&
+ (obj->image == 'o' || obj->image == 'O' || obj->image == 'X'))
+ goto accell; /* try not to ram "friendly" torps */
+ break;
+ case Web:
+ if (curkl->image != 'T')
+ goto accell; /* non-Tholians shouldn't ram web */
+ if (count <= 5)
+ break; /* Tholians retrace web if desperate */
+ if (obj->image ==
+ (curkl->vely?
+ (curkl->velx?
+ (curkl->velx==curkl->vely?
+ '\\'
+ :
+ '/'
+ )
+ :
+ '|'
+ )
+ :
+ '-'
+ )
+ ) goto accell; /* Tholians try not to retrace web */
+ break; /* No problem with crossing web */
+ }
+ break; /* okay to move over object */
+
+ accell:
+ /* determine maximum velocity */
+ if (massacre && curkl->image != 'T') {
+ curkl->vely = rand_mod(7) - 3;
+ curkl->velx = rand_mod(7) - 3;
+ }
+ else if (curkl->image == '&') {
+ if (rand_mod(2)) {
+ curkl->vely = rand_mod(3) - 1;
+ curkl->velx = rand_mod(3) - 1;
+ }
+ else {
+ curkl->vely = curkl->strategy & 3;
+ if (curkl->vely & 2)
+ curkl->vely = -1;
+ curkl->velx = (curkl->strategy >> 2) & 3;
+ if (curkl->velx & 2)
+ curkl->velx = -1;
+ }
+ }
+ else if (curkl->energy >= 2500 && curkl->image != 'T') {
+ curkl->vely = rand_mod(5) - 2;
+ curkl->velx = rand_mod(5) - 2;
+ }
+ else {
+ curkl->vely = rand_mod(3) - 1;
+ curkl->velx = rand_mod(3) - 1;
+ }
+ }
+ if (count != 10) {
+ if (curkl->image == ' ') {
+ setimage(curkl, curkl->flags & PIRATE ? 'P' : 'R');
+ }
+ if (!count) {
+ curkl->vely = 0;
+ curkl->velx = 0;
+ }
+ }
+ if (curkl->image == 'G' && (base||ent) &&
+ !rand_mod((103-smarts)*10) ) {
+ int xxx,yyy;
+
+ for (xxx = -1; xxx<=1; xxx++)
+ for (yyy = -1; yyy<=1; yyy++)
+ if ((xxx||yyy) && rand_mod(2))
+ fire_torp(curkl,yyy,xxx);
+ }
+ else if (curkl->image == 'T' && (curkl->velx || curkl->vely)) {
+ Make_object(Web,
+ curkl->vely?
+ (curkl->velx?
+ (curkl->velx==curkl->vely?
+ '\\'
+ :
+ '/'
+ )
+ :
+ '|'
+ )
+ :
+ '-',
+ curkl->posy,curkl->posx,0,0,32767L,32767L,&root);
+ if (obj && obj->type == Web) {
+ unmake_object(obj);
+ occupant[y][x] = Null(OBJECT*);
+ }
+ }
+ }
+ /* klingon-style fighting */
+ if (numamoebas)
+ attack(nuke);
+ attack(base);
+ if (ent && (!cloaked || ent->image=='E' || ent->image=='e'))
+ attack(ent);
+}
+
+void
+modify_amoeba(y,x,where,ch,quant)
+Reg1 int y;
+Reg2 int x;
+int where;
+Reg6 int ch;
+Reg7 int quant;
+{
+ Reg3 int dy;
+ Reg4 int dx;
+ Reg5 int count = 15;
+
+ if (!numamoebas)
+ return;
+ if (!where || (where==1 && rand_mod(2))) {
+ y = nuke->posy;
+ x = nuke->posx;
+ }
+ if (nuke->strategy && rand_mod(3)) {
+ dy = nuke->strategy & 3;
+ if (dy & 2)
+ dy = -1;
+ dx = (nuke->strategy >> 2) & 3;
+ if (dx & 2)
+ dx = -1;
+ if (ch == ' ') { /* take from the tail */
+ dy = -dy;
+ dx = -dx;
+ }
+ if (!rand_mod(100))
+ nuke->strategy = rand_mod(256);
+ }
+ else {
+ dy = rand_mod(3) - 1;
+ dx = rand_mod(3) - 1;
+ }
+ if (!dy && !dx)
+ return;
+ do {
+ if (--count < 0)
+ return;
+ y = (y + dy + YSIZE00) % YSIZE;
+ x = (x + dx + XSIZE00) % XSIZE;
+ } while (amb[y][x] != ' ');
+ if (ch == ' ') {
+ y = (y - dy + YSIZE00) % YSIZE;
+ x = (x - dx + XSIZE00) % XSIZE;
+ }
+ if (ambsize > 100 && quant > 2) {
+ quant >>= (ambsize/100);
+ }
+ if ((nuke->energy += quant << 6) > 32767)
+ nuke->energy = 32767;
+ count = quant << 3; /* endless loop catcher */
+ while (count-- > 0 && quant > 0) {
+ if (amb[y][x] != ch) {
+ quant--;
+ amb[y][x] = ch;
+ if (ch == '~') {
+ ambsize++;
+ yblasted[y] |= 2;
+ xblasted[x] |= 2;
+ blasted = TRUE;
+ }
+ else
+ ambsize--;
+ if (!occupant[y][x])
+ mvaddch(y+1,x*2,ch);
+ }
+ y = (y + rand_mod(3) + YSIZE99) % YSIZE;
+ x = (x + rand_mod(3) + XSIZE99) % XSIZE;
+ }
+}
diff --git a/warp/them.h b/warp/them.h
new file mode 100644
index 00000000..fe91825e
--- /dev/null
+++ b/warp/them.h
@@ -0,0 +1,29 @@
+/* $Header: /cvsroot/src/games/warp/them.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: them.h,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 86/10/08 15:14:19 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+void their_smarts();
+void modify_amoeba();
+void them_init();
diff --git a/warp/us.c b/warp/us.c
new file mode 100644
index 00000000..c12f4090
--- /dev/null
+++ b/warp/us.c
@@ -0,0 +1,528 @@
+/* $Header: /cvsroot/src/games/warp/us.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: us.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.3 87/01/13 17:13:21 lwall
+ * Partially fixed ^S behavior. It now just ignores ^S.
+ *
+ * Revision 7.0.1.2 86/12/12 17:06:09 lwall
+ * Baseline for net release.
+ *
+ * Revision 7.0.1.1 86/10/16 10:53:50 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:14:21 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "bang.h"
+#include "object.h"
+#include "play.h"
+#include "sig.h"
+#include "term.h"
+#include "util.h"
+#include "weapon.h"
+#include "INTERN.h"
+#include "us.h"
+
+void
+us_init()
+{
+ ;
+}
+
+void
+do_direction(dy,dx)
+int dy, dx;
+{
+ Reg1 int decr;
+ Reg2 OBJECT *obj;
+
+ if (status < 2) {
+ if (cloaking) {
+ char ch;
+
+ cloaked = FALSE;
+ ch = (ent->energy >= 500?'E':'e');
+ if (ch != ent->image) {
+ setimage(ent, ch);
+ }
+ }
+ decr = 5+abs(evely)+abs(evelx)+tractor*tractor;
+ if (ent->energy >= decr) {
+ ent->energy -= decr;
+ if (tractor) {
+ if (!damage || !damflag[NOTRACTORS]) {
+ if (!rand_mod(50)) {
+ damage++;
+ damflag[NOTRACTORS] = rand_mod(smarts+10)+2;
+ }
+ if (tract(ent,dy,dx,tractor)) {
+ evely += tractor*dy;
+ evelx += tractor*dx;
+ }
+ }
+ }
+ else if (!damage ||
+ (!entmode && !damflag[NOIMPULSE]) ||
+ (entmode && !damflag[NOWARP]) ) {
+ if (!rand_mod(30+500/(abs(evely)+abs(evelx)+1))) {
+ damage++;
+ damflag[entmode?NOWARP:NOIMPULSE] = rand_mod(smarts+10)+2;
+ }
+ evely += dy;
+ evelx += dx;
+ }
+ if (inumthols &&
+ (obj=occupant[(ent->posy+evely+YSIZE00)%YSIZE]
+ [(ent->posx+evelx+XSIZE00)%XSIZE] ) &&
+ obj->type == Web)
+ evely = evelx = 0;
+ }
+ }
+ else if (status == 2) {
+ decr = 500+abs(bvely)*5+abs(bvelx)*5+tractor*tractor*100;
+ if (base->energy >= decr) {
+ base->energy -= decr;
+ if (tractor) {
+ if (tract(base,dy,dx,tractor)) {
+ bvely += tractor*dy;
+ bvelx += tractor*dx;
+ }
+ }
+ else {
+ bvely += dy;
+ bvelx += dx;
+ }
+ if (inumthols &&
+ (obj=occupant[(base->posy+bvely+YSIZE00)%YSIZE]
+ [(base->posx+bvelx+XSIZE00)%XSIZE] ) &&
+ obj->type == Web)
+ bvely = bvelx = 0;
+ }
+ }
+ tractor = 0;
+}
+
+void
+ctrl_direction(dy,dx)
+int dy, dx;
+{
+ if (status < 2) {
+ if (cloaking) {
+ char ch;
+
+ cloaked = FALSE;
+ ch = (ent->energy >= 500?'E':'e');
+ if (ch != ent->image) {
+ setimage(ent, ch);
+ }
+ }
+ if (!damage || !damflag[NOPHASERS]) {
+ if (!rand_mod(200)) {
+ damage++;
+ damflag[NOPHASERS] = rand_mod(smarts+10)+2;
+ }
+ fire_phaser(ent, dy, dx);
+ }
+ }
+ else if (status == 2)
+ fire_phaser(base, dy, dx);
+}
+
+void
+shift_direction(dy,dx)
+int dy, dx;
+{
+ if (status < 2) {
+ if (cloaking) {
+ char ch;
+
+ cloaked = FALSE;
+ ch = (ent->energy >= 500?'E':'e');
+ if (ch != ent->image) {
+ setimage(ent, ch);
+ }
+ }
+ if (!damage || !damflag[NOTORPS]) {
+ if (!rand_mod(300)) {
+ damage++;
+ damflag[NOTORPS] = rand_mod(smarts+10)+2;
+ }
+ fire_torp(ent, dy, dx);
+ }
+ }
+ else if (status == 2)
+ fire_torp(base, dy, dx);
+}
+
+void
+get_commands(done)
+bool *done;
+{
+ static char ch[80];
+ Reg1 int i;
+ Reg2 int count;
+ Reg3 bool ctrla = FALSE;
+ char numdestructs = 0, numzaps = 0;
+
+top:
+ while (count = read_nd(ch,(sizeof ch))) {
+ for (i=0; i<count; i++) {
+ if (ch[i] == 'Q') {
+ bombed_out = TRUE;
+ *done = TRUE;
+ keepgoing = FALSE;
+ return;
+ }
+ if (ch[i] == 'q' || ch[i] == BREAKCH || ch[i] == INTRCH) {
+ int x;
+ static char quest[] = "Do you wish to escape from reality? ";
+
+ if (timer >= whenok) {
+ mvaddstr(12,22,quest);
+ do {
+ getcmd(&ch[i]);
+ } while (ch[i] != 'y' && ch[i] != 'n');
+ if (ch[i] == 'y') {
+ bombed_out = TRUE;
+ *done = TRUE;
+ return;
+ }
+ else {
+ for (x=11; x<=28; x++) {
+ mvaddch(12,x*2,
+ occupant[11][x]
+ ? occupant[11][x]->image
+ : numamoebas
+ ? amb[11][x]
+ : ' ');
+ addspace();
+ }
+ roundsleep(2);
+ whenok = timer + 10;
+ goto top;
+ }
+ }
+ else {
+ write(1,"\07",1);
+ goto top;
+ }
+ }
+ }
+ for (i=0; i<count; i++) {
+ if (ctrla) {
+ switch (ch[i]) {
+ case '1': case 'b':
+ ctrl_direction(1, -1);
+ break;
+ case '2': case 'j':
+ ctrl_direction(1, 0);
+ break;
+ case '3': case 'n':
+ ctrl_direction(1, 1);
+ break;
+ case '4': case 'h':
+ ctrl_direction(0, -1);
+ break;
+ case '6': case 'l':
+ ctrl_direction(0, 1);
+ break;
+ case '7': case 'y':
+ ctrl_direction(-1, -1);
+ break;
+ case '8': case 'k':
+ ctrl_direction(-1, 0);
+ break;
+ case '9': case 'u':
+ ctrl_direction(-1, 1);
+ break;
+ case 'r':
+ rewrite();
+ roundsleep(3);
+ ctrla = FALSE;
+ goto top;
+ case 'w':
+ clear();
+ while (!input_pending())
+ sleep(1);
+ rewrite();
+ roundsleep(3);
+ ctrla = FALSE;
+ goto top;
+#ifdef SIGTSTP
+ case 'z':
+ clear();
+ mytstp();
+ sleep(4);
+ ctrla = FALSE;
+ goto top;
+#endif
+ default:
+ break;
+ }
+ ctrla = FALSE;
+ }
+ else {
+ switch (ch[i]) {
+ case 'Z':
+ clear();
+ mytstp();
+ sleep(4);
+ goto top;
+ case 'i':
+ if (ent && (!damage || !damflag[NOIMPULSE])) {
+ entmode = 0;
+ status = 0;
+ }
+ break;
+ case 'w':
+ if (ent && (!damage || !damflag[NOWARP])) {
+ entmode = 1;
+ status = 1;
+ }
+ break;
+ case 'p':
+ if (base) {
+ status = 2;
+ }
+ break;
+ case 'o':
+ if (status < 2) {
+ if (base)
+ status = 2;
+ }
+ else if (status == 2) {
+ if (ent)
+ status = entmode;
+ }
+ break;
+ case 'v':
+ if (ent) {
+ status = entmode;
+ }
+ cloaking=FALSE;
+ cloaked=FALSE;
+ break;
+ case 'c':
+ if (ent) {
+ status = entmode;
+ if (ent->energy >= 250)
+ cloaking = TRUE;
+ }
+ break;
+ case 'z':
+ if (ent && (!damage || !damflag[NOZAPPER])) {
+ ++numzaps;
+ if (!rand_mod(100/numzaps)) {
+ damage++;
+ damflag[NOZAPPER] = rand_mod(smarts+10)+2;
+ }
+ if (nxtbang && bangm[nxtbang-1] < 0)
+ --nxtbang; /* consolidate zaps */
+ make_blast(evely*2+ent->posy,evelx*2+ent->posx,
+ -5000000L, 3*numzaps);
+ ent->energy /= 2;
+ }
+ break;
+ case 'D':
+ if (status < 2 && (!damage || !damflag[NODESTRUCT])) {
+ if (ent && !rand_mod(10)) {
+ damage++;
+ damflag[NODESTRUCT] = rand_mod(smarts+10)+2;
+ }
+ if (++numdestructs <= 2)
+ make_blast(evely*2+ent->posy,evelx*2+ent->posx,
+ 15000L, 3);
+ ent->energy /= 4;
+ }
+ else if (status == 2) {
+ if (numdestructs)
+ base->energy = base->energy / 2;
+ if (++numdestructs <= 2)
+ make_blast(base->posy, base->posx, 15000L, 5);
+ }
+ break;
+ case 'd':
+ if ((!damage || !damflag[NODESTRUCT]) && (base||ent)) {
+ Reg4 OBJECT *obj;
+ int x, y;
+
+ if (ent && !rand_mod(200)) {
+ damage++;
+ damflag[NODESTRUCT] = rand_mod(smarts+10)+2;
+ }
+ for (obj = root.prev;
+ obj != &root;
+ obj = obj->prev) {
+ if (obj->image == '+') {
+ blast[y=(obj->posy+obj->vely+YSIZE00)%YSIZE]
+ [x=(obj->posx+obj->velx+XSIZE00)%XSIZE]
+ += 1;
+ yblasted[y] |= 1;
+ xblasted[x] |= 1;
+ blasted = TRUE;
+ obj->mass = (massacre?3000:4000);
+ }
+ }
+ }
+ break;
+ case 's':
+ if ((!damage || !damflag[NODESTRUCT]) && (base||ent)) {
+ Reg4 OBJECT *obj;
+ if (ent && !rand_mod(200)) {
+ damage++;
+ damflag[NODESTRUCT] = rand_mod(smarts+10)+2;
+ }
+ for (obj = root.prev;
+ obj->type == Torp || obj->type == Web ||
+ obj->type == Star;
+ obj = obj->prev) {
+ if (obj->image == '+')
+ obj->vely = obj->velx = 0;
+ }
+ }
+ break;
+ case '\001':
+ ctrla = TRUE;
+ break;
+ case '\002':
+ case '\003':
+ case '\004':
+ case '\005':
+ case '\006':
+ case '\007':
+ case '\010':
+ case '\011':
+ case '\012':
+ case '\013':
+ case '\014':
+ case '\015':
+ case '\016':
+ case '\017':
+ case '\020':
+ case '\021':
+ case '\022':
+ case '\023':
+ case '\024':
+ case '\025':
+ case '\026':
+ case '\027':
+ case '\030':
+ case '\031':
+ case '\032':
+ ch[i] += 96;
+ i--;
+ ctrla = TRUE;
+ break;
+ case '\033':
+ tractor = 0;
+ break;
+ case 'a':
+ tractor++;
+ break;
+ case 'r':
+ tractor--;
+ break;
+ case '1': case 'b':
+ do_direction(1,-1);
+ break;
+ case '2': case 'j':
+ do_direction(1,0);
+ break;
+ case '3': case 'n':
+ do_direction(1,1);
+ break;
+ case '4': case 'h':
+ do_direction(0,-1);
+ break;
+ case '6': case 'l':
+ do_direction(0,1);
+ break;
+ case '7': case 'y':
+ do_direction(-1,-1);
+ break;
+ case '8': case 'k':
+ do_direction(-1,0);
+ break;
+ case '9': case 'u':
+ do_direction(-1,1);
+ break;
+ case '0': case 'S':
+ if (status < 2) {
+ evely = 0;
+ evelx = 0;
+ }
+ break;
+ case '-':
+ if (status < 2 && ent->energy >= 10) {
+ evely *= -1;
+ evelx *= -1;
+ ent->energy -= 10;
+ }
+ break;
+ case '%': case '\177': case '_':
+ shift_direction(0, -1);
+ shift_direction(0, 1);
+ shift_direction(-1, 0);
+ shift_direction(1, 0);
+ shift_direction(-1, -1);
+ shift_direction(-1, 1);
+ shift_direction(1, -1);
+ shift_direction(1, 1);
+ break;
+ case '!': case 'B':
+ shift_direction(1, -1);
+ break;
+ case '@': case 'J':
+ shift_direction(1, 0);
+ break;
+ case '#': case 'N':
+ shift_direction(1, 1);
+ break;
+ case '$': case 'H':
+ shift_direction(0, -1);
+ break;
+ case '^': case 'L':
+ shift_direction(0, 1);
+ break;
+ case '&': case 'Y':
+ shift_direction(-1, -1);
+ break;
+ case '*': case 'K':
+ shift_direction(-1, 0);
+ break;
+ case '(': case 'U':
+ shift_direction(-1, 1);
+ break;
+ case '?':
+ helper();
+ roundsleep(3);
+ goto top;
+ default:
+ break;
+ }
+ }
+ }
+ }
+}
diff --git a/warp/us.h b/warp/us.h
new file mode 100644
index 00000000..9b6e008a
--- /dev/null
+++ b/warp/us.h
@@ -0,0 +1,79 @@
+/* $Header: /cvsroot/src/games/warp/us.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: us.h,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.1 86/10/16 10:53:58 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:14:27 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+EXT bool cloaking;
+EXT bool cloaked;
+
+EXT int status;
+EXT int entmode;
+
+EXT int evely;
+EXT int evelx;
+EXT int bvely;
+EXT int bvelx;
+
+#define MAXDAMAGE 9
+#define NOWARP 0
+#define NOIMPULSE 1
+#define NOPHASERS 2
+#define NOTORPS 3
+#define NOCLOAKING 4
+#define NOSHIELDS 5
+#define NOZAPPER 6
+#define NODESTRUCT 7
+#define NOTRACTORS 8
+
+EXT int dam INIT(0);
+EXT int lastdam INIT(-1);
+EXT int damage INIT(0);
+EXT int olddamage INIT(-1);
+
+#ifdef DOINIT
+char *dammess[MAXDAMAGE] = {
+ "WARP",
+ "IMPULSE",
+ "PHASERS",
+ "TORPS",
+ "CLOAKING",
+ "SHIELDS",
+ "ZAPPER",
+ "DESTRUCT",
+ "TRACTORS"
+};
+char damflag[MAXDAMAGE] = {0,0,0,0,0,0,0,0,0};
+#else
+extern char *dammess[];
+extern char damflag[];
+#endif
+
+void do_direction();
+void ctrl_direction();
+void shift_direction();
+void get_commands();
+void us_init();
diff --git a/warp/util.c b/warp/util.c
new file mode 100644
index 00000000..a446d7d4
--- /dev/null
+++ b/warp/util.c
@@ -0,0 +1,344 @@
+/* $Header: /cvsroot/src/games/warp/util.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: util.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.2 86/10/20 12:07:46 lwall
+ * Made all exits reset tty.
+ *
+ * Revision 7.0.1.1 86/10/16 10:54:02 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:14:31 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "sys/dir.h"
+#include "object.h"
+#include "sig.h"
+#include "term.h"
+#include "INTERN.h"
+#include "util.h"
+
+void
+util_init()
+{
+ ;
+}
+
+void
+movc3(len,src,dest)
+#ifdef vax
+char *dest, *src;
+int len;
+{
+ asm("movc3 4(ap),*8(ap),*12(ap)");
+}
+#else
+Reg1 char *dest;
+Reg2 char *src;
+Reg3 int len;
+{
+ if (dest <= src) {
+ for (; len; len--) {
+ *dest++ = *src++;
+ }
+ }
+ else {
+ dest += len;
+ src += len;
+ for (; len; len--) {
+ *--dest = *--src;
+ }
+ }
+}
+#endif
+
+void
+no_can_do(what)
+char *what;
+{
+ fprintf(stderr,"Sorry, your terminal is too %s to play warp.\r\n",what);
+ finalize(1);
+}
+
+int
+exdis(maxnum)
+int maxnum;
+{
+ double temp, temp2;
+ double exp();
+ double log();
+
+ temp = (double) maxnum;
+#ifndef lint
+ temp2 = (double) myrand();
+#else
+ temp2 = 0.0;
+#endif
+#if RANDBITS == 15
+ return (int) exp(temp2 * log(temp)/0x7fff);
+#else
+#if RANDBITS == 16
+ return (int) exp(temp2 * log(temp)/0xffff);
+#else
+ return (int) exp(temp2 * log(temp)/0x7fffffff);
+#endif
+#endif
+}
+
+static char nomem[] = "warp: out of memory!\r\n";
+
+/* paranoid version of malloc */
+
+char *
+safemalloc(size)
+MEM_SIZE size;
+{
+ char *ptr;
+ char *malloc();
+
+ ptr = malloc(size?size:1); /* malloc(0) is NASTY on our system */
+ if (ptr != Nullch)
+ return ptr;
+ else {
+ fputs(nomem,stdout);
+ sig_catcher(0);
+ }
+ /*NOTREACHED*/
+}
+
+/* safe version of string copy */
+
+char *
+safecpy(to,from,len)
+char *to;
+Reg2 char *from;
+Reg1 int len;
+{
+ Reg3 char *dest = to;
+
+ if (from != Nullch)
+ for (len--; len && (*dest++ = *from++); len--) ;
+ *dest = '\0';
+ return to;
+}
+
+/* copy a string up to some (non-backslashed) delimiter, if any */
+
+char *
+cpytill(to,from,delim)
+Reg2 char *to;
+Reg1 char *from;
+Reg3 int delim;
+{
+ for (; *from; from++,to++) {
+ if (*from == '\\' && from[1] == delim)
+ from++;
+ else if (*from == delim)
+ break;
+ *to = *from;
+ }
+ *to = '\0';
+ return from;
+}
+
+/* return ptr to little string in big string, NULL if not found */
+
+char *
+instr(big, little)
+char *big, *little;
+
+{
+ Reg3 char *t;
+ Reg1 char *s;
+ Reg2 char *x;
+
+ for (t = big; *t; t++) {
+ for (x=t,s=little; *s; x++,s++) {
+ if (!*x)
+ return Nullch;
+ if (*s != *x)
+ break;
+ }
+ if (!*s)
+ return t;
+ }
+ return Nullch;
+}
+
+/* effective access */
+
+#ifdef SETUIDGID
+int
+eaccess(filename, mod)
+char *filename;
+int mod;
+{
+ int protection, euid;
+
+ mod &= 7; /* remove extraneous garbage */
+ if (stat(filename, &filestat) < 0)
+ return -1;
+ euid = geteuid();
+ if (euid == ROOTID)
+ return 0;
+ protection = 7 & (filestat.st_mode >>
+ (filestat.st_uid == euid ? 6 :
+ (filestat.st_gid == getegid() ? 3 : 0)
+ ));
+ if ((mod & protection) == mod)
+ return 0;
+ errno = EACCES;
+ return -1;
+}
+#endif
+
+/*
+ * Get working directory
+ */
+
+#ifdef GETWD
+#define dot "."
+#define dotdot ".."
+
+static char *name;
+
+static DIR *dirp;
+static int off;
+static struct stat d, dd;
+static struct direct *dir;
+
+char *
+getwd(np)
+char *np;
+{
+ long rdev, rino;
+
+ *np++ = '/';
+ *np = 0;
+ name = np;
+ off = -1;
+ stat("/", &d);
+ rdev = d.st_dev;
+ rino = d.st_ino;
+ for (;;) {
+ stat(dot, &d);
+ if (d.st_ino==rino && d.st_dev==rdev)
+ goto done;
+ if ((dirp = opendir(dotdot)) == Null(DIR *))
+ prexit("getwd: cannot open ..\r\n");
+ stat(dotdot, &dd);
+ chdir(dotdot);
+ if(d.st_dev == dd.st_dev) {
+ if(d.st_ino == dd.st_ino)
+ goto done;
+ do
+ if ((dir = readdir(dirp)) == Null(struct direct *))
+ prexit("getwd: read error in ..\r\n");
+ while (dir->d_ino != d.st_ino);
+ }
+ else do {
+ if ((dir = readdir(dirp)) == Null(struct direct *))
+ prexit("getwd: read error in ..\r\n");
+ stat(dir->d_name, &dd);
+ } while(dd.st_ino != d.st_ino || dd.st_dev != d.st_dev);
+ cat();
+ closedir(dirp);
+ }
+done:
+ name--;
+ if (chdir(name) < 0) {
+ printf("getwd: can't cd back to %s\r\n",name);
+ sig_catcher(0);
+ }
+ return (name);
+}
+
+void
+cat()
+{
+ Reg1 int i;
+ Reg2 int j;
+
+ i = -1;
+ while (dir->d_name[++i] != 0);
+ if ((off+i+2) > 1024-1)
+ return;
+ for(j=off+1; j>=0; --j)
+ name[j+i+1] = name[j];
+ if (off >= 0)
+ name[i] = '/';
+ off=i+off+1;
+ name[off] = 0;
+ for(--i; i>=0; --i)
+ name[i] = dir->d_name[i];
+}
+
+void
+prexit(cp)
+char *cp;
+{
+ write(2, cp, strlen(cp));
+ sig_catcher(0);
+}
+#else
+char *
+getwd(np) /* shorter but slower */
+char *np;
+{
+ FILE *popen();
+ FILE *pipefp = popen("/bin/pwd","r");
+
+ if (pipefp == Nullfp) {
+ printf("Can't run /bin/pwd\r\n");
+ finalize(1);
+ }
+ Fgets(np,512,pipefp);
+ np[strlen(np)-1] = '\0'; /* wipe out newline */
+ pclose(pipefp);
+ return np;
+}
+#endif
+
+/* copy a string to a safe spot */
+
+char *
+savestr(str)
+char *str;
+{
+ Reg1 char *newaddr = safemalloc((MEM_SIZE)(strlen(str)+1));
+
+ strcpy(newaddr,str);
+ return newaddr;
+}
+
+char *
+getval(nam,def)
+char *nam,*def;
+{
+ char *val;
+
+ if ((val = getenv(nam)) == Nullch || !*val)
+ val = def;
+ return val;
+}
diff --git a/warp/util.h b/warp/util.h
new file mode 100644
index 00000000..ed16ccae
--- /dev/null
+++ b/warp/util.h
@@ -0,0 +1,102 @@
+/* $Header: /cvsroot/src/games/warp/util.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: util.h,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 86/10/08 15:14:37 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#if RANDBITS < 15 || defined(lint)
+#define rand_mod(m) getpid()
+#define RANDRAND 0.0
+#define HALFRAND 0
+#define myrand() getpid()
+#else
+#if RANDBITS == 15 /* 15 bits of rand()? */
+#define RANDRAND 268435456.0 /* that's 2**28 */
+#define HALFRAND 0x4000 /* that's 2**14 */
+int rand();
+#define myrand() (rand()&32767)
+#define rand_mod(m) ((int)((double)myrand() / 32768.0 * ((double)(m))))
+/* pick number in 0..m-1 */
+
+#else
+
+#if RANDBITS < 31 /* 16 bits of rand()? */
+#define RANDRAND 1073741824.0 /* that's 2**30 */
+#define HALFRAND 0x8000 /* that's 2**15 */
+unsigned rand();
+#define myrand() (rand()&65535)
+#define rand_mod(m) ((int)((double)myrand() / 65536.0 * ((double)(m))))
+/* pick number in 0..m-1 */
+
+#else /* assume 31 bits */
+#define RANDRAND 1152921504606846976.0 /* that's 2**60 */
+#define HALFRAND 0x40000000 /* that's 2**30 */
+long rand();
+#define myrand() rand()
+#define rand_mod(m) ((myrand() / 37) % (m)) /* pick number in 0..m-1 */
+/*
+ * The reason for the /37 above is that our random number generator yields
+ * successive evens and odds, for some reason. This makes strange star maps.
+ */
+#endif
+#endif
+#endif
+
+
+ /* we get fractions of seconds from calling ftime on timebuf */
+
+EXT struct timeb timebuf;
+#define roundsleep(x) (ftime(&timebuf),sleep(timebuf.millitm > 500?x+1:x))
+
+void movc3();
+void no_can_do();
+int exdis();
+
+EXT bool waiting INIT(FALSE); /* are we waiting for subprocess (in doshell)? */
+
+#ifdef NOTDEF
+EXT int len_last_line_got INIT(0);
+ /* strlen of some_buf after */
+ /* some_buf = get_a_line(bufptr,buffersize,fp) */
+#endif
+
+#ifdef NOTDEF
+/* is the string for makedir a directory name or a filename? */
+
+#define MD_DIR 0
+#define MD_FILE 1
+#endif
+
+void util_init();
+char *safemalloc();
+char *safecpy();
+char *cpytill();
+char *instr();
+#ifdef SETUIDGID
+ int eaccess();
+#endif
+char *getwd();
+void cat();
+void prexit();
+char *savestr();
+char *getval();
diff --git a/warp/version.c b/warp/version.c
new file mode 100644
index 00000000..4bdabb89
--- /dev/null
+++ b/warp/version.c
@@ -0,0 +1,39 @@
+/* $Header: /cvsroot/src/games/warp/version.c,v 1.1 2020/11/09 23:37:05 kamil Exp $
+ *
+ * $Log: version.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 86/10/08 15:14:39 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "patchlevel.h"
+#include "INTERN.h"
+#include "version.h"
+
+/* Print out the version number. */
+
+void
+version()
+{
+ extern char rcsid[];
+
+ printf("%s\r\nPatch level: %d\r\n", rcsid, PATCHLEVEL);
+}
diff --git a/warp/version.h b/warp/version.h
new file mode 100644
index 00000000..3739b71b
--- /dev/null
+++ b/warp/version.h
@@ -0,0 +1,27 @@
+/* $Header: /cvsroot/src/games/warp/version.h,v 1.1 2020/11/09 23:37:05 kamil Exp $
+ *
+ * $Log: version.h,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 86/10/08 15:14:43 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+void version();
diff --git a/warp/warp.c b/warp/warp.c
new file mode 100644
index 00000000..941b4ca2
--- /dev/null
+++ b/warp/warp.c
@@ -0,0 +1,424 @@
+char rcsid[] = "@(#)$Header: /cvsroot/src/games/warp/warp.c,v 1.1 2020/11/09 23:37:05 kamil Exp $";
+
+/* warp -- a real-time space war program
+ * author: Larry Wall
+ * helpers: Jonathan and Mark Biggar, and Dan Faigin
+ * special thanks to my sweetie Gloria who suggested the Planet Crusher
+ *
+ * Copyright (C) 1986, Larry Wall
+ *
+ * This program may be copied as long as this copyright notice is
+ * included, and as long as it is not being copied for purposes
+ * of profit. If you want to modify this program in any way other
+ * than normal configuration changes, common decency would suggest
+ * that you also modify the name of the program so that my good name
+ * (what there is of it) is not impugned. (Calling it something like
+ * "warpx" or "superwarp" would be fine.) Also, give it another
+ * WARPDIR so that the scoreboards don't get confused.
+ *
+ * version 5.0 04/20/83
+ * 5.1 05/05/83 various tidbits
+ * 5.2 05/12/83 VAX -> vax, ifdef'ed a SIGCONT
+ * 5.3 05/24/83 RCS
+ *
+ * $Log: warp.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.3 86/12/12 17:07:44 lwall
+ * Baseline for net release.
+ *
+ * Revision 7.0.1.2 86/10/20 12:08:00 lwall
+ * Made all exits reset tty.
+ *
+ * Revision 7.0.1.1 86/10/16 10:54:13 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:14:47 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ * Revision 6.4 83/12/16 13:11:45 lwall
+ * Handled 15 bit random number generators.
+ *
+ * Fixed array overflow bug on multiple zaps.
+ *
+ * Multiple zaps now consolidated to minimize output.
+ *
+ * Tholian jackpot games outlawed under difficulty 15.
+ *
+ * Revision 6.3 83/08/24 11:17:49 lwall
+ * Fixed array overflow bug on multiple zap.
+ *
+ * Revision 6.2 83/08/23 18:06:37 lwall
+ * Added zap command.
+ * Warp -s should now work on dumb terminals
+ * Specifying difficulty >= 40 now just makes it a special game.
+ * SIGTTOU #ifdef'ed.
+ * No-delay read provided as alternative to FIONREAD.
+ * Warp won't report "-1 obsolete" when there are no Enterprises left.
+ * Some high-difficulty tuning.
+ *
+ * Revision 6.1 83/08/17 08:49:03 lwall
+ * Fixed obscure bug in storing UP that caused a %. in CM to occasionally
+ * foist garbage onto the screen.
+ *
+ * Revision 6.0 83/08/08 17:09:26 lwall
+ * New baseline version for net release.
+ *
+ * Revision 5.5 83/08/01 10:59:56 lwall
+ * Cloaking for the Enterprise.
+ * Difficulty now goes to 99, and many activities depending on difficulty
+ * have been adjusted in frequency.
+ * Simplified exit sequence, and reduced dependencies on control
+ * characters. You needn't see the scoreboard if you don't want to.
+ * Hitting i,w,c, or v switches to Enterprise. Hitting p switches to Base.
+ * Excessive use of q is not allowed.
+ * Excessive use of D is not allowed.
+ * Scoreboard may depend on either full name or login name.
+ * Integrated scoreboard lister. Login name now shows up on scoreboard.
+ * "Hidden" startup options are now upper case.
+ * Checks upon startup for no cursor movement, or screen too small.
+ * Checks upon startup that WARPDIR is correctly protected, and that warp
+ * is running setuid. As an additional bonus this prevents root from
+ * running warp, which mucks things up, UN*X be blessed.
+ * All gets's turned into fgets's for safety.
+ * Bonus Enterprises and Bases.
+ * Escalating bonuses for saving Base and Enterprise.
+ * Escalating Enterprise energy.
+ * Turbolasers decrease with distance.
+ * Really smart enemies can see through stars occasionally.
+ * Occasional Tholian jackpot waves. Tholians are a trifle nastier.
+ * Choleric Gorns.
+ * An O or o can miss seeing you. Enemies can avoid a stationary O, o, or X.
+ * Warp 3 enemies and other nastinesses are possible in massacre mode.
+ * Enemies that decide to navigate when they see you can do other things than
+ * just come toward you.
+ * Gorns occasionally launch a salvo for the fun of it.
+ * Only star and enemy explosions can keep the round going now.
+ * Bounces don't always go back to starting spot now.
+ * Better full name processing. USG quirks handled. & substitution also
+ * handled now (whoever dreamed up that one must have been in the middle
+ * of the night before the morning after).
+ * Catch ^D on fgets.
+ * Version number printer.
+ * Less signal catching during debugging.
+ *
+ * Revision 5.4 83/06/24 09:28:38 lwall
+ * 16 bit random number generators are now supported.
+ * Made warp not blow up on a null save file.
+ * Warp now prints E and B before the stars.
+ * Fixed bug which caused torp count to get decremented even when no torp
+ * was launched because of an obstacle.
+ * Put %<n>ld formats where appropriate.
+ * Fixed E: 0 0 bug on refresh.
+ *
+ * Revision 5.3 83/05/24 14:03:10 lwall
+ * Starting RCS
+ *
+ */
+
+#include "INTERN.h"
+#include "warp.h"
+#include "EXTERN.h"
+#include "bang.h"
+#include "init.h"
+#include "intrp.h"
+#include "object.h"
+#include "move.h"
+#include "play.h"
+#include "score.h"
+#include "sig.h"
+#include "term.h"
+#include "them.h"
+#include "us.h"
+#include "util.h"
+#include "version.h"
+#include "weapon.h"
+
+main(argc,argv)
+int argc;
+char *argv[];
+{
+ char tmp, *s, *tcbuf;
+
+ int i;
+
+ FILE *savfil;
+
+#if RANDBITS > 16
+ for (i=100; i; i--)
+ if (rand() >= 65536)
+ goto rand_ok;
+ printf("Recompile with RANDBITS = 15 or 16.\n");
+ exit(1);
+#else
+#if RANDBITS > 15
+ for (i=100; i; i--) {
+ if (rand() >= 32768)
+ goto rand_ok;
+ }
+ printf("Recompile with RANDBITS = 15.\n");
+ exit(1);
+#endif
+#endif
+rand_ok:
+
+#ifdef lint /* to suppress "defined but never used" */
+# ifdef SIGTSTP
+ (void)stop_catcher();
+# endif
+# ifdef SIGCONT
+ (void)cont_catcher();
+# endif
+#endif
+
+ while (--argc > 0 && (*++argv)[0] == '-')
+ for (s = argv[0]+1; *s != '\0'; s++)
+ switch (*s) {
+ case '&':
+ amoebaspec = TRUE;
+ beginner = TRUE;
+ break;
+ case 'A':
+ apolspec = TRUE;
+ beginner = TRUE;
+ break;
+ case 'b':
+ beginner = TRUE;
+ break;
+ case 'C':
+ crushspec = TRUE;
+ beginner = TRUE;
+ break;
+ case 'D':
+ debugging = TRUE;
+#ifdef DEBUGGING
+ debug = atoi(++s);
+#endif
+ s += strlen(s)-1;
+ break;
+ case 'd':
+ s++;
+ if (*s == '=') s++;
+ ismarts = atoi(s);
+ if (ismarts <= 0)
+ ismarts = 1;
+ if (ismarts > 99)
+ ismarts = 99;
+ if (ismarts > 40)
+ beginner = TRUE;
+ s += strlen(s)-1;
+ break;
+ case 'E':
+ klingspec = TRUE;
+ beginner = TRUE;
+ s++;
+ if (*s == '=') s++;
+ inumenemies = atoi(s);
+ s += strlen(s)-1;
+ break;
+ case 'F':
+ friendspec = TRUE;
+ beginner = TRUE;
+ s++;
+ if (*s == '=') s++;
+ inumfriends = atoi(s);
+ s += strlen(s)-1;
+ break;
+ case 'G':
+ gornspec = TRUE;
+ beginner = TRUE;
+ break;
+ case 'l':
+ lowspeed = TRUE;
+ break;
+ case 'm':
+ metakey = TRUE;
+ break;
+ case 'M':
+ massacre = TRUE;
+ break;
+ case 'P':
+ piratespec = TRUE;
+ beginner = TRUE;
+ s++;
+ if (*s == '=') s++;
+ inumpirates = atoi(s);
+ s += strlen(s)-1;
+ break;
+ case 'S':
+ prespec = TRUE;
+ beginner = TRUE;
+ s++;
+ if (*s == '=') s++;
+ if (*s)
+ prescene = atoi(s);
+ else
+ prescene = -1;
+ s += strlen(s)-1;
+ break;
+ case 'R':
+ romspec = TRUE;
+ beginner = TRUE;
+ break;
+ case '*':
+ starspec = TRUE;
+ beginner = TRUE;
+ s++;
+ if (*s == '=') s++;
+ inumstars = atoi(s);
+ s += strlen(s)-1;
+ break;
+ case 's':
+ scorespec = TRUE;
+ break;
+ case 'T':
+ tholspec = TRUE;
+ beginner = TRUE;
+ break;
+ case 'x':
+ experimenting = TRUE;
+ break;
+ case 'v':
+ version();
+ exit(0);
+ break;
+ default:
+ fprintf(stderr,"warp: illegal option %c\n", *s);
+ fprintf(stderr, "Usage: warp -dn -b -x -v -s\n");
+ exit(1);
+ }
+ if (argc != 0) {
+ fprintf(stderr, "Usage: warp -dn -b -x -v -s\n");
+ exit(1);
+ }
+ bang_init();
+ move_init();
+ object_init();
+ play_init();
+ them_init();
+ us_init();
+ util_init();
+ weapon_init();
+
+ tcbuf = malloc(1024);
+ intrp_init(tcbuf);
+
+ if (chdir(warplib) < 0)
+ fprintf(stderr,nocd,warplib);
+
+ term_init();
+
+ term_set(tcbuf);
+ free(tcbuf);
+
+ umask(022); /* mustn't rely on incoming umask--could be 033 which */
+ /* would disable people from running wscore */
+
+ score_init();
+
+ sig_init();
+
+ if (totalscore) {
+ clear();
+ mvaddstr(12,25,"*** restoring saved game ***");
+ roundsleep(1);
+ }
+
+ srand(getpid());
+
+ do {
+ for (keepgoing = TRUE;;) {
+ if (!experimenting) {
+ if ((savfil = fopen(savefilename,"w")) == NULL) {
+ resetty();
+ printf("Can't open savefile\r\n");
+ finalize(1);
+ }
+ fprintf(savfil,
+ "%-8s %10ld, %2d,%5d,%2d,%2d,%3d %c%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 ? '&' : ' '
+ );
+ fprintf(savfil," running on %s, process #%d\n",
+ term+5,getpid());
+ Fclose(savfil);
+ }
+
+ lastscore = totalscore;
+ initialize();
+ play();
+ cumsmarts += smarts;
+ wavescore();
+ if (numents<=0 && numbases<=0)
+ keepgoing = FALSE;
+ if (!keepgoing) break;
+ do {
+ if (experimenting) {
+ mvaddstr(23,15,
+ " [Hit space to continue, 'q' to quit] ");
+ }
+ else {
+ mvaddstr(23,15,
+ "[Hit space to continue, 's' to save, 'q' to quit]");
+ }
+ sleep(1);
+ Fflush(stdout);
+ eat_typeahead();
+ getcmd(&tmp);
+ if (tmp == BREAKCH || tmp == INTRCH) {
+ mvaddstr(23,15,
+ " ");
+ mvaddstr(23,33,
+ "Really quit? ");
+ getcmd(&tmp);
+ if (tmp == 'y' || tmp == 'Y')
+ tmp = 'q';
+ else
+ tmp = 1;
+ }
+ } while (tmp != INTRCH && tmp != BREAKCH && !index(" qQs",tmp));
+ if (tmp != ' ' && tmp != 's') break;
+ if (!beginner && smarts < 20)
+ smarts += 4;
+ else if (!beginner && smarts < 35)
+ smarts += 2;
+ else if (smarts < 99)
+ smarts++;
+ if (tmp == 's') save_game();
+ }
+ score();
+
+ } while (justonemoretime);
+
+ if (!experimenting)
+ unlink(savefilename);
+
+ clear();
+ resetty();
+ exit(0);
+}
diff --git a/warp/warp.doc b/warp/warp.doc
new file mode 100644
index 00000000..bd4c19e4
--- /dev/null
+++ b/warp/warp.doc
@@ -0,0 +1,193 @@
+Warp is a real-time space war game. This means that the enemies will keep
+playing even when you sit still. Another peculiarity is that things which
+blow up can damage other things around them. Universes above a critical
+density may chain react.
+
+The game starts at difficulty 1, and gets more difficult with each
+succeeding wave, up to difficulty 99. You're not likely to get that far.
+(Invoking warp with a -b switch causes the difficulty to increase more
+slowly, but games count only a tenth as much.) The game starts with
+5 Enterprises and 3 Bases, and you get more for surviving long enough.
+The game is over when you run out of Enterprises and Bases.
+
+The object of the game is to get as many points as possible. This is done
+by destroying as many enemies as possible. This is not a trivial task.
+Each wave starts with one Enterprise and one Base, and continues until
+either both the Enterprise and Base are destroyed, or all the enemies
+(including any homing torpedoes) are destroyed. It is possible to abort a
+wave, but you will be penalized for it. The game may be saved between waves.
+
+A -x switch causes any saved game to be ignored, and causes the new game
+not to be saveable. Hence it is possible to run test games without
+invalidating a currently saved game.
+
+The game is played in a 23 x 40 double wrap-around universe. Everybody
+(both you and the enemies) gets the chance to move once every second,
+unless a -l (low-speed) switch was given or you are under 2400 baud, in
+which case it's every two seconds. The following symbols are displayed:
+
+ FRIENDS
+E Enterprise with shields e Enterprise without shields
+C Cloaked E with shields c Cloaked E without shields
+B Base with shields b Base without shields
++ Friendly torpedo M Harry Mudd
+
+ ENEMIES
+K Klingon G Gorn
+R Romulan A Apollo
+ Romulan with cloaking device! & Space Amoeba Nucleus
+T Tholian >,< Planet crusher
+x,X Hostile torpedo o,O Homing torpedo
+P Pirate M Harry Mudd
+
+ MISCELLANEOUS
+* Star @ Inhabited star
+|,-,/,\ Web ~ Protoplasm
+other Friendly Freighter, for now...
+
+The following keys control the DIRECTION of your various actions:
+
+ h or 4 left
+ j or 2 down
+ k or 8 up
+ l or 6 right
+ b or 1 down and left
+ n or 3 down and right
+ y or 7 up and left
+ u or 9 up and right
+
+(You will note that the letters are the same as other visual games, and the
+numbers are for use with a keypad.) By themselves, these keys move either
+the Enterprise or the Base, whichever is the current vessel. When shifted,
+they fire photon torpedoes in the specified direction from the current
+vessel. When used with either the CTRL key or the FUNCT key, phasers
+(turbo-lasers for the Base) are fired in the specified direction. (CTRL
+won't work with numbers, and FUNCT probably doesn't exist on non-TVI
+terminals.) When preceded by an 'a', an attractor beam is fired in the
+specified direction, and when preceded by an 'r', a repulsor beam is fired.
+
+These keys have special functions:
+
+ del or % fire photon torpedoes in every (reasonable) direction
+ s stop all friendly torpedoes
+ S or 0 stop the Enterprise when in warp mode
+ d destruct all friendly torpedoes (quite useful)
+ D destruct the current vessel (commit suicide)
+ i/w switch to Enterprise and put into impulse/warp mode
+ c/v switch to Enterprise and put into cloaking/visible mode
+ p switch to Base (not very mnemonic, but 'b' is taken)
+ o switch from Enterprise to Base, or vice versa
+ z zap explosions (multiple zaps extend further) (E only)
+
+ ^R refresh the screen
+ ^Z suspend the game (on a bsd system)
+ q asks if you want to exit this wave (will not work
+ within 10 cycles of previous q command)
+ Q exit this game (not wave)
+ ? display a summary of these commands
+
+There may be additional commands listed in your terminal's keymap file.
+Unrecognized keystrokes are ignored. IF YOU FORGET ALL THE OTHER COMMANDS,
+REMEMBER "?", which gives you help.
+
+Commands for moving the Enterprise may operate in one of two ways. If it
+is in impulse mode, movement commands affect the position of the ship;
+if it is in warp mode, movement commands affect the velocity instead.
+The Base always moves in impulse mode. Since multiple commands may be
+entered in one turn (if you can type fast enough), it is possible to jump
+over things even in impulse mode. In a crowded universe this may be the
+only way to go.
+
+(Actually, motion commands always change the velocity--the actual motion
+does not occur until the next turn. Impulse mode simply causes the
+velocity to be zeroed out at the end of every turn. Phaser commands, on
+the other hand, are executed immediately. If you want to move and fire a
+phaser, you must wait for the motion to actually occur before typing the
+phaser command, or the phaser fires from your old position. This is a
+feature, not a bug, and is intended to reflect reality. Really.)
+
+If multiple torpedo launching commands are given in a turn, a single torpedo
+is launched with extra velocity. You can thus launch photon torpedoes over
+objects in the way, and get them where you want them quickly. This feature
+works well with the destruct button. Variations on this may be useful
+against the Space Amoeba.
+
+NOTE: Phasers destroy the target by blasting the projected next location of
+the object hit. This means that if the object hit, be it Klingon, Romulan or
+Enterprise, changes velocity in the same turn, it can elude the effect of
+the phaser! (Note that this also means that if you phaser a Klingon or
+torpedo that is about to ram you, you will be phasered as well as he/she/it.
+This can be embarrassing, not to mention deadly.) Smart players move
+immediately upon phasering something at short range, or whenever they
+think they might get phasered (in other words, most of the time).
+
+Objects with larger mass can bounce objects with smaller mass out of the way.
+In a crowded universe the bouncee can bounce quite a way before finding an
+empty place to land. If you let the Tholians fill up the universe with web,
+so that there is no place to bounce to, the Tholians win that wave.
+
+The status line across the top gives the current mode, the number of
+points accumulated this wave, the Enterprise's energy and torpedoes, the
+Base's energy and torpedoes, the number of stars, the number of enemies,
+and the stardate. You will note that nice things happen to your energy levels
+when you put the Enterprise next to the Base, or the Base next to some stars.
+Bad things happen inside an Amoeba.
+
+An object is destroyed when its energy goes negative, either from a direct
+hit, or from the blast of the previous turn's explosions. Enemies and
+stars start with random amounts of energy. High energy enemies can go warp
+2. A Romulan with sufficient energy maintains a cloaking device. Tholians
+spin web, Gorns shoot homing torpedoes, and the Planet Crusher munches
+anything in its way, even Apollo. Apollo won't let you go unless you kill
+him, but he loves you very much and beefs up your shields considerably.
+Both Apollo and the Planet Crusher recharge themselves, so you must hit
+them hard in a single turn to do them in. (Yes, the Planet Crusher must be
+shot in the mouth--he can only die of gluttony--and he blasts out of his
+mouth when he dies.) Tholian web may be crossed only by coasting across it
+in warp mode, or by blasting it (but web blasts extend twice as far as
+normal blasts, so keep your distance). The Space Amoeba sucks energy and
+grows, and you must destroy the nucleus. Somehow. There are at least four
+ways. Phasers won't work on the big ones.
+
+Pirates turn inhabited star systems into uninhabited ones. Even Friendly
+Freighters will take potshots at you if you get them mad enough.
+
+Note that because of the size of the Base's turbo-lasers (the Base does not
+have phasers) they cannot shoot anything next to the Base. (This is why the
+Death Star died!) In part, this is to protect the Enterprise. It also lets
+you shoot over one adjacent star. The Enterprise's phasers will shoot over
+a arbitrary number of adjacent, contiguous stars, including inhabited ones.
+Phasers die away with distance, so don't expect them to kill everything with
+one blow.
+
+While the Enterprise's shields are up (when it is displayed as "E" rather
+than "e"), hits on it count only a fifth as much (or even less if you are
+moving in warp mode). The shields are automatically maintained as long as
+there are more than 500 units of energy for the Enterprise. The Base also
+has shields, which stay up as long as it has at least 1000 units of energy.
+
+Aside from losing energy, the Enterprise can also take damage, either random
+damage from getting blasted, or specific damage when a system is in use
+and breaks down under the load. In place of the score you will see the
+Estimated Time to Repair. Sometimes docking helps to get things fixed faster.
+If you lose both your warp and impulse engines, try the tractors. The
+Base doesn't take damage because it has much more redundancy than the
+Enterprise.
+
+You get points for destroying enemies and hostile torpedoes. At the end of
+a wave, you also get bonus points for saving stars, saving the Enterprise
+and Base, and for having an efficiency rating higher that 0.8. You get
+NEGATIVE bonus points for letting friendly life forms get blown up, and for
+giving up. Bonuses tend to be scaled by the ratio of the number of points
+you got over the number of points you could have got. If you think you are
+done with a wave, but it won't quit, there may be homing torpedoes that you
+haven't destroyed--you must make the universe safe for posterity, you know.
+
+When you have used up your Enterprises and Bases (or quit), your score will
+be posted to the scoreboard. You may see the scoreboard outside of the game
+simply by giving the command "warp -s".
+
+If you get bored, you can always play with some of the undocumented switches
+that are used to test warp. Such funny games go on their own scoreboard.
+For kicks try "warp -x -d50 -C -\& -G -T -E400 -S5" and then go hide. Quick.
+
diff --git a/warp/warp.h b/warp/warp.h
new file mode 100644
index 00000000..4cd4d7e5
--- /dev/null
+++ b/warp/warp.h
@@ -0,0 +1,463 @@
+/* $Header: /cvsroot/src/games/warp/warp.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: warp.h,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.2 86/12/12 17:08:42 lwall
+ * Baseline for net release.
+ *
+ * Revision 7.0.1.1 86/10/16 10:54:26 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:17:55 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+extern int errno;
+
+#include "config.h" /* generated by Configure script */
+
+#include <stdio.h>
+#include <signal.h>
+#include <ctype.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <errno.h>
+
+/* WARPLIB must be readable and writeable by warp, but not by anyone who you
+ * don't trust. In other words, to set up warp so everyone can play and
+ * no one can cheat, give warp a uid of its own and make warp setuid to
+ * that uid. WARPLIB must then NOT be made writeable by the world,
+ * since no attempt is made to encrypt saved games or anything.
+ * (It must be readable by the world, however, due to a strangeness in
+ * access.)
+ */
+
+#define SAVEDIR "./"
+#define NEWSFILE "warp.news"
+#define HELPFILE "warp.doc"
+#define LOCKFILE ".warp.lock"
+#define LOGFILE "warp.log"
+#define SCOREBOARD "warp.top"
+#define LSCOREBOARD "warp.lowtop"
+#define FSCOREBOARD "warp.funtop"
+#define TMPSCOREBOARD "warp.topnew"
+#define WARPMACRO "%X/Kbmap.%{TERM}"
+
+/* warp library */
+#ifndef WARPLIB /* ~ and %l only ("~%l" is permissable) */
+# ifdef PRIVLIB
+# define WARPLIB PRIVLIB
+# else
+# define WARPLIB "/usr/games/warp"
+# endif
+#endif
+
+EXT char *warplib;
+
+#define PERMMAPS 8 /* how many starmaps are permanent */
+#define MAPS 20 /* how many starmaps to choose from */
+ /* (MAPS - PERMMAPS is # of half-gone universes) */
+
+/*
+ * Screen size info, minimum screen size is 23x40 (actually 24x80).
+ * YSIZE and XSIZE should be relatively prime so that a torpedo launched
+ * at an angle will eventually cover the whole screen.
+ * To calculate a new position for something:
+ * new_position = (current_position + delta + ?SIZE00) % ?SIZE
+ * This allows for negative deltas of up to ?SIZE00 (% doesn't work right
+ * on negative numbers).
+ * ?SIZE01, etc. are fudges for efficiency--they already include a delta.
+ */
+
+#define XYSIZE 920
+#define XYSIZEx4 3680
+
+#define YSIZE 23
+#define YSIZE00 2300
+#define YSIZE01 2301
+#define YSIZE99 2299
+
+#define XSIZE 40
+#define XSIZE00 4000
+#define XSIZE01 4001
+#define XSIZE99 3999
+#define XSIZE02 4002
+#define XSIZE98 3998
+#define XSIZE03 4003
+#define XSIZE97 3997
+#define XSIZE08 4008
+#define XSIZE92 3992
+
+EXT char amb[YSIZE][XSIZE];
+
+#ifdef WHOAMI
+# include <whoami.h>
+#endif
+
+#ifndef isalnum
+# define isalnum(c) (isalpha(c) || isdigit(c))
+#endif
+
+#ifdef TERMIO
+# include <termio.h>
+#else
+# include <sgtty.h>
+#endif
+
+#include <sys/timeb.h>
+
+# include <pwd.h>
+
+#define BITSPERBYTE 8
+#define LBUFLEN 512 /* line buffer length */
+
+#ifdef pdp11
+# define CBUFLEN 256 /* command buffer length */
+# define PUSHSIZE 128
+#else
+# define CBUFLEN 512 /* command buffer length */
+# define PUSHSIZE 256
+#endif
+#ifdef pdp11
+# define MAXFILENAME 128
+#else
+# define MAXFILENAME 512
+#endif
+#define FINISHCMD 0177
+
+/* some handy defs */
+
+#define bool char
+#define TRUE (1)
+#define FALSE (0)
+#define Null(t) ((t)0)
+#define Nullch Null(char *)
+#define Nullfp Null(FILE *)
+
+#define Ctl(ch) (ch & 037)
+
+#define strNE(s1,s2) (strcmp(s1,s2))
+#define strEQ(s1,s2) (!strcmp(s1,s2))
+#define strnNE(s1,s2,l) (strncmp(s1,s2,l))
+#define strnEQ(s1,s2,l) (!strncmp(s1,s2,l))
+
+#define sgn(x) ((x) < 0 ? -1 : (x) > 0)
+
+/* Things we can figure out ourselves */
+
+#ifdef SIGPROF
+# define BSD42 /* do we have Berkeley 4.2? */
+#endif
+
+#ifdef FIONREAD
+# define PENDING
+#else
+# ifdef O_NDELAY
+# define PENDING
+# else
+# ifdef RDCHK
+# define PENDING
+# endif
+# endif
+#endif
+
+#define UNLINK(victim) unlink(victim)
+
+/* Valid substitutions for strings marked with % comment are:
+ * %H Host name (yours)
+ * %L Login name (yours)
+ * %N Full name (yours)
+ * %O Original working directory (where you ran warp from)
+ * %X Warp library directory
+ * %~ Home directory
+ * %. Directory containing . files
+ * %$ current process number
+ * %{name} Environment variable "name". %{name-default} form allowed.
+ * %"prompt"
+ * Print prompt and insert what is typed.
+ * %`command`
+ * Insert output of command.
+ * %(test_text=pattern?if_text:else_text)
+ * Substitute if_text if test_text matches pattern, otherwise
+ * substitute else_text. Use != for negated match.
+ * % substitutions are done on test_text, if_text, and else_text.
+ * (Note: %() only works if CONDSUB defined.)
+ */
+
+/* *** System Dependent Stuff *** */
+
+/* NOTE: many of these are defined in the config.h file */
+
+#ifndef ROOTID
+# define ROOTID 0 /* uid of superuser */
+#endif
+
+# define sigset Signal
+# define sigignore(sig) Signal(sig,SIG_IGN)
+
+#ifndef LOGDIRFIELD
+# define LOGDIRFIELD 6 /* Which field (origin 1) is the */
+ /* login directory in /etc/passwd? */
+ /* (If it is not kept in passwd, */
+ /* but getpwnam() returns it, */
+ /* define the symbol GETPWENT) */
+#endif
+#ifndef GCOSFIELD
+# define GCOSFIELD 5
+#endif
+
+/* Undefine any of the following features to save both I and D space */
+/* In general, earlier ones are easier to get along without */
+/* Pdp11's without split I and D may have to undefine them all */
+#define DEBUGGING /* include debugging code */
+#define PUSHBACK /* macros and keymaps using pushback buffer */
+#define CONDSUB /* allow %(cond?text:text) */
+#define BACKTICK /* allow %`command` */
+#define PROMPTTTY /* allow %"prompt" */
+#define GETLOGIN /* use getlogin() routine as backup to environment */
+ /* variables USER or LOGNAME */
+#define TILDENAME /* allow ~logname expansion */
+#define GETWD /* use our getwd() instead of piped in pwd */
+#define SETUIDGID /* substitute eaccess() for access() so that rn */
+ /* can run setuid or setgid */
+ /* if not setuid or setgid, you don't need it */
+#define VERBOSE /* compile in more informative messages */
+#define TERSE /* compile in shorter messages */
+
+/* some dependencies among options */
+
+#ifndef SETUIDGID
+# define eaccess access
+#endif
+
+#ifdef VERBOSE
+# ifdef TERSE
+# define IF(c) if (c)
+# define ELSE else
+# else /* !TERSE */
+# define IF(c)
+# define ELSE
+# endif
+#else /* !VERBOSE */
+# ifndef TERSE
+# define TERSE
+# endif
+# define IF(c) "IF" outside of VERBOSE???
+# define ELSE "ELSE" outside of VERBOSE???
+#endif
+
+#ifdef DEBUGGING
+# define assert(ex) {if (!(ex)){fprintf(stderr,"Assertion failed: file %s, line %d\r\n", __FILE__, __LINE__);sig_catcher(0);}}
+#else
+# define assert(ex) ;
+#endif
+
+#define TCSIZE 512 /* capacity for termcap strings */
+
+/* End of Space Conservation Section */
+
+/* More System Dependencies */
+
+/* preferred shell for use in doshell routine */
+/* ksh or sh would be okay here */
+#ifndef PREFSHELL
+# define PREFSHELL "/bin/csh"
+#endif
+
+/* path to fastest starting shell */
+#ifndef SH
+# define SH "/bin/sh"
+#endif
+
+/* location of macro file */
+#ifndef WARPMACRO
+# ifdef PUSHBACK
+# define WARPMACRO "%./.warpmac"
+# endif
+#endif
+
+/* location of full name */
+#ifndef FULLNAMEFILE
+# ifndef PASSNAMES
+# define FULLNAMEFILE "%./.fullname"
+# endif
+#endif
+
+/* a motd-like file for warp */
+#ifndef WARPNEWSNAME /* % and ~ */
+# define WARPNEWSNAME "%X/warp.news"
+#endif
+
+/* typedefs */
+
+typedef unsigned int MEM_SIZE; /* for passing to malloc */
+
+/* *** end of the machine dependent stuff *** */
+
+/* GLOBAL THINGS */
+
+/* file statistics area */
+
+EXT struct stat filestat;
+
+/* various things of type char */
+
+char *index();
+char *rindex();
+char *getenv();
+char *strcat();
+char *strcpy();
+
+EXT char buf[LBUFLEN+1]; /* general purpose line buffer */
+
+EXT char *cwd INIT(Nullch); /* current working directory */
+
+/* switches */
+
+#ifdef DEBUGGING
+ EXT int debug INIT(0); /* -D */
+# define DEB_FILEXP 64
+#endif
+
+#ifdef VERBOSE
+# ifdef TERSE
+ EXT bool verbose INIT(TRUE); /* +t */
+# endif
+#endif
+
+/* miscellania */
+
+EXT FILE *tmpfp INIT(Nullfp); /* scratch fp */
+
+#define NOMARKING 0
+#define STANDOUT 1
+#define UNDERLINE 2
+
+/* Factored strings */
+
+EXT char nullstr[] INIT("");
+EXT char readerr[] INIT("warp read error");
+EXT char cantopen[] INIT("Can't open %s\r\n");
+
+#ifdef VERBOSE
+ EXT char nocd[] INIT("Can't chdir to directory %s\r\n");
+#else
+ EXT char nocd[] INIT("Can't find %s\r\n");
+#endif
+
+extern int errno;
+
+EXT bool justonemoretime INIT(TRUE);
+EXT bool keepgoing INIT(TRUE);
+
+EXT bool friendspec INIT(FALSE);
+EXT bool piratespec INIT(FALSE);
+EXT bool amoebaspec INIT(FALSE);
+EXT bool starspec INIT(FALSE);
+EXT bool klingspec INIT(FALSE);
+EXT bool apolspec INIT(FALSE);
+EXT bool crushspec INIT(FALSE);
+EXT bool romspec INIT(FALSE);
+EXT bool prespec INIT(FALSE);
+EXT bool tholspec INIT(FALSE);
+EXT bool gornspec INIT(FALSE);
+EXT bool beginner INIT(FALSE);
+EXT bool massacre INIT(FALSE);
+EXT bool lowspeed INIT(FALSE);
+EXT bool debugging INIT(FALSE);
+EXT bool didkill INIT(FALSE);
+EXT bool experimenting INIT(FALSE);
+EXT bool scorespec INIT(FALSE);
+EXT bool metakey INIT(FALSE);
+
+EXT bool bombed_out;
+EXT bool panic INIT(FALSE);
+EXT bool madgorns;
+
+EXT int madfriends;
+
+EXT int inumpirates;
+EXT int numpirates;
+EXT int inumfriends;
+EXT int numfriends;
+EXT int inumamoebas;
+EXT int numamoebas;
+EXT int inumstars;
+EXT int numstars;
+EXT int inumenemies;
+EXT int numenemies;
+EXT int inumroms;
+EXT int inumthols;
+EXT int inumapollos;
+EXT int numapollos;
+EXT int apolloflag;
+EXT int inumcrushes;
+EXT int numcrushes;
+EXT int inumgorns;
+EXT int numgorns;
+EXT int deados;
+EXT int deadmudds;
+EXT int smarts;
+EXT int ismarts INIT(0);
+EXT int numos INIT(0);
+EXT int numxes INIT(0);
+EXT int ient;
+EXT int numents;
+EXT int ibase;
+EXT int numbases;
+EXT int inuminhab;
+EXT int numinhab;
+EXT int wave;
+EXT int cumsmarts;
+EXT int prescene INIT(-1);
+EXT int scandist;
+EXT int antibase;
+EXT int sm35;
+EXT int sm45;
+EXT int sm50;
+EXT int sm55;
+EXT int sm80;
+EXT int sm95;
+EXT int entmax;
+EXT int basemax;
+EXT int enemshields;
+EXT int super;
+EXT int whenok;
+EXT int yamblast;
+EXT int xamblast;
+EXT int ambsize;
+
+EXT char spbuf[512];
+
+char *index(), *ttyname(), *malloc(), *ctime(), *strcpy();
+char *getenv(), cmstore(), *tgoto();
+long atol();
+
+#define Fclose (void)fclose
+#define Fflush (void)fflush
+#define Fgets (void)fgets
+#define Sprintf (void)sprintf
+#define Signal (void)signal
+#define Safecpy (void)safecpy
+#define Cpytill (void)cpytill
+#define Tract (void)tract
+#define Make_object (void)make_object
+#define Read_tty (void)read_tty
diff --git a/warp/warp.man b/warp/warp.man
new file mode 100644
index 00000000..a5b0cedb
--- /dev/null
+++ b/warp/warp.man
@@ -0,0 +1,133 @@
+.TH WARP 6
+.SH NAME
+warp - a real-time space war game
+.SH SYNOPSIS
+.B warp [options]
+.SH DESCRIPTION
+.I Warp
+is a real-time space war game that requires skill and quick thinking.
+"Real-time" in this context means that the enemies keep moving (and shooting)
+even if you don't.
+A unique feature of
+.I warp
+is that blast propagates; it is unhealthy to remain near things that are
+in the process of blowing up.
+If a given universe is above a critical density it may chain react.
+Scoring is like many popular arcade games--there are multiple waves which
+get harder and harder as you go along.
+Nobody has ever maxed out the scoreboard without cheating.
+.PP
+Unlike many space-war games,
+.I warp
+is not simply a shooting gallery.
+Along with phasers and photon torpedoes, you have tractor beams and a cloaking
+device.
+Skill in navigation is important.
+It helps to be schizophrenic, because you must manage an Enterprise and a Base
+simultaneously.
+And enemies do not simply shoot back.
+You can get tailed, absorbed, snuck up upon, hemmed in, rammed, loved to death,
+reprimanded for destroying civilized life, dragged around, robbed, damaged
+and eaten.
+And if you should happen to get bored by the enemies (a trifle unlikely),
+you can always watch the interesting star patterns.
+In fact, you'll have to, since your tactics will depend upon what kind of
+universe you find yourself in.
+.PP
+.I Warp
+is played in a double wraparound universe, i.e. the bottom is connected to the
+top, and the right is connected to the left.
+You need a crt with random cursor addressing and at least 24 lines by 80
+columns.
+For more information about about how to play, simply run
+.I warp
+and say "y" when it asks if you want to see the instructions.
+There is also a single-page command summary that you can get while playing
+by typing a "?".
+.PP
+Command line options include:
+.TP 5
+.B -b
+Put
+.I warp
+into beginner mode.
+Makes the difficulty increase more slowly, but penalizes you for it.
+.TP 5
+.B -d<n>
+Sets the initial difficulty to
+.BR n .
+.TP 5
+.B -l
+Play a low-speed game.
+Changes the basic cycle time from 1 second to 2 seconds.
+This switch is automatically set at baud rates below 2400.
+You may want to set it at higher speeds if your terminal cannot keep up
+with the output.
+(This should never happen on BSD systems, which have an IOCTL call to
+determine output queue length.)
+Because this makes the game easier, a separate scoreboard is kept for
+low-speed games.
+.TP 5
+.B -m
+Terminal has a meta key which turns on the eighth bit. Ordinarily the
+eighth bit is stripped in order to ignore parity.
+Metacharacters will appear to the keymap as prefixed with a ^A, and will
+subsequently have the same effect as a control character, unless otherwise
+mapped.
+.TP 5
+.B -s
+Just prints out the scoreboards and saved games and then exits.
+.TP 5
+.B -v
+Prints out the version number.
+.TP 5
+.B -x
+Play an experimental game.
+This causes
+.I warp
+to ignore any saved game, and disables the ability to save
+the current game.
+Thus you can play around with something or show
+.I warp
+to someone without jeopardizing a currently saved game.
+.SH ENVIRONMENT
+.TP 5
+.B WARPMACRO
+If defined, names a file containing keyboard mappings and macros.
+If not defined, the value %X/Kbmap.%{TERM} is assumed.
+The macro file contains lines of the following form:
+.sp
+<keystroke-sequence> <whitespace> <canonical-keystroke-sequence>
+.sp
+You may use certain % interpolations and ^<letter> control characters.
+For possible % interpolations see warp.h.
+Sequences in the canonical-keystroke-sequence bounded by ^(...^) are
+subject to reinterpretation via the keymap.
+This file has two major uses.
+First, you can set up your commands to use any kind of prefix key your terminal
+might have, or change the key bindings in any other way you choose.
+Second, you can define arbitrary macros, such as this:
+.sp
+# define Corbamite maneuver
+= DDllllll
+.SH AUTHOR
+Larry Wall <lwall@sdcrdcf.UUCP>
+.SH FILES
+~/.fullname, if full names aren't in /etc/passwd
+.SH DIAGNOSTICS
+Generally self-documenting, as they say.
+.SH BUGS
+Addicting.
+At the end of a wave, all you have to do to keep going is hit a space.
+You see the message "Hit space to continue" and automatically hit space.
+About 2 seconds later you remember you wanted to go home, but by then
+it's too late to escape without penalty.
+.PP
+You can't kill a backgrounded
+.I warp
+process directly, because it is running setuid.
+You have to use the killer built in to
+.IR warp .
+.PP
+Now that there is a space amoeba, there ought to be tribbles.
+But it might be too much trouble...
diff --git a/warp/warp.news b/warp/warp.news
new file mode 100644
index 00000000..eef59cdf
--- /dev/null
+++ b/warp/warp.news
@@ -0,0 +1,4 @@
+ *** WARP NEWS ***
+
+Welcome to warp! Please send any gripes, comments, fantastic ideas, etc.
+to lwall@sdcrdcf.uucp (Larry Wall).
diff --git a/warp/weapon.c b/warp/weapon.c
new file mode 100644
index 00000000..024d635c
--- /dev/null
+++ b/warp/weapon.c
@@ -0,0 +1,706 @@
+/* $Header: /cvsroot/src/games/warp/weapon.c,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: weapon.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.2 86/10/20 14:36:33 lwall
+ * Picked some lint.
+ *
+ * Revision 7.0.1.1 86/10/16 10:54:42 lwall
+ * Added Damage. Fixed random bugs.
+ *
+ * Revision 7.0 86/10/08 15:18:08 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+#include "EXTERN.h"
+#include "warp.h"
+#include "bang.h"
+#include "object.h"
+#include "move.h"
+#include "score.h"
+#include "sig.h"
+#include "term.h"
+#include "them.h"
+#include "us.h"
+#include "util.h"
+#include "INTERN.h"
+#include "weapon.h"
+
+void
+weapon_init()
+{
+ ;
+}
+
+void
+fire_torp(from, ydir, xdir)
+Reg1 OBJECT *from;
+Reg3 int ydir;
+Reg4 int xdir;
+{
+ Reg2 OBJECT *to;
+
+ if (from->type == Enemy ||
+ (from == ent && etorp > 0) ||
+ (from == base && btorp > 0)) {
+ to = occupant[(from->posy+from->vely+ydir+YSIZE00)%YSIZE]
+ [(from->posx+from->velx+xdir+XSIZE00)%XSIZE];
+ if (from->type != Enemy || !to || to->vely || to->velx) {
+ if (from->type != Enemy &&
+ (to = isatorp[from==base][ydir+1][xdir+1])) {
+ to->vely += ydir;
+ to->velx += xdir;
+ }
+ else {
+ if (from == ent) {
+ to = make_object(Torp, '+', from->posy,from->posx,
+ from->vely+ydir,from->velx+xdir, 0L, 1L,&root);
+ aretorps++;
+ isatorp[0][ydir+1][xdir+1] = to;
+ etorp--;
+ }
+ else if (from == base) {
+ to = make_object(Torp, '+', from->posy,from->posx,
+ from->vely+ydir,from->velx+xdir, 0L, 1L,&root);
+ aretorps++;
+ isatorp[1][ydir+1][xdir+1] = to;
+ btorp--;
+ }
+ else if (from->image == 'G') {
+ numos++;
+ to = make_object(Torp, 'o', from->posy,from->posx,
+ from->vely+ydir,from->velx+xdir, 100L, 1L,&root);
+ if (madgorns) {
+ possiblescore += 35;
+ to->image = '0';
+ to->mass = 2000;
+ to->energy = 2000;
+ }
+ else if (rand_mod(120)+10 > smarts)
+ possiblescore += 100;
+ else {
+ possiblescore += 200;
+ to->image = 'O';
+ }
+ }
+ else {
+ to = make_object(Torp, 'x', from->posy,from->posx,
+ from->vely+ydir,from->velx+xdir, 0L, 1L,&root);
+ if (rand_mod(160)+10 > smarts)
+ possiblescore += 10;
+ else {
+ possiblescore += 100;
+ to->image = 'X';
+ to->mass = 1000+super*20;
+ numxes++;
+ }
+ }
+ }
+ }
+ }
+}
+
+void
+attack(attackee)
+Reg7 OBJECT *attackee;
+{
+ Reg1 int dx;
+ Reg2 int dy;
+ Reg3 int curx;
+ Reg4 int cury;
+ Reg5 int prob;
+ Reg6 OBJECT *obj;
+ Reg8 bool torps;
+ Reg9 bool webnear = FALSE;
+ Reg10 bool thru_stars;
+ int nukey;
+ int nukex;
+ int nukedist;
+
+ if (attackee) {
+ if (attackee == nuke) {
+ if (amb[attackee->posy][attackee->posx] != '~')
+ return;
+ nukey = nukex = 0;
+ nukedist = 100;
+ }
+ for (dx= -1; dx<=1 ; dx++) {
+ for (dy= -1; dy<=1; dy++) {
+ if (dx||dy) {
+ cury = attackee->posy;
+ curx = attackee->posx;
+ torps = thru_stars = FALSE;
+ if (massacre || madgorns || !rand_mod(53-super) )
+ webnear += rand_mod(2);
+ else
+ webnear = FALSE;
+ for (prob = scandist;prob;prob--) {
+ cury = (cury + dy + YSIZE00) % YSIZE;
+ curx = (curx + dx + XSIZE00) % XSIZE;
+ if (obj = occupant[cury][curx]) {
+ switch (obj->image) {
+ case 'P': case 'K': case 'R': case ' ':
+ pot_shot:
+ if (attackee == nuke) {
+ if (rand_mod(2+scandist-prob) <
+ rand_mod(smarts/40+1))
+ Tract(nuke,dy,dx,rand_mod(3)?1:-1);
+ }
+ if (rand_mod(51 - sm50) <= prob) {
+ switch (obj->strategy||thru_stars?0:
+ rand_mod(ent?4:2)) {
+ case 1: case 2:
+ if (-dy + attackee->vely == obj->vely
+ && -dx + attackee->velx == obj->velx)
+ fire_torp(obj,
+ -dy + attackee->vely,
+ -dx + attackee->velx);
+ else
+ fire_torp(obj,
+ -dy + attackee->vely - obj->vely,
+ -dx + attackee->velx - obj->velx);
+ if (obj->image == ' ')
+ setimage(obj,
+ obj->flags & PIRATE ? 'P' : 'R');
+ break;
+ case 3: {
+ int newspeed =
+ rand_mod(prob<5&&smarts>70?4:3)-1;
+
+ obj->vely = -dy * newspeed;
+ obj->velx = -dx * newspeed;
+ if (newspeed >= 0 &&
+ !rand_mod(82-sm80)) {
+ obj->vely += attackee->vely;
+ obj->velx += attackee->velx;
+ }
+ break;
+ }
+ case 0:
+ if (!torps && obj->energy > 1000) {
+ fire_phaser(obj, -dy, -dx);
+ if (smarts > 40 &&
+ (scandist-prob > 5
+ || attackee==base) &&
+ (massacre || obj->strategy ||
+ rand_mod(2)))
+ while (rand_mod(2))
+ fire_phaser(obj, -dy, -dx);
+ if (obj->image == ' ')
+ setimage(obj,
+ obj->flags&PIRATE ? 'P':'R');
+ }
+ if (obj->strategy) {
+ obj->velx = obj->vely = 0;
+ if (obj->energy < 1000 ||
+ bvely || bvelx)
+ obj->strategy = 0;
+ }
+ else if ((attackee==base ||
+ (cloaking && attackee==ent)
+ ) &&
+ scandist-prob > 5 &&
+ !(rand_mod(
+ ent?antibase*2:antibase)) )
+ obj->strategy = 1;
+ break;
+ }
+ }
+ goto bombout;
+ case 'G':
+ if (thru_stars && obj->strategy < 7)
+ goto bombout;
+ if (attackee == nuke) {
+ if (rand_mod(2+scandist-prob) <
+ rand_mod(smarts/40+1))
+ Tract(nuke,dy,dx,rand_mod(3)?1:-1);
+ goto bombout;
+ }
+ if (obj->strategy) {
+ if (madgorns || !rand_mod(4)) {
+ obj->vely = attackee->vely;
+ obj->velx = attackee->velx;
+ }
+ obj->strategy += (!torps && deados > 10);
+ if (obj->strategy > 4)
+ madgorns = TRUE;
+ if (!torps && obj->strategy > 5) {
+ do {
+ fire_phaser(obj, -dy, -dx);
+ } while (rand_mod(2));
+ }
+ }
+ else if (numgorns >= numenemies-1 &&
+ deados > 15+numgorns*5)
+ obj->strategy = 1;
+ if (madgorns || rand_mod(51 - sm50) <= prob) {
+ if (-dy + attackee->vely == obj->vely
+ && -dx + attackee->velx == obj->velx)
+ fire_torp(obj,
+ -dy + attackee->vely,
+ -dx + attackee->velx);
+ else
+ fire_torp(obj,
+ -dy + attackee->vely - obj->vely,
+ -dx + attackee->velx - obj->velx);
+ }
+ goto bombout;
+ case 'T':
+ if (attackee == nuke) {
+ if (rand_mod(2+scandist-prob) <
+ rand_mod(smarts/40+1))
+ Tract(nuke,dy,dx,rand_mod(3)?1:-1);
+ }
+ if (thru_stars)
+ goto bombout;
+ if (webnear && scandist-prob > 5) {
+ if (massacre || rand_mod(50) < super) {
+ if (!torps && obj->energy > 1000) {
+ fire_phaser(obj, -dy, -dx);
+ while (!rand_mod(57-sm55))
+ fire_phaser(obj, -dy, -dx);
+ }
+ }
+ }
+ goto bombout;
+ case 'C': case 'c':
+ if (thru_stars)
+ goto bombout;
+ break;
+ case 'Q': case 'W': case 'Y': case 'U':
+ case 'I': case 'S': case 'D': case 'H': case 'J':
+ case 'L': case 'Z': case 'V': case 'M': case 'F':
+ if (attackee == nuke) {
+ if (rand_mod(2+scandist-prob) <
+ rand_mod(smarts/40+1))
+ Tract(nuke,dy,dx,rand_mod(3)?1:-1);
+ if (rand_mod(2))
+ goto pot_shot;
+ }
+ if (madfriends > 1000) {
+ madfriends -= 200;
+ goto pot_shot;
+ }
+ /* FALL THROUGH */
+ case '+':
+ if (attackee == nuke) {
+ if (smarts > 70) {
+ if (
+ (obj->posx + obj->velx + XSIZE00)%XSIZE
+ == attackee->posx &&
+ (obj->posy + obj->vely + YSIZE00)%YSIZE
+ == attackee->posy ) {
+ Tract(nuke,dy,dx,-1);
+ }
+ else
+ while (!rand_mod(82-sm80))
+ Tract(nuke,dy,dx,-1);
+ }
+ else if (smarts > 60 ||
+ rand_mod(2+scandist-prob) <
+ rand_mod(smarts/20+1))
+ Tract(nuke,dy,dx,rand_mod(3)?1:-1);
+ }
+ torps = FALSE;
+ thru_stars = FALSE;
+ break;
+ case '|': case '-': case '/': case '\\':
+ if (thru_stars)
+ goto bombout;
+ webnear = (scandist-prob < 3);
+ torps = FALSE;
+ break;
+ case 'x':
+ if (attackee == nuke) {
+ if (rand_mod(2+scandist-prob) <
+ rand_mod(smarts/20+1))
+ Tract(nuke,dy,dx,rand_mod(3)?1:-1);
+ }
+ if (thru_stars)
+ goto bombout;
+ torps = TRUE;
+ break;
+ case 'o': case 'O': case '0':
+ if (attackee == nuke) {
+ if (rand_mod(2+scandist-prob) <
+ rand_mod(smarts/20+1))
+ Tract(nuke,dy,dx,rand_mod(3)?1:-1);
+ }
+ if (thru_stars)
+ goto bombout;
+ torps = TRUE;
+ if (rand_mod(99+3*scandist) < smarts+3*prob) {
+ obj->vely = -dy + attackee->vely;
+ obj->velx = -dx + attackee->velx;
+ if (obj->flags & STATIC) {/* not a mover? */
+ obj->flags &= ~STATIC;
+ obj->prev->next = obj->next;
+ obj->next->prev = obj->prev;
+ root.prev->next = obj;
+ obj->prev = root.prev;
+ root.prev = obj;
+ obj->next = &root;
+ }
+ }
+ if (obj->image != '0')
+ break;
+ /* DROP THROUGH! */
+ case 'X':
+ if (attackee == nuke) {
+ if (rand_mod(2+scandist-prob) <
+ rand_mod(smarts/20+1))
+ Tract(nuke,dy,dx,rand_mod(3)?1:-1);
+ }
+ torps = TRUE;
+ if (thru_stars)
+ goto bombout;
+ if (prob == scandist) {
+ int y, x;
+
+ blast[y=(obj->posy+obj->vely+YSIZE00)%YSIZE]
+ [x=(obj->posx+obj->velx+XSIZE00)%XSIZE]
+ += (obj->image == '0' ? 2000 : 200);
+ yblasted[y] |= 1;
+ xblasted[x] |= 1;
+ blasted = TRUE;
+ }
+ break;
+ case 'A':
+ if (attackee != nuke) {
+ if (scandist-prob>1 && !rand_mod(51-super))
+ Tract(obj,-dy,-dx,1);
+ }
+ /* FALL THROUGH */
+ case '*': case '@':
+ if (attackee == nuke) {
+ if (amb[cury][curx] != '~') {
+ if (scandist-prob < nukedist) {
+ nukedist = scandist-prob;
+ nukey = dy; /* nearest food in */
+ nukex = dx; /* this direction */
+ }
+ if (smarts > 55 && scandist-prob > 8) {
+ if (rand_mod(30+scandist-prob) <
+ rand_mod(smarts/20+1))
+ Tract(nuke,dy,dx,1);
+ }
+ }
+ else if (obj->vely || obj->velx) {
+ Tract(nuke,dy,dx,1); /* for looks */
+ obj->vely = obj->velx = 0;
+ }
+ }
+ if (!thru_stars)
+ if (rand_mod(97-sm95))
+ goto bombout;
+ else
+ thru_stars = TRUE;
+ break;
+ case '<': case '>':
+ if (attackee == nuke) {
+ if ((!dy && scandist-prob < 8) ||
+ rand_mod(2+scandist-prob) <
+ rand_mod(smarts/20+1) ) {
+ nuke->mass += 10000;
+ Tract(nuke,dy,dx,-1);
+ nuke->mass -= 10000;
+ }
+ }
+ goto bombout;
+ case 'E': case 'B':
+ if (attackee == nuke) {
+ if (rand_mod(2+scandist-prob) <
+ rand_mod(smarts/40+1))
+ Tract(nuke,dy,dx,rand_mod(3)?1:-1);
+ }
+ goto bombout;
+ default:
+ goto bombout;
+ }
+ }
+ else {
+ if (thru_stars)
+ goto bombout;
+ }
+ }
+bombout: ; /* end of loop */
+ }
+ }
+ }
+ if (attackee == nuke && nukedist < 100) {/* aim amoeba at nearest */
+ if (nukey < 0) /* free star */
+ nukey = 2;
+ if (nukex < 0)
+ nukex = 2;
+ nuke->strategy = nukey + (nukex << 2);
+ }
+ }
+}
+
+void
+fire_phaser(obj, dy, dx)
+Reg7 OBJECT *obj;
+Reg5 int dy;
+Reg6 int dx;
+{
+ Reg1 int y;
+ Reg2 int x;
+ Reg3 int skipping;
+ Reg4 int size=5000;
+ int decr = 50, oldy, oldx;
+ static char curchar[] = "@* ";
+
+ if (obj == ent)
+ decr = 100;
+ else if (obj == base) {
+ decr = 1000;
+ size = 200;
+ }
+ if (!dy)
+ curchar[2] = '-';
+ else if (!dx)
+ curchar[2] = '!';
+ else if (dy == dx)
+ curchar[2] = '\\';
+ else
+ curchar[2] = '/';
+ if (obj->energy >= decr) {
+ obj->energy -= decr;
+ for (
+ /* initialize */
+ skipping = (obj != base),
+ y = (obj->posy+(obj==base?dy*2:dy)+YSIZE00)%YSIZE,
+ x = (obj->posx+(obj==base?dx*2:dx)+XSIZE00)%XSIZE;
+ /* while */
+ size && (!occupant[y][x]||(skipping && occupant[y][x]->type==Star));
+ /* at end of loop */
+ y = (y+dy+YSIZE00) % YSIZE,
+ x = (x+dx+XSIZE00) % XSIZE,
+ size = size * 3 / 4 ) {
+ move(y+1,x*2,0);
+ beg_qwrite();
+ if (obj == base || obj->image == 'T') {
+ *filler = '@';
+ qwrite();
+ *filler = '#';
+ qwrite();
+ *filler = '~';
+ qwrite();
+ *filler = '%';
+ qwrite();
+ *filler = ':';
+ qwrite();
+ *filler = '@';
+ }
+ else {
+ *filler = size >= 500 ?
+ *curchar : (size >= 50 ?
+ curchar[1] :
+ curchar[2]);
+ }
+ qwrite();
+ if (occupant[y][x])
+ qaddc(occupant[y][x]->image);
+ else {
+ if (numamoebas)
+ qaddc(amb[y][x]);
+ else
+ qaddspace();
+ if (skipping)
+ skipping = 0;
+ }
+ end_qwrite();
+ }
+ if (size) {
+ char img;
+
+ assert(occupant[y][x]);
+ img = occupant[y][x]->image;
+ if (occupant[y][x]->type == Crusher) {
+ if (dy)
+ return;
+ if (dx==(img == '<' ? 1 : -1) ) {
+ occupant[y][x]->image =
+ (occupant[y][x]->velx *= -1) < 0 ? '>' : '<';
+ return;
+ }
+ }
+ else if (occupant[y][x]->flags & FRIENDLY)
+ madfriends += 200;
+ if (numamoebas && amb[y][x] == '~' && smarts % 3 &&
+ (smarts > 70 || rand_mod(smarts) > rand_mod(20)) ) {
+ if (size > 10000)
+ modify_amoeba(y,x,1,'~',10);
+ else if (size > 1000)
+ modify_amoeba(y,x,1,'~',7);
+ else if (size > 50)
+ modify_amoeba(y,x,1,'~',5);
+ else
+ modify_amoeba(y,x,1,'~',2);
+ if (occupant[y][x] == nuke) {
+ nuke->strategy = rand_mod(30);
+ nuke->flags |= COUNTDOWN;
+ }
+ return;
+ }
+ else {
+ move(y+1,x*2,0);
+ beg_qwrite();
+ if (img == ' ') {
+ *filler = occupant[y][x]->flags & PIRATE ? 'P' : 'R';
+ occupant[y][x]->image = *filler;
+ occupant[y][x]->strategy = 0;
+ qwrite();
+ qwrite();
+ }
+ else if (img == 'C' || img == 'c') {
+ cloaked = 0;
+ img += 2;
+ occupant[y][x]->image = img;
+ *filler = img;
+ qwrite();
+ qwrite();
+ }
+ else if (img == 'K' && size > 50)
+ occupant[y][x]->strategy = 0;
+ *filler = '@';
+ qwrite();
+ *filler = '#';
+ qwrite();
+ *filler = '@';
+ qwrite();
+ *filler = '#';
+ qwrite();
+ *filler = '@';
+ qwrite();
+ qaddc(img);
+ end_qwrite();
+ oldy = y;
+ oldx = x;
+ y = (occupant[oldy][oldx]->posy + occupant[oldy][oldx]->vely +
+ YSIZE00) % YSIZE;
+ x = (occupant[oldy][oldx]->posx + occupant[oldy][oldx]->velx +
+ XSIZE00) % XSIZE;
+ if (occupant[y][x] && occupant[y][x]->type == Star) {
+ y = occupant[oldy][oldx]->posy;
+ x = occupant[oldy][oldx]->posx;
+ }
+ if (obj==base)
+ blast[y][x] += size>50 ? 15000 : (size>15 ? 1500 : 150);
+ else if (obj==ent)
+ blast[y][x] += size*4;
+ else if (obj->image=='T')
+ blast[y][x] += 15000;
+ else
+ blast[y][x] += size*smarts/25;
+ yblasted[y] |= 1;
+ xblasted[x] |= 1;
+ blasted = TRUE;
+ }
+ }
+ }
+}
+
+int
+tract(obj, dy, dx, to_or_fro)
+Reg7 OBJECT *obj;
+Reg4 int dy;
+Reg5 int dx;
+int to_or_fro;
+{
+ Reg1 int y;
+ Reg2 int x;
+ Reg3 int size=10;
+ static char ch;
+ Reg6 OBJECT *tractee;
+
+ if (!dy)
+ ch = '|';
+ else if (!dx)
+ ch = '-';
+ else if (dy == dx)
+ ch = '/';
+ else
+ ch = '\\';
+ {
+ for (
+ y = (obj->posy+dy+YSIZE00)%YSIZE,
+ x = (obj->posx+dx+XSIZE00)%XSIZE;
+ size && (!occupant[y][x]);
+ y = (y+dy+YSIZE00) % YSIZE, x = (x+dx+XSIZE00) % XSIZE, size--) {
+ move(y+1,x*2,0);
+ beg_qwrite();
+ *filler = ch;
+ qwrite();
+ qwrite();
+ if (numamoebas)
+ qaddch(amb[y][x]);
+ else
+ qaddspace();
+ end_qwrite();
+ }
+ tractee = occupant[y][x];
+ if (size) {
+ assert(tractee);
+ if (numamoebas && obj != nuke && amb[y][x] == '~') {
+ if (to_or_fro > 0)
+ modify_amoeba(y,x,2,'~',size);
+ else
+ modify_amoeba(y,x,1,' ',size);
+ }
+ if (tractee->type != Web &&
+ (tractee->mass < obj->mass * 5 ||
+ (tractee->type == Crusher && !dx) ) ) {
+ if (tractee == ent) {
+ evely -= dy * to_or_fro;
+ evelx -= dx * to_or_fro;
+ }
+ else if (tractee == base) {
+ bvely -= dy * to_or_fro;
+ bvelx -= dx * to_or_fro;
+ }
+ else {
+ tractee->vely -= dy * to_or_fro;
+ tractee->velx -= dx * to_or_fro;
+ }
+ if (tractee->type == Torp ||
+ tractee->type == Star) {
+ if (tractee->flags & STATIC) { /* not a mover? */
+ tractee->flags &= ~STATIC;
+ tractee->prev->next = tractee->next;
+ tractee->next->prev = tractee->prev;
+ root.prev->next = tractee;
+ tractee->prev = root.prev;
+ root.prev = tractee;
+ tractee->next = &root;
+ }
+ }
+ }
+ else if (tractee->type == Crusher && !dy &&
+ dx==(tractee->image == '<' ? 1 : -1) ) {
+ setimage(tractee, (tractee->velx *= -1) < 0 ? '>' : '<');
+ }
+ if (tractee->mass * 5 > obj->mass)
+ return(1);
+ }
+ }
+ return(0);
+}
diff --git a/warp/weapon.h b/warp/weapon.h
new file mode 100644
index 00000000..b89c015e
--- /dev/null
+++ b/warp/weapon.h
@@ -0,0 +1,40 @@
+/* $Header: /cvsroot/src/games/warp/weapon.h,v 1.1 2020/11/09 23:37:05 kamil Exp $ */
+
+/* $Log: weapon.h,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 86/10/08 15:18:20 lwall
+ * Split into separate files. Added amoebas and pirates.
+ *
+ */
+
+EXT int tractor INIT(0);
+
+EXT int etorp;
+EXT int btorp;
+
+EXT OBJECT *isatorp[2][3][3];
+
+EXT int aretorps;
+
+void fire_torp();
+void attack();
+void fire_phaser();
+int tract();
+void weapon_init();