[comp.sources.sun] v01i002: Sunview/X Mazewar , Part01/06

mcgrew@aramis.rutgers.edu (Charles Mcgrew) (05/06/89)

Submitted-by: kent@wsl.dec.com
Posting-number: Volume 1, Issue 2
Archive-name: mazewar/part01

This is mazewar, that game that we've all seen somewhere or other,
this version will run under sunview and also under X.  

#!/bin/sh
mkdir ./bitmaps
mkdir ./bitmaps/X10
sed 's/^X//' >./Makefile << 'xxFUNNYxx'
XCFLAGS = -O -DBROAD_ADDR=INADDR_BROADCAST -DBSD_43
XOBJS = mazewar.o display.o init.o
XSRCS = mazewar.c display.c init.c
X
X#all: 		sun_mazewar X10_mazewar X11_mazewar mazefind 
Xall: 		X11_mazewar mazefind 
X
Xsun_mazewar: 	${OBJS} winSunView.o
X		${CC} ${CFLAGS} ${OBJS} winSunView.o -o sun_mazewar \
X			-lsuntool -lsunwindow -lpixrect
X
XX10_mazewar:	${OBJS} winX10.o
X		${CC} ${CFLAGS} ${OBJS} winX10.o -o X10_mazewar -lX
X	
XX11_mazewar:	${OBJS} winX11.o
X		${CC} ${CFLAGS} ${OBJS} winX11.o -o X11_mazewar -lXt -lX11
X
Xsaber_o:
X		#load ${CFLAGS} ${OBJS} winX11.o -lXt -lX11
X
Xsaber:		
X		#load ${CFLAGS} mazewar.c display.c init.c winX11.c -lXt -lX11
X	
Xmazefind: 	mazefind.o
X		${CC} ${CFLAGS} mazefind.o -o mazefind
X
Xlint:
X		lint -hcx $(SRCS) winX11.c
X
Xclean:
X		rm -f *.o sun_mazewar X10_mazewar X11_mazewar mazefind
X
Xmazewar.o: mazewar.h
Xdisplay.o: mazewar.h
Xinit.o: mazewar.h
XwinX10.o: mazewar.h
XwinX11.o: mazewar.h
XwinSunView.o: mazewar.h
Xmazefind.o: mazewar.h
xxFUNNYxx
sed 's/^X//' >./README << 'xxFUNNYxx'
XThis is Mazewar for UNIX. It is a direct descendant of the Mazewar
Xplayed at MIT and Xerox PARC, and boasts none of the embellishments found
Xin other such programs. It's basically just run, peek, and shoot; no robot
Xamenuenses, teleport traps, or other such fluff.
X
XBasically, ASDF and space move you around, middle mouse shoots, left and
Xright mouse let you peek around corners. Type Q to quit. Lefties may use
Xthe numeric pad instead of ASDF; on a DEC LK201 keyboard, the 456, row
Xserves for ASDF, and the right cursor arrow is equivalent to the space bar.
XQ quits.
X
XGames are normally begun by broadcasting to find members of a game; if
Xyour system doesn't allow normal users to do broadcasts, you'll have to do
Xsomething like run it setuid root (or whomever) and change findDuke$init.c
Xto do a setuid(getuid()) after the broadcast. The code as distributed does a
Xbroadcast to INADDR_BROADCAST (all 1s); your network might still be configured
Xto use INADDR_ANY (all 0s). The place to change this is in the declaration of
XCFLAGS in the Makefile.
X
XAlso, the 4.3 setsockopt() call is pickier about its arguments when trying to
Xenable broadcasting.  Define BSD_43 in the Makefile to compile the appropriate
Xcode for 4.3 and 4.3-derived systems.  The code that worked on 4.2 is still
Xavailable for systems that might not like the new arguments.
X
XIf you know you don't have broadcast ability and never will, define
XNO_BROADCAST in the Makefile, and that code will be compiled out of init.c;
Xmazefind isn't touched, but it won't do anything useful. In this case, you must
Xspecify a duke host (the name of any host currently in a game will do) or the
Xplayers won't be able to find each other. 
X
XIn each game there is one player who is designated the "duke" and manages
Xthe joining and leaving of other players. When starting a game, if you
Xwish to join a specific game, especially one on a different net, you may
Xspecify the name of the duke host, which will be contacted directly. This
Xhas not been extensively tested. Games across long network delays might be
Xpretty strange...
X
XIf you enjoy this program and keep it, please send a picture post card to me:
X
XChris Kent
XDEC Western Research Lab
X100 Hamilton Avenue
XPalo Alto, CA 94301
X
XInclude your ArpaNet or UUCP mailing address and I'll keep you informed 
Xof updates.
X
XDecember, 1986
X
XBob Brown, Malcolm Slaney, and Mike Yang deserve a long round of applause for
Xhaving ported to new window systems.  We've tested it on a lot of
Xarchitectures, but byte- or bit-order bugs may still be lurking.  Note that
Xthere is conditional code in the X11 driver to not use server-resident bitmaps
Xif your server doesn't do them right (this was designed for the QDSS).
X
XHave fun,
Xchris
X
XAugust, 1988
xxFUNNYxx
sed 's/^X//' >./bitmaps/X10/cup.cur << 'xxFUNNYxx'
X#define coffeeCup_width 16
X#define coffeeCup_height 16
X#define coffeeCup_x_hot 1
X#define coffeeCup_y_hot 12
Xstatic short coffeeCup_bits[] = {
X   0x0080, 0x0700, 0x0800, 0x07c0,
X   0x0020, 0x07f0, 0x3c48, 0x47f8,
X   0x5808, 0x4008, 0x3c08, 0x0818,
X   0x37f6, 0x2002, 0x17fc, 0x0000};
xxFUNNYxx
sed 's/^X//' >./bitmaps/X10/dRat.cur << 'xxFUNNYxx'
X#define deadRat_width 16
X#define deadRat_height 16
X#define deadRat_x_hot 0
X#define deadRat_y_hot 9
Xstatic short deadRat_bits[] = {
X   0x0000, 0x2088, 0x1045, 0x0082,
X   0x0000, 0x1000, 0x2000, 0x4100,
X   0x8220, 0x87ff, 0x8ffa, 0x7ffc,
X   0x0fe8, 0x07c0, 0x0000, 0x0000};
xxFUNNYxx
sed 's/^X//' >./bitmaps/X10/dRatMask.cur << 'xxFUNNYxx'
X#define deadRatMask_width 16
X#define deadRatMask_height 16
Xstatic short deadRatMask_bits[] = {
X   0x6098, 0x71dd, 0x38ef, 0x19c7,
X   0x0082, 0x3000, 0xf100, 0xf3e0,
X   0xc7ff, 0xcfff, 0xffff, 0xfffe,
X   0x7ffc, 0x0fe8, 0x07c0, 0x0000};
xxFUNNYxx
sed 's/^X//' >./bitmaps/X10/icon.ic << 'xxFUNNYxx'
X#define icon_width 48
X#define icon_height 48
Xstatic short icon_bits[] = {
X   0x0000, 0x0000, 0x0000, 0x0041,
X   0x1000, 0x0004, 0x0041, 0x1000,
X   0x0004, 0x0063, 0x1000, 0x0004,
X   0x0055, 0x1000, 0x0004, 0x9e49,
X   0x13cf, 0x69e4, 0x2049, 0x9424,
X   0x9a04, 0x3e41, 0x97e2, 0x0be4,
X   0x2141, 0x9021, 0x0a14, 0xb141,
X   0x5020, 0x0b15, 0xae41, 0x23cf,
X   0x0ae2, 0x0000, 0x0000, 0x0000,
X   0x0000, 0x0000, 0x0000, 0x0000,
X   0x0000, 0x0000, 0x0008, 0x0000,
X   0x0000, 0x0010, 0x0000, 0x0000,
X   0x0020, 0x0000, 0x1fc0, 0x0040,
X   0x0000, 0x0060, 0x0080, 0x0000,
X   0x0050, 0x0100, 0x0000, 0x0048,
X   0x0200, 0x0000, 0x0044, 0x0400,
X   0x0000, 0x0042, 0x0800, 0x0000,
X   0x0041, 0x1000, 0x8000, 0x0040,
X   0x1000, 0x4000, 0x0040, 0xf000,
X   0x3fff, 0x0040, 0x1000, 0x2000,
X   0x0040, 0x1000, 0x2000, 0x0040,
X   0x1000, 0x2000, 0x0040, 0x1000,
X   0x2000, 0x0040, 0x1000, 0x2000,
X   0x0040, 0x1000, 0x2000, 0x0040,
X   0xf000, 0x3fff, 0x0040, 0x1000,
X   0x4000, 0x0040, 0x1000, 0x8000,
X   0x0040, 0x0800, 0x01f0, 0x0041,
X   0x0400, 0x03fa, 0x0042, 0x0200,
X   0x03ff, 0x0044, 0x8100, 0x1ffe,
X   0x0048, 0xc080, 0x23ff, 0x0050,
X   0x8040, 0x2210, 0x0060, 0x0020,
X   0x1000, 0x1fc0, 0x0010, 0x0fc0,
X   0x0000, 0x0008, 0x0020, 0x0000,
X   0x0000, 0x0040, 0x0000, 0x0000,
X   0x0080, 0x0000, 0x0000, 0x0040,
X   0x0000, 0x0000, 0x0000, 0x0000};
xxFUNNYxx
sed 's/^X//' >./bitmaps/X10/iconMask.ic << 'xxFUNNYxx'
X#define icon_mask_width 48
X#define icon_mask_height 48
Xstatic short icon_mask_bits[] = {
X   0x0000, 0x0000, 0x0000, 0xffff,
X   0xffff, 0xffff, 0xffff, 0xffff,
X   0xffff, 0xffff, 0xffff, 0xffff,
X   0xffff, 0xffff, 0xffff, 0xffff,
X   0xffff, 0xffff, 0xffff, 0xffff,
X   0xffff, 0xffff, 0xffff, 0xffff,
X   0xffff, 0xffff, 0xffff, 0xffff,
X   0xffff, 0xffff, 0xffff, 0xffff,
X   0xffff, 0x0000, 0x0000, 0x0000,
X   0x0000, 0x0000, 0x0000, 0x0000,
X   0x0000, 0x0000, 0xfff8, 0xffff,
X   0x1fff, 0xfff8, 0xffff, 0x1fff,
X   0xfff8, 0xffff, 0x1fff, 0xfff8,
X   0xffff, 0x1fff, 0xfff8, 0xffff,
X   0x1fff, 0xfff8, 0xffff, 0x1fff,
X   0xfff8, 0xffff, 0x1fff, 0xfff8,
X   0xffff, 0x1fff, 0xfff8, 0xffff,
X   0x1fff, 0xfff8, 0xffff, 0x1fff,
X   0xfff8, 0xffff, 0x1fff, 0xfff8,
X   0xffff, 0x1fff, 0xfff8, 0xffff,
X   0x1fff, 0xfff8, 0xffff, 0x1fff,
X   0xfff8, 0xffff, 0x1fff, 0xfff8,
X   0xffff, 0x1fff, 0xfff8, 0xffff,
X   0x1fff, 0xfff8, 0xffff, 0x1fff,
X   0xfff8, 0xffff, 0x1fff, 0xfff8,
X   0xffff, 0x1fff, 0xfff8, 0xffff,
X   0x1fff, 0xfff8, 0xffff, 0x1fff,
X   0xfff8, 0xffff, 0x1fff, 0xfff8,
X   0xffff, 0x1fff, 0xfff8, 0xffff,
X   0x1fff, 0xfff8, 0xffff, 0x1fff,
X   0xfff8, 0xffff, 0x1fff, 0xfff8,
X   0xffff, 0x1fff, 0xfff8, 0xffff,
X   0x1fff, 0xfff8, 0xffff, 0x1fff,
X   0xfff8, 0xffff, 0x1fff, 0xfff8,
X   0xffff, 0x1fff, 0xfff8, 0xffff,
X   0x1fff, 0x0000, 0x0000, 0x0000};
xxFUNNYxx
sed 's/^X//' >./bitmaps/X10/rat.cur << 'xxFUNNYxx'
X#define rat_width 16
X#define rat_height 16
X#define rat_x_hot 0
X#define rat_y_hot 6
Xstatic short rat_bits[] = {
X   0x0000, 0x0000, 0x07c0, 0x0fe8,
X   0x0ffc, 0x7ffa, 0x8fff, 0x0842,
X   0x4000, 0x3f00, 0x0080, 0x0100,
X   0x0200, 0x0100, 0x0000, 0x0000};
xxFUNNYxx
sed 's/^X//' >./bitmaps/X10/rat.icon << 'xxFUNNYxx'
X/* Format_version=1, Width=16, Height=16, Depth=1, Valid_bits_per_item=16
X */
X	0x0000,0x0000,0x07C0,0x0FE8,0x0FFC,0x7FFA,0x8FFF,0x8842,
X	0x4000,0x3F00,0x0080,0x0100,0x0200,0x0100,0x0000,0x0000
xxFUNNYxx
sed 's/^X//' >./bitmaps/X10/ratMask.cur << 'xxFUNNYxx'
X#define ratMask_width 16
X#define ratMask_height 16
Xstatic short ratMask_bits[] = {
X   0x0000, 0x07c0, 0x0fe8, 0x1ffc,
X   0x7ffe, 0xffff, 0xffff, 0xdfff,
X   0xfce7, 0xff00, 0x7f80, 0x0380,
X   0x0300, 0x0380, 0x0100, 0x0000};
xxFUNNYxx
sed 's/^X//' >./bitmaps/cup.cur << 'xxFUNNYxx'
X#define cup_width 16
X#define cup_height 16
X#define cup_x_hot 1
X#define cup_y_hot 12
Xstatic char cup_bits[] = {
X   0x80, 0x00, 0x00, 0x07, 0x00, 0x08, 0xc0, 0x07, 0x20, 0x00, 0xf0, 0x07,
X   0x48, 0x3c, 0xf8, 0x47, 0x08, 0x58, 0x08, 0x40, 0x08, 0x3c, 0x18, 0x08,
X   0xf6, 0x37, 0x02, 0x20, 0xfc, 0x17, 0x00, 0x00};
xxFUNNYxx
sed 's/^X//' >./bitmaps/dRat.cur << 'xxFUNNYxx'
X#define dRat_width 16
X#define dRat_height 16
X#define dRat_x_hot 0
X#define dRat_y_hot 9
Xstatic char dRat_bits[] = {
X   0x00, 0x00, 0x88, 0x20, 0x45, 0x10, 0x82, 0x00, 0x00, 0x00, 0x00, 0x10,
X   0x00, 0x20, 0x00, 0x41, 0x20, 0x82, 0xff, 0x87, 0xfa, 0x8f, 0xfc, 0x7f,
X   0xe8, 0x0f, 0xc0, 0x07, 0x00, 0x00, 0x00, 0x00};
xxFUNNYxx
sed 's/^X//' >./bitmaps/dRatMask.cur << 'xxFUNNYxx'
X#define dRatMask_width 16
X#define dRatMask_height 16
X#define dRatMask_x_hot -1
X#define dRatMask_y_hot -1
Xstatic char dRatMask_bits[] = {
X   0x98, 0x60, 0xdd, 0x71, 0xef, 0x38, 0xc7, 0x19, 0x82, 0x00, 0x00, 0x30,
X   0x00, 0xf1, 0xe0, 0xf3, 0xff, 0xc7, 0xff, 0xcf, 0xff, 0xff, 0xfe, 0xff,
X   0xfc, 0x7f, 0xe8, 0x0f, 0xc0, 0x07, 0x00, 0x00};
xxFUNNYxx
sed 's/^X//' >./bitmaps/deadrat.icon << 'xxFUNNYxx'
X{
X    0x0000, 0x2088, 0x1045, 0x0082,
X    0x0000, 0x1000, 0x2000, 0x4100,
X    0x8220, 0x87ff, 0x8ffa, 0x7ffc,
X    0x0fe8, 0x07c0, 0x0000, 0x0000
X}
xxFUNNYxx
sed 's/^X//' >./bitmaps/icon.ic << 'xxFUNNYxx'
X#define icon_width 32
X#define icon_height 32
Xstatic char icon_bits[] = {
X   0x0000, 0x0000, 0x0000, 0x0000, 0x0002, 0x0000, 0x0000, 0x003c,
X   0x0004, 0x0000, 0x0000, 0x0006, 0x0008, 0x0000, 0x0000, 0x0005,
X   0x0010, 0x0000, 0x0080, 0x0004, 0x0020, 0x0000, 0x0040, 0x0004,
X   0x0040, 0x0000, 0x0020, 0x0004, 0x0040, 0x0000, 0x0010, 0x0004,
X   0x00c0, 0x00ff, 0x000f, 0x0004, 0x0040, 0x0000, 0x0008, 0x0004,
X   0x0040, 0x0000, 0x0008, 0x0004, 0x0040, 0x0000, 0x0008, 0x0004,
X   0x0040, 0x0000, 0x0008, 0x0004, 0x0040, 0x0000, 0x0008, 0x0004,
X   0x0040, 0x0000, 0x0008, 0x0004, 0x00c0, 0x00ff, 0x000f, 0x0004,
X   0x0040, 0x0000, 0x0010, 0x0004, 0x0040, 0x0000, 0x0020, 0x0004,
X   0x0020, 0x00f0, 0x0041, 0x0004, 0x0010, 0x00fa, 0x0083, 0x0004,
X   0x0008, 0x00ff, 0x0003, 0x0005, 0x0084, 0x00fe, 0x001f, 0x0006,
X   0x00c2, 0x00ff, 0x0023, 0x003c, 0x0080, 0x0010, 0x0022, 0x0000,
X   0x0000, 0x0000, 0x0010, 0x0000, 0x0000, 0x00c0, 0x000f, 0x0000,
X   0x0000, 0x0020, 0x0000, 0x0000, 0x0000, 0x0040, 0x0000, 0x0000,
X   0x0000, 0x0080, 0x0000, 0x0000, 0x0000, 0x0040, 0x0000, 0x0000,
X   0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000};
xxFUNNYxx
sed 's/^X//' >./bitmaps/maze.icon << 'xxFUNNYxx'
X/* Format_version=1, Width=64, Height=64, Depth=1, Valid_bits_per_item=16
X */
X	0x8888,0x8888,0x8888,0x8888,0x8800,0x0000,0x0000,0x0008,
X	0x2200,0x0000,0x0000,0x0022,0x2284,0x0000,0x0820,0x0022,
X	0x8884,0x0000,0x0820,0x0008,0x88CC,0x71F1,0xC827,0x1608,
X	0x22CC,0x8812,0x2928,0x9922,0x22B4,0x0822,0x2540,0x9022,
X	0x88B4,0x7843,0xE547,0x9008,0x8884,0x8882,0x0548,0x9008,
X	0x2284,0x8902,0x2288,0x9022,0x2284,0x79F1,0xC287,0x9022,
X	0x8800,0x0000,0x0000,0x0008,0x8800,0x0000,0x0000,0x0008,
X	0x2200,0x0000,0x0000,0x0022,0x2222,0x2222,0x2222,0x2222,
X	0x8888,0x8888,0x8888,0x8888,0x9FFF,0xFFFF,0xFFFF,0xFFFC,
X	0x3800,0x0000,0x0000,0x0006,0x3400,0x0000,0x0000,0x0006,
X	0x9200,0x0000,0x0000,0x0004,0x9100,0x0000,0x0000,0x0004,
X	0x3080,0x0000,0x0000,0x0006,0x3040,0x0000,0x0000,0x01FE,
X	0x9020,0x0000,0x0000,0x0304,0x9010,0x0000,0x0000,0x0504,
X	0x3008,0x0000,0x0000,0x0906,0x3004,0x0000,0x0000,0x1106,
X	0x9002,0x0000,0x0000,0x2104,0x9001,0x0000,0x0000,0x4104,
X	0x3000,0x8000,0x0000,0x8106,0x3000,0x4000,0x0001,0x0106,
X	0x9000,0x3FFF,0xFFFE,0x0104,0x9000,0x2000,0x0002,0x0104,
X	0x3000,0x2000,0x0002,0x0106,0x3000,0x2000,0x0002,0x0106,
X	0x9000,0x2000,0x0002,0x0104,0x9000,0x2000,0x0002,0x0104,
X	0x3000,0x2000,0x0002,0x0106,0x3000,0x2000,0x0002,0x0106,
X	0x9000,0x2000,0x0002,0x0104,0x9000,0x2000,0x0002,0x0104,
X	0x3000,0x2000,0x0002,0x0106,0x3000,0x3FFF,0xFFFE,0x0106,
X	0x9000,0x4000,0x0001,0x0104,0x9000,0x8000,0x0000,0x8104,
X	0x3001,0x0000,0x0000,0x4106,0x3002,0x0000,0x0000,0x2106,
X	0x9004,0x0000,0x0000,0x1104,0x9008,0x0001,0xF000,0x0904,
X	0x3010,0x000B,0xF800,0x0506,0x3020,0x001F,0xF800,0x0306,
X	0x9040,0x002F,0xFF00,0x01FC,0x9080,0x007F,0xF880,0x0004,
X	0x3100,0x0021,0x0880,0x0006,0x3200,0x0000,0x0100,0x0006,
X	0x9400,0x0000,0x7E00,0x0004,0x9800,0x0000,0x8000,0x0004,
X	0x3000,0x0000,0x4000,0x0006,0x3000,0x0000,0x2000,0x0006,
X	0x9FFF,0xFFFF,0xFFFF,0xFFFC,0x8888,0x8888,0x8888,0x8888,
X	0x2222,0x2222,0x2222,0x2222,0x2222,0x2222,0x2222,0x2222
xxFUNNYxx
sed 's/^X//' >./bitmaps/rat.cur << 'xxFUNNYxx'
X#define rat_width 16
X#define rat_height 16
X#define rat_x_hot 0
X#define rat_y_hot 6
Xstatic char rat_bits[] = {
X   0x00, 0x00, 0x00, 0x00, 0xc0, 0x07, 0xe8, 0x0f, 0xfc, 0x0f, 0xfa, 0x7f,
X   0xff, 0x8f, 0x42, 0x08, 0x00, 0x40, 0x00, 0x3f, 0x80, 0x00, 0x00, 0x01,
X   0x00, 0x02, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00};
xxFUNNYxx
sed 's/^X//' >./bitmaps/ratMask.cur << 'xxFUNNYxx'
X#define ratMask_width 16
X#define ratMask_height 16
X#define ratMask_x_hot -1
X#define ratMask_y_hot -1
Xstatic char ratMask_bits[] = {
X   0x00, 0x00, 0xc0, 0x07, 0xe8, 0x0f, 0xfc, 0x1f, 0xfe, 0x7f, 0xff, 0xff,
X   0xff, 0xff, 0xff, 0xdf, 0xe7, 0xfc, 0x00, 0xff, 0x80, 0x7f, 0x80, 0x03,
X   0x00, 0x03, 0x80, 0x03, 0x00, 0x01, 0x00, 0x00};
X
xxFUNNYxx
sed 's/^X//' >./mazewar.6 << 'xxFUNNYxx'
X.TH MAZEWAR 6
X.SH NAME
XMazeWar \- distributed rats in a maze
X.SH SYNTAX
X.B /usr/games/mw
X[
X.I 
Xwindow system options
X]
X.SH DESCRIPTION
XThis program implements the age-old game of MazeWar.
XMazeWar first appeared at MIT in the early 1970s, using IMLAC displays and
Xthe ArpaNet network.
XLegend has it that, at one point during that period, MazeWar was banned
Xby DARPA from the ArpaNet because half of all the packets in a given
Xmonth were MazeWar packets flying between Stanford and MIT.
X.PP
XMazeWar appeared again at the Xerox Palo Alto Research Center in the late
X1970's on the Alto, the first personal computer.
XThis version has subsequently been ported to many
Xpersonal machines, and forms the basis for this Unix version.
X.PP
X.I Mw
Xattempts to be as faithful to the original Alto version as possible. 
XThe shape and pictures of the maze are as in the original, and there are
Xno embellishments such as teleport traps or robot amanuenses.
X.SH PLAY
XYou, the player, are a rat in a maze, and the objective is to 
Xfind your opponents and shoot them before they shoot you.
X.PP
XEach of the (up to eight) players in a game may be on a different host. 
XUpon startup, you are asked for the name by which you wish to be known for
Xthe duration of the game, and the name of the ``Duke host''.
XIf you type a bare carriage return to this query, 
X.I mw
Xwill find a game by broadcasting on the local network, and join any game
Xit finds. 
XIf you wish to join a specific game, or a game on another network, or your
Xnetwork doesn't support broadcasting,
Xtype in the name of one of the hosts involved in that game.
XThe program
X.I mazefind
Xwill aid you in finding out what games are currently being played.
X.PP
XOnce in a game, you are presented with the game window.
XThis window is made up of three sections.
XThe upper section is a perspective view of your view forward. 
XBy pressing
Xthe left or right mouse buttons, you may peek to the left or right around
Xcorners.
X.PP
XThe middle section of the window is a top view of the maze, showing your
Xcurrent position and heading in the maze. 
XYou move around the maze by using the following keys:
X.sp
X.ta .6i
X.nf
XA	About face; flip end\-for\-end
XS	Turn 90 degrees left
XD	Move forward one cell
XF	Turn 90 degrees right
X<space>	Move backward one cell
XQ	Quit
X.fi
X.sp
XFor left\-handers, there are equivalents on the numeric keypad. 
XOn the DEC LK201 keyboard, the `4', `5', `6', `,', and right cursor arrow
Xkeys perform the equivalent operations.
X.PP
XThe lower section of the window shows the names and scores of the other
Xplayers in the game.
XWhen you sight another rat, that rat's score line is highlighted.
XShoot by pressing the middle mouse button.
XWhen you are shot at, the mouse cursor changes from a rat to a dead rat,
Xand you have one second to move out of the way of the shot or shoot back
Xor both.
XA shot costs one point; getting hit costs five points; hitting someone
Xadds ten points.
XWhen you are hit, the screen flashes and you are transported to another
Xsection of the maze.
X.PP
XIf your window system supports it, when you iconify the game window, it
Xwill let you know when someone joins the game or shoots at you (by
Xflashing, in most cases).
XThis way, you can be notified whenever someone else is interested in
Xwasting some time, by always leaving a game around.
X.SH "SEE ALSO"
Xmazefind(6)
X.SH AUTHOR
XChristopher A. Kent
xxFUNNYxx
sed 's/^X//' >./mazefind.c << 'xxFUNNYxx'
X/* $Header: mazefind.c,v 1.5 88/09/07 11:23:42 kent Exp $ */
X
X/* 
X * mazefind.c - find ongoing mazewar games
X * 
X * Author:	Christopher A. Kent
X * 		Western Research Laboratory
X * 		Digital Equipment Corporation
X * Date:	Thu Dec  4 1986
X */
X
X/***********************************************************
XCopyright 1986 by Digital Equipment Corporation, Maynard, Massachusetts,
X
X                        All Rights Reserved
X
XPermission to use, copy, modify, and distribute this software and its 
Xdocumentation for any purpose and without fee is hereby granted, 
Xprovided that the above copyright notice appear in all copies and that
Xboth that copyright notice and this permission notice appear in 
Xsupporting documentation, and that the names of Digital not be
Xused in advertising or publicity pertaining to disstribution of the
Xsoftware without specific, written prior permission.  
X
XDIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
XALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
XDIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
XANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
XWHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
XARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
XSOFTWARE.
X
X******************************************************************/
X
X/*
X * $Log:	mazefind.c,v $
X * Revision 1.5  88/09/07  11:23:42  kent
X * 
X * 
X * Revision 1.4  88/08/25  09:57:53  kent
X * 
X * 
X * Revision 1.3  88/06/15  16:36:20  kent
X * 
X * 
X * Revision 1.2  87/03/31  14:42:26  kent
X * Portability considerations, especially byteswapping to/from the net.
X * 
X * Revision 1.1  86/12/04  17:19:31  kent
X * Initial revision
X * 
X */
X
Xstatic char rcs_ident[] = "$Header: mazefind.c,v 1.5 88/09/07 11:23:42 kent Exp $";
X
X#include <sys/types.h>
X#include <sys/socket.h>
X#include <sys/time.h>
X
X#include <netinet/in.h>
X
X#include <errno.h>
X#include <netdb.h>
X#include <stdio.h>
X#include <strings.h>
X
X#include "mazewar.h"
X
Xstruct answer {
X	Sockaddr	source;
X	int		srclen;
X	RatPacket	packet;
X};
X
XBoolean	FoundOne = FALSE;
X
X/* 
X * Broadcast to check out all the games on the net. This is basically
X * findDuke() from init.c.
X */
X
Xmain()
X{
X	register int	i;
X	int		cnt = 0;
X	Sockaddr	rmtAddr;
X	struct	timeval	timeout;
X	RatPacket	*b = (RatPacket *) malloc(sizeof(RatPacket));
X	struct answer	answer;
X	int		fds, fd;
X	int		ret, cc;
X	int		mazePort;
X	struct servent	*mazeService;
X	char		buf[128];
X	Boolean		duke(), freeSlot();
X	struct in_addr	inet_makeaddr();
X	Sockaddr	*resolveHost();
X
X	fd = socket(AF_INET, SOCK_DGRAM, 0);
X	if (fd < 0)
X		MFError("can't get socket");
X#ifdef	SO_BROADCAST
X#ifdef	BSD_43
X	{
X	int	one = 1;
X
X	if (setsockopt(fd, SOL_SOCKET, SO_BROADCAST, &one, sizeof one) < 0)
X		MFError("can't get broadcast permission");
X	}
X#else	BSD_43
X	if (setsockopt(fd, SOL_SOCKET, SO_BROADCAST, NULL, 0) < 0)
X		MFError("can't get broadcast permission");
X#endif	BSD_43
X#endif	SO_BROADCAST
X
X	mazeService = getservbyname(MAZESERVICE, "udp");
X	if (mazeService != (struct servent *) NULL)
X		mazePort = mazeService->s_port;
X	else
X		mazePort = htons(MAZEPORT);
X
X	gethostname(buf, sizeof(buf));
X	bcopy((char *)resolveHost(buf), (char *) &rmtAddr, sizeof(rmtAddr));
X	rmtAddr.sin_addr = inet_makeaddr(inet_netof(rmtAddr.sin_addr),
X					BROAD_ADDR);	/* from Makefile */
X	rmtAddr.sin_port = mazePort;
X
X	setupSurvey(b);
X	ConvertOutgoing(b);
X	if (sendto(fd, (char *) b, sizeof(*b), 0, &rmtAddr, sizeof(rmtAddr)) < 0)
X		MFError("survey");
X
X	while (1) {
X		fds = (1<<fd);
X		timeout.tv_sec = 5;
X		timeout.tv_usec = 0;
X		ret = select(32, &fds, NULL, NULL, &timeout);
X		if (ret < 0)
X			MFError("select");
X		if (ret == 0)
X			break;
X		answer.srclen = sizeof(Sockaddr);
X		cc = recvfrom(fd, &answer.packet, sizeof(RatPacket),
X			0, &answer.source, &answer.srclen);
X		if (cc < 0)
X			MFError("recv");
X		ConvertIncoming(&answer.packet);
X		if (answer.packet.type != RAT_STATUS)
X			continue;
X		if (!duke(&answer)) {
X			RatStatus	rs;
X
X			rs = (RatStatus) &answer.packet.body;
X			setupSurvey(b);
X			ConvertOutgoing(b);
X			if (rs->rats[rs->dukeRat].addr.sin_port == mazePort)
X				continue;	/* will answer himself */
X				
X			if (sendto(fd, b, sizeof(*b), 0,
X				   &rs->rats[rs->dukeRat].addr,
X				   sizeof(rs->rats[rs->dukeRat].addr)) < 0)
X				MFError("resend");
X			continue;
X		} else
X			printAnswer(&answer);
X	}
X	if (FoundOne == FALSE)
X		printf("No one's playing now\n");
X	exit(0);
X}
X
XMFError(s)
Xchar *s;
X{
X	fprintf(stderr, "mazefind: %s\n", s);
X	perror("mazefind");
X	exit(-1);
X}
X
X/* 
X * Fill in the RAT_SURVEY packet.
X */
X
XsetupSurvey(b)
XRatPacket *b;
X{
X	RatNew	ratSurvey;
X
X	b->type = RAT_SURVEY;
X	ratSurvey = (RatNew) &b->body;
X	ratSurvey->pass = RAT_PASSWORD;
X}
X
X/* 
X * Check if this guy's the duke of his game.
X */
X
XBoolean
Xduke(a)
Xstruct answer	*a;
X{
X	RatStatus	test;
X
X	test = (RatStatus) &a->packet.body;
X	return !bcmp((char *) &test->rats[test->dukeRat].addr.sin_addr,
X			(char *) &a->source.sin_addr, sizeof(struct in_addr));
X}
X
X/* 
X * Decode an answer packet.
X */
X
XprintAnswer(a)
Xstruct answer	*a;
X{
X	RatStatus	status;
X	RatId		ratId;
X	RatInfo		rat;
X	struct hostent	*host;
X
X	status = (RatStatus) &a->packet.body;
X	
X	if (FoundOne == FALSE) {
X		FoundOne = TRUE;
X		printf("Current game(s):\n");
X		printf("\t%-20s\t%s\t\thost\n", "Name", "score");
X	} else
X		printf("\n");
X	for(ratId = 0; ratId < MAXRATS; ratId++) {
X		rat = (RatInfo) &status->rats[ratId];
X		if (rat->playing == FALSE)
X			continue;
X
X		if (ratId == status->dukeRat)
X			printf("duke");
X		printf("\t");
X
X		printf("%-20s\t%d\t\t", rat->name, rat->score);
X
X		host = gethostbyaddr(&rat->addr.sin_addr,
X				sizeof(struct in_addr), AF_INET);
X		if (host != NULL)
X			printf("%s\n", host->h_name);
X		else
X			printf("%s\n", inet_ntoa(rat->addr.sin_addr));
X	}
X}
X
X/*
X * Resolve the specified host name into an internet address.  The "name" may
X * be either a character string name, or an address in the form a.b.c.d where
X * the pieces are octal, decimal, or hex numbers.  Returns a pointer to a
X * sockaddr_in struct (note this structure is statically allocated and must
X * be copied), or NULL if the name is unknown.
X */
X
XSockaddr *
XresolveHost(name)
Xregister char *name;
X{
X	register struct hostent *fhost;
X	struct in_addr fadd;
X	static Sockaddr sa;
X
X	if ((fhost = gethostbyname(name)) != NULL) {
X		sa.sin_family = fhost->h_addrtype;
X		sa.sin_port = 0;
X		bcopy(fhost->h_addr, &sa.sin_addr, fhost->h_length);
X	} else {
X		fadd.s_addr = inet_addr(name);
X		if (fadd.s_addr != -1) {
X			sa.sin_family = AF_INET;	/* grot */
X			sa.sin_port = 0;
X			sa.sin_addr.s_addr = fadd.s_addr;
X		} else
X			return(NULL);
X	}
X	return(&sa);
X}
X
X/* 
X * Convert the contents of a packet to network order before sending.
X */
X
XConvertOutgoing(p)
XRatPacket *p;
X{
X	char		buf[64];
X	RatId		ratId;
X	RatLocation	ratLoc;
X	RatKill		ratKill;
X	RatDead		ratDead;
X	RatStatus	ratStatus;
X	RatNew		ratNew;
X	RatGone		ratGone;
X	RatQuery	ratQuery;
X	RatAlive	ratAlive;
X	RatMove		ratMove;
X
X	switch(p->type) {
X	case RAT_LOCATION:
X		ratLoc = (RatLocation) &p->body;
X		ratLoc->ratId = htonl(ratLoc->ratId);
X		ratLoc->xLoc =  htons(ratLoc->xLoc);
X		ratLoc->yLoc =  htons(ratLoc->yLoc);
X		ratLoc->dir =   htons(ratLoc->dir);
X		ratLoc->score = htonl(ratLoc->score);
X		break;
X
X	case RAT_KILL:
X		ratKill = (RatKill) &p->body;
X		ratKill->ratId = htonl(ratKill->ratId);
X		ratKill->xLoc  = htons(ratKill->xLoc);
X		ratKill->yLoc  = htons(ratKill->yLoc);
X		ratKill->dir   = htons(ratKill->dir);
X		break;
X
X	case RAT_DEAD:
X		ratDead = (RatDead) &p->body;
X		ratDead->ratId = htonl(ratDead->ratId);
X		ratDead->killedBy = htonl(ratDead->killedBy);
X		break;
X
X	case RAT_STATUS:
X		ratStatus = (RatStatus) &p->body;
X		ratStatus->dukeRat = htonl(ratStatus->dukeRat);
X		for (ratId = 0; ratId < MAXRATS; ratId++) {
X			RatInfo	ratInfo;
X
X			ratInfo = &ratStatus->rats[ratId];
X			ratInfo->playing = htons(ratInfo->playing);
X			ratInfo->xLoc = htons(ratInfo->xLoc);
X			ratInfo->yLoc = htons(ratInfo->yLoc);
X			ratInfo->dir = htons(ratInfo->dir);
X			ratInfo->score = htonl(ratInfo->score);
X			ratInfo->addr.sin_family =
X				ntohs(ratInfo->addr.sin_family);
X			/* don't touch address or name */
X		}
X		break;
X
X	case RAT_NEW:
X		ratNew = (RatNew) &p->body;
X		ratNew->pass = htons(ratNew->pass);
X		ratNew->xLoc = htons(ratNew->xLoc);
X		ratNew->yLoc = htons(ratNew->yLoc);
X		ratNew->dir  = htons(ratNew->dir);
X		ratNew->addr.sin_family =
X			htons(ratNew->addr.sin_family);
X		/* don't touch address or name */
X		break;
X
X	case RAT_GOING:
X		ratGone = (RatGone) &p->body;
X		ratGone->ratId = htonl(ratGone->ratId);
X		break;
X
X	case RAT_QUERY:
X		ratQuery = (RatQuery) &p->body;
X		ratQuery->ratId = htonl(ratQuery->ratId);
X		break;
X
X	case RAT_ALIVE:
X		ratAlive = (RatAlive) &p->body;
X		ratAlive->ratId = htonl(ratAlive->ratId);
X		break;
X
X	case RAT_SURVEY:
X		ratNew = (RatNew) &p->body;
X		ratNew->pass = htons(ratNew->pass);
X		ratNew->xLoc = htons(ratNew->xLoc);
X		ratNew->yLoc = htons(ratNew->yLoc);
X		ratNew->dir  = htons(ratNew->dir);
X		/* don't touch address or name */
X		break;
X
X	case RAT_MOVE:
X		ratMove = (RatMove) &p->body;
X		ratMove->ratId = htonl(ratMove->ratId);
X		break;
X
X	default:
X		sprintf(buf, "ConvertOutgoing bad type %d (%d)",
X			p->type, htons(p->type));
X		MFError(buf);
X	}
X	p->type = htonl(p->type);
X}
X
X/* 
X * Convert the contents of a packet to host order after ConvertIncoming.
X */
X
XConvertIncoming(p)
XRatPacket *p;
X{
X	char		buf[64];
X	RatId		ratId;
X	RatLocation	ratLoc;
X	RatKill		ratKill;
X	RatDead		ratDead;
X	RatStatus	ratStatus;
X	RatNew		ratNew;
X	RatGone		ratGone;
X	RatQuery	ratQuery;
X	RatAlive	ratAlive;
X	RatMove		ratMove;
X
X	p->type = ntohl(p->type);
X	switch(p->type) {
X	case RAT_LOCATION:
X		ratLoc = (RatLocation) &p->body;
X		ratLoc->ratId = ntohl(ratLoc->ratId);
X		ratLoc->xLoc =  ntohs(ratLoc->xLoc);
X		ratLoc->yLoc =  ntohs(ratLoc->yLoc);
X		ratLoc->dir =   ntohs(ratLoc->dir);
X		ratLoc->score = ntohl(ratLoc->score);
X		break;
X
X	case RAT_KILL:
X		ratKill = (RatKill) &p->body;
X		ratKill->ratId = ntohl(ratKill->ratId);
X		ratKill->xLoc  = ntohs(ratKill->xLoc);
X		ratKill->yLoc  = ntohs(ratKill->yLoc);
X		ratKill->dir   = ntohs(ratKill->dir);
X		break;
X
X	case RAT_DEAD:
X		ratDead = (RatDead) &p->body;
X		ratDead->ratId = ntohl(ratDead->ratId);
X		ratDead->killedBy = ntohl(ratDead->killedBy);
X		break;
X
X	case RAT_STATUS:
X		ratStatus = (RatStatus) &p->body;
X		ratStatus->dukeRat = ntohl(ratStatus->dukeRat);
X		for (ratId = 0; ratId < MAXRATS; ratId++) {
X			RatInfo	ratInfo;
X
X			ratInfo = &ratStatus->rats[ratId];
X			ratInfo->playing = ntohs(ratInfo->playing);
X			ratInfo->xLoc = ntohs(ratInfo->xLoc);
X			ratInfo->yLoc = ntohs(ratInfo->yLoc);
X			ratInfo->dir = ntohs(ratInfo->dir);
X			ratInfo->score = ntohl(ratInfo->score);
X			ratInfo->addr.sin_family =
X				ntohs(ratInfo->addr.sin_family);
X			/* don't touch address or name */
X		}
X		break;
X
X	case RAT_NEW:
X		ratNew = (RatNew) &p->body;
X		ratNew->pass = ntohs(ratNew->pass);
X		ratNew->xLoc = ntohs(ratNew->xLoc);
X		ratNew->yLoc = ntohs(ratNew->yLoc);
X		ratNew->dir  = ntohs(ratNew->dir);
X		ratNew->addr.sin_family =
X			ntohs(ratNew->addr.sin_family);
X		/* don't touch address or name */
X		break;
X
X	case RAT_GOING:
X		ratGone = (RatGone) &p->body;
X		ratGone->ratId = ntohl(ratGone->ratId);
X		break;
X
X	case RAT_QUERY:
X		ratQuery = (RatQuery) &p->body;
X		ratQuery->ratId = ntohl(ratQuery->ratId);
X		break;
X
X	case RAT_ALIVE:
X		ratAlive = (RatAlive) &p->body;
X		ratAlive->ratId = ntohl(ratAlive->ratId);
X		break;
X
X	case RAT_SURVEY:
X		ratNew = (RatNew) &p->body;
X		ratNew->pass = ntohs(ratNew->pass);
X		ratNew->xLoc = ntohs(ratNew->xLoc);
X		ratNew->yLoc = ntohs(ratNew->yLoc);
X		ratNew->dir  = ntohs(ratNew->dir);
X		/* don't touch address or name */
X		break;
X
X	case RAT_MOVE:
X		ratMove = (RatMove) &p->body;
X		ratMove->ratId = ntohl(ratMove->ratId);
X		break;
X
X	default:
X		sprintf(buf, "ConvertIncoming bad type %d (%d)",
X			p->type, ntohs(p->type));
X		MFError(buf);
X	}
X}
X
xxFUNNYxx