[net.sources.games] PC/IX Hack: Repost Part 4

peterb@pbear.UUCP (06/25/85)

#!/bin/sh
# This is a shell archive, meaning:
# 1. Remove everything above the #!/bin/sh line.
# 2. Save the resulting text in a file.
# 3. Execute the file with /bin/sh (not csh) to create the files:
#	hack.monst.c
#	hack.move.c
#	hack.name.h
#	hack.office.c
#	hack.pri.c
#	hack.rip.c
#	hack.save.c
#	hack.savelev.c
#	hack.shk.c
# This archive created: Tue Jun 25 12:42:58 1985
export PATH; PATH=/bin:$PATH
echo shar: extracting "'hack.monst.c'" '(3125 characters)'
if test -f 'hack.monst.c'
then
	echo shar: over-writing existing file "'hack.monst.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.monst.c'
X/*
X * Hack.monst.c
X */
X
X#include "hack.h"
X#include "hack.dog.h"
X
X/*
X * Unfortunately the syntax for structure initialization is
X * different on VAX and 11/45. Define VAX to get the VAX syntax
X */
X
X#define VAX
X
X#ifdef VAX
X
X#define	SOSEP	{
X#define	SCSEP	}
X#define GOSEP
X#define	GMSEP
X#define	GCSEP
X
X#else
X
X#define	SOSEP
X#define	SCSEP
X#define	GOSEP	{
X#define	GMSEP	},{
X#define	GCSEP	}
X
X#endif VAX
X
Xstruct permonst mon[8][7]={
X	GOSEP
X	SOSEP "bat",		'B',1,22,8,1,4,0 SCSEP,
X	SOSEP "gnome",		'G',1,6,5,1,6,0 SCSEP,
X	SOSEP "hobgoblin",	'H',1,9,5,1,8,0 SCSEP,
X	SOSEP "jackal",		'J',0,12,7,1,2,0 SCSEP,
X	SOSEP "kobold",		'K',1,6,7,1,4,0 SCSEP,
X	SOSEP "leprechaun",	'L',1,15,8,1,5,0 SCSEP,
X	SOSEP "giant rat",	'r',0,12,7,1,3,0 SCSEP,
X	GMSEP
X	SOSEP "acid blob",	'a',2,3,8,0,0,0 SCSEP,
X	SOSEP "floating eye",	'E',2,1,9,0,0,0 SCSEP,
X	SOSEP "homunculus",	'h',2,6,6,1,3,0 SCSEP,
X	SOSEP "imp",		'i',2,6,2,1,4,0 SCSEP,
X	SOSEP "orc",		'O',2,9,6,1,8,0 SCSEP,
X	SOSEP "yellow light",	'y',3,15,0,0,0,0 SCSEP,
X	SOSEP "zombie",		'Z',2,6,8,1,8,0 SCSEP,
X	GMSEP
X	SOSEP "giant ant",	'A',3,18,3,1,6,0 SCSEP,
X	SOSEP "fog cloud",	'f',3,1,0,1,6,0 SCSEP,
X	SOSEP "nymph",		'N',3,12,9,1,4,0 SCSEP,
X	SOSEP "piercer",	'p',3,1,3,2,6,0 SCSEP,
X	SOSEP "quasit",		'Q',3,15,3,1,4,0 SCSEP,
X	SOSEP "quivering blob",	'q',3,1,8,1,8,0 SCSEP,
X	SOSEP "violet fungi",	'v',3,1,7,1,4,0 SCSEP,
X	GMSEP
X	SOSEP "giant beetle",	'b',4,6,4,3,4,0 SCSEP,
X	SOSEP "centaur",	'C',4,18,4,1,6,0 SCSEP,
X	SOSEP "cockatrice",	'c',4,6,6,1,3,0 SCSEP,
X	SOSEP "gelatinous cube",'g',4,6,8,2,4,0 SCSEP,
X	SOSEP "jaguar",		'j',4,15,6,1,8,0 SCSEP,
X	SOSEP "killer bee",	'k',4,6,4,2,4,0 SCSEP,
X	SOSEP "snake",		'S',4,15,3,1,6,0 SCSEP,
X	GMSEP
X	SOSEP "freezing sphere",'F',2,13,4,0,0,0 SCSEP,
X	SOSEP "owlbear",	'o',5,12,5,2,6,0 SCSEP,
X	SOSEP "rust monster",	'R',5,18,3,0,0,0 SCSEP,
X	SOSEP "giant scorpion",	's',5,15,3,1,4,0 SCSEP,
X	SOSEP "teleporter",	't',5,3,5,1,7,0 SCSEP,
X	SOSEP "wraith",		'W',5,12,5,1,6,0 SCSEP,
X	SOSEP "long worm",	'w',6,3,5,2,5,0 SCSEP,
X	GMSEP
X	SOSEP "large dog",	'd',6,15,4,2,4,0 SCSEP,
X	SOSEP "leocrotta",	'l',6,18,4,3,6,0 SCSEP,
X	SOSEP "mimic",		'M',7,3,7,3,4,0 SCSEP,
X	SOSEP "minotaur",	'm',6,12,6,2,8,0 SCSEP,
X	SOSEP "troll",		'T',7,12,4,2,6,0 SCSEP,
X	SOSEP "ugod",		'u',6,11,5,1,10,0 SCSEP,
X	SOSEP "yeti",		'Y',5,15,6,1,6,0 SCSEP,
X	GMSEP
X	SOSEP "invisible stalker",'I',8,12,3,4,4,0 SCSEP,
X	SOSEP "umber hulk",	'U',9,6,2,2,14,0 SCSEP,
X	SOSEP "vampire",	'V',8,12,1,1,6,0 SCSEP,
X	SOSEP "xorn",		'X',8,9,-2,4,6,0 SCSEP,
X	SOSEP "xerp",		'x',7,6,3,2,4,0 SCSEP,
X	SOSEP "zelomp",		'z',9,8,3,3,6,0 SCSEP,
X	SOSEP "chameleon",	':',6,5,6,4,2,0 SCSEP,
X	GMSEP
X	SOSEP "dragon",		'D',20,9,-1,3,8,0 SCSEP,
X	SOSEP "ettin",		'e',10,12,3,2,8,0 SCSEP,
X	SOSEP "lurker above",	'\'',10,3,3,0,0,0 SCSEP,
X	SOSEP "neo-otyugh",	'n',11,6,0,1,3,0 SCSEP,
X	SOSEP "trapper",	',',12,3,3,0,0,0 SCSEP,
X	SOSEP "purple worm",	'P',20,9,-1,2,8,0 SCSEP,
X	SOSEP "demon",		'&',14,9,-4,1,6,0 SCSEP
X	GCSEP
X};
Xstruct permonst /* _mon={0,0,0,0,0,0,0,0},*/
X	li_dog={"little dog",	'd',2,18,6,1,6,sizeof(struct edog)},
X		dog={"dog",	'd',4,16,5,1,6,sizeof(struct edog)},
X	la_dog={"large dog",	'd',6,15,4,2,4,sizeof(struct edog)};
SHAR_EOF
if test 3125 -ne "`wc -c 'hack.monst.c'`"
then
	echo shar: error transmitting "'hack.monst.c'" '(should have been 3125 characters)'
fi
echo shar: extracting "'hack.move.c'" '(11537 characters)'
if test -f 'hack.move.c'
then
	echo shar: over-writing existing file "'hack.move.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.move.c'
X/*
X * Hack.move.c
X */
X
X#include "hack.h"
X
Xextern char     STOPGLOW[], UMISS[], *setan ();
X
X
Xextern  OBJECT addinv ();
X
Xchar    seelx, seehx, seely, seehy;/* Corners of lit room */
X /* l for Low, h for High */
X
X#define ZOO		1
X#define GRAVEYARD	2
X#define SWAMP		3
X#define FORT_KNOX	4
X
X
X/* Contains move commands */
X
Xchar    sdir[] = "hjklyubn";
Xshort   xdir[8] = {
X	-1, 0, 0, 1, -1, 1, -1, 1
X}      ,
X        ydir[8] = {
X	0, 1, -1, 0, -1, -1, 1, 1
X};
X
Xmovecm (cmd)
Xregister char  *cmd;
X{
X	register char  *dp;
X
X	if (!(dp = index (sdir, *cmd)))
X		return 0;
X	dx = xdir[dp - sdir];
X	dy = ydir[dp - sdir];
X	return 1;
X}
X
X
Xdomove () {
X	char    nx, ny, tmpx, tmpy, let;
X	register        MONSTER mtmp;
X	register        PART * tmpr, *ust;
X	GOLD_TRAP gold, trap, gtm1;
X	OBJECT otmp, obj;
X
X	if (u.uswallow) {
X		nx = u.ux;
X		ny = u.uy;
X		goto M;
X	}
X /*  n<letter> is used for u.u<letter> + d<letter>  */
X	if (u.uconfused) {
X		do {
X			dx = rn2 (3);
X			dy = rn2 (3);
X			dx--;
X			dy--;
X			tmpr = &levl[u.ux + dx][u.uy + dy];
X		}
X		while ((!dx && !dy) || tmpr -> typ < DOOR);
X	}
X	else
X		tmpr = &levl[u.ux + dx][u.uy + dy];
X	ust = &levl[u.ux][u.uy];
X	tmpx = u.ux;
X	tmpy = u.uy;
X	nx = u.ux + dx;
X	ny = u.uy + dy;
X	if (trap = g_at (nx, ny, ftrap)) {
X		if (trap -> gflag == MIMIC) {
X			nomul (0);
X			pline ("The door is actually a mimic.");
X			deltrap (trap);
X			if (makemon (PM_MIMIC)) {
X				newsym (nx, ny);
X				return;
X			}
X			if (m_at (nx, ny))
X				mnexto (fmon);
X			else {
X				fmon -> mx = nx;
X				fmon -> my = ny;
X			}
X			if (!u.ustuck)
X				u.ustuck = fmon;
X			pmon (fmon);
X			return;
X		}
X		if (trap -> gflag & SEEN)
X			nomul (0);
X	}
X	if (u.ustuck && (nx != u.ustuck -> mx || ny != u.ustuck -> my)) {
X		pseebl ("You cannot escape from %s!",
X				u.ustuck -> data -> mname);
X		nomul (0);
X		return;
X	}
XM: 
X	if (mtmp = m_at (nx, ny)) {
X/* Attack monster */
X		char    tmp;
X		register        MONSTDATA mdat = mtmp -> data;
X
X		tmp = u.ulevel - 1 + mdat -> ac + abon ();
X		if (uwep) {
X			tmp += uwep -> spe;
X			if (uwep -> otyp == W_TWOH_SWORD)
X				tmp--;
X			else if (uwep -> otyp == W_DAGGER)
X				tmp += 2;
X			else if (uwep -> otyp == W_SPEAR && index ("XDne",
X						mdat -> mlet))
X				tmp += 2;
X		}
X		if (mtmp -> msleep) {
X			mtmp -> msleep = 0;
X			tmp += 2;
X		}
X		if (mtmp -> mfroz) {
X			tmp += 4;
X			if (!rn2 (10))
X				mtmp -> mfroz = 0;
X		}
X		if (mtmp -> mflee)
X			tmp += 2;
X		if (u.utrap)
X			tmp -= 3;
X		if (mtmp == shopkeeper)
X			setangry ();
X		if (tmp < rnd (20) && !u.uswallow)
X			pseebl (UMISS, mdat -> mname);
X		else {
X/* We hit the monster; but: it might die! */
X
X			if (hmon (mtmp, uwep)) {
X			/* 0-destroy,1-hit */
X				if (!u.uswallow && !rn2 (25) &&
X						mtmp -> mhp < mtmp -> orig_hp >> 1) {
X/* You might be stucked at this point ! { FRED } */
X					if (mtmp == u.ustuck)
X						unstuck (mtmp);
X					mtmp -> mflee = 1;
X				}
X				pseebl ("You hit %s!", mdat -> mname);
X				if (u.umconf && !u.uswallow) {/* a3 */
X					if (!u.ublind) {
X						pline (STOPGLOW);
X						pseebl ("The %s appears confused.", mdat -> mname);
X					}
X					mtmp -> mconf = 1;
X					u.umconf = 0;
X				}
X				if (mtmp -> wormno)
X					cutworm (mtmp, nx, ny,
X							uwep -> otyp);
X				switch (mdat -> mlet) {
X
X					case 'a': 
X						if (rn2 (2)) {
X							pline ("You are splashed by the blob's acid!");
X							losehp (rnd (6), mdat -> mname);
X						}
X						if (!rn2 (6) && uwep) {
X							pline ("Your %s corrodes!",
X									weapons[uwep -> otyp].wepnam);
X							--uwep -> spe;
X						}
X						break;
X
X					case 'E': 
X						if (!u.ublind && rn2 (2)) {
X							pline ("You are frozen by the floating eye's gaze!");
X							nomul (rn1 (20, -20));
X							return;
X						}
X						break;
X				}
X			}
X		}
X		nomul (0);
X		return;
X	}
X
X/* Not attacking an animal, so we try to move  */
X	if (u.utrap) {
X		pline ((u.upit) ? "You are still in a pit." :
X				"You are caught in a beartrap.");
X		if (u.upit || (dx && dy) || !rn2 (5))
X			u.utrap--;
X		return;
X	}
X	if ((dx && dy && (tmpr -> typ == DOOR || ust -> typ == DOOR)) ||
X			tmpr -> typ < DOOR || tmpr -> typ == VAULT) {
X	/* 0, WALL, or SDOOR */
X		flags.move = 0;
X		nomul (0);
X		return;
X	}
X	u.ux = nx;		/* u.ux+=dx; u.uy+=dy; */
X	u.uy = ny;
X	nx += dx;
X	ny += dy;
X	if (flags.run)
X		if (tmpr -> typ == DOOR ||
X				(xupstair == u.ux && yupstair == u.uy) ||
X				(xdnstair == u.ux && ydnstair == u.uy))
X			nomul (0);
X	if (tmpr -> typ >= 30 && tmpr -> typ <= 41) {
X		for (otmp = invent; otmp; otmp = otmp -> nobj) {
X			if (otmp -> otyp == tmpr -> typ && otmp -> olet == '_') {
X				pline ("The door opens.");
X				doname (otmp, buf);
X				pline ("The %s vanishes.", buf);
X				useup (otmp);
X				tmpr -> typ = DOOR;
X				break;
X			}
X		}
X		if (!otmp) {
X			if (rn2 (2))
X				pline ("The door is locked!");
X			else
X				pline ("You cannot unlock the door!");
X			u.ux -= dx;
X			u.uy -= dy;
X			return;
X		}
X	}
X	if (ust -> scrsym == '@') {
X		newsym (tmpx, tmpy);
X		oldux = tmpx;
X		olduy = tmpy;
X	}
X	if (!u.ublind) {
X		if (ust -> lit) {
X			if (tmpr -> lit) {
X				if (tmpr -> typ == DOOR)
X					prl1 (nx, ny);
X				if (ust -> typ == DOOR)
X					nose1 (tmpx - dx, tmpy - dy);
X			}
X			else {
X				unCoff (UNC, 1);
X				prl1 (nx, ny);
X			}
X		}
X		else {
X			if (tmpr -> lit)
X				setCon (SETC);
X			else {
X				prl1 (nx, ny);
X				if (tmpr -> typ == DOOR) {
X					if (dy) {
X						prl (u.ux - 1, u.uy);
X						prl (u.ux + 1, u.uy);
X					}
X					else {
X						prl (u.ux, u.uy - 1);
X						prl (u.ux, u.uy + 1);
X					}
X				}
X			}
X			nose1 (tmpx - dx, tmpy - dy);
X		}
X	}
X	else
X		newunseen (tmpx, tmpy);
X	if (!multi)
X		pru ();
X	while (gold = g_at (u.ux, u.uy, fgold)) {
X		if (!gold -> gflag) {
X			pline ("The chest was a mimic!");
X			if (!makemon (PM_MIMIC)) {
X				mnexto (fmon);
X				u.ustuck = fmon;
X			}
X			nomul (0);
X		}
X		else {
X			if (u.uhcursed) {
X				pline ("You cannot pick up the gold!");
X				break;
X			}
X			if (gold -> gflag == 1)
X				gold -> gflag++;/* a3 */
X			pline ("%u gold pieces", gold -> gflag);
X			u.ugold += gold -> gflag;
X			flags.dgold = 1;
X		}
X		if (gold == fgold)
X			fgold = fgold -> ngen;
X		else {
X			for (gtm1 = fgold; gtm1 -> ngen != gold;
X					gtm1 = gtm1 -> ngen);
X			gtm1 -> ngen = gold -> ngen;
X		}
X		free (gold);
X		if (flags.run)
X			nomul (0);
X		if (u.uinvis)
X			newsym (u.ux, u.uy);
X	}
X	while (obj = o_at (u.ux, u.uy)) {
X		for (otmp = invent, let = 0; otmp; otmp = otmp -> nobj)
X			let += weight (otmp);
X		let += weight (obj);
X		if (let > 85) {
X			pline ("You can't carry anything more.");
X			if (flags.run)
X				nomul (0);
X			break;
X		}
X		if (let > 80)
X			pline ("You have a little trouble lifting");
X		if (!(obj -> cursed))
X			obj -> cursed = u.uhcursed;
X		freeobj (obj);
X		addtobill (obj);/* Sets obj->unpaid if necessary */
X		prinv (addinv (obj));
X	/* Might merge it with other objects */
X		if (u.uinvis)
X			newsym (u.ux, u.uy);
X		if (flags.run)
X			nomul (0);
X	}
X	if (trap) {
X		nomul (0);
X		if (trap -> gflag & SEEN && !rn2 (5))
X			pline ("You escape a%s.",
X					traps[trap -> gflag & 037]);
X		else {
X			trap -> gflag |= SEEN;
X			switch (((trap -> gflag) & 037)) {
X
X				case SLPTRP: 
X					pline ("A cloud of gas puts you to sleep!");
X					nomul (-rnd (25));
X					break;
X
X				case BEAR: 
X					u.utrap = rn1 (4, 4);
X					u.upit = 0;
X					pline ("A bear trap closes on your foot!");
X					break;
X
X				case PIERC: 
X					pline ("A piercer suddenly drops from the ceiling!");
X					deltrap (trap);
X					if (!makemon (PM_PIERC)) {
X						mnexto (fmon);
X						hitu (3, d (4, 6),
X								"falling piercer");
X					}
X					break;
X
X				case ARROW: 
X					pline ("An arrow shoots out at you!");
X					hitu (8, rnd (6), "arrow");
X					break;
X
X				case TDOOR: 
X					if (!xdnstair) {
X						pline ("A trap door in the ceiling opens and a rock falls on your head!");
X						losehp (d (2, 10),
X								"falling rock");
X						break;
X					}
X					pline ("A trap door opens up under you!");
X					if (u.ufloat || u.ustuck) {
X						pline ("For some reason you don't fall in.");
X						break;
X					}
X					more ();
X					keepdogs (1);
X					unCoff (COFF, 1);
X					do {
X						dosavelev ();
X						dodown ();
X						levl[u.ux][u.uy].scrsym = '<';
X					} while (!rn2 (4) && xdnstair);
X					land ();
X					losedogs ();
X					setCon (CON);
X					inshop ();/* a3:zie tele */
X					break;
X
X				case DART: 
X					pline ("A little dart shoots out at you!");
X					if (hitu (7, rnd (3), "little dart") &&
X							!rn2 (6))
X						poisoned ("dart", "poison dart");
X					break;
X
X				case TELE: 
X					newsym (u.ux, u.uy);
X					tele ();
X					break;
X
X				case PIT: 
X					if (u.ufloat) {
X						pline ("A pit opens up under you!");
X						pline ("You don't fall in!");
X						break;
X					}
X					pline ("You fall into a pit!");
X					u.utrap = rn1 (6, 2);
X					u.upit = 1;
X					losehp (rnd (6), "pit");
X					break;
X
X				default: 
X					pline ("Bad(%d)trap", trap -> gflag);
X					impossible ();
X			}
X		}
X	}
X	if (tmpr -> typ == DOOR && dlevel) {
X		inshop ();
X		switch (rooms[inroom (u.ux, u.uy)].rtype) {
X			case ZOO: 
X				if (!u.uinzoo) {
X					pline ("Welcome to the Zoo!");
X					u.uinzoo++;
X				}
X				break;
X			case GRAVEYARD: 
X				if (!u.uinyard) {
X					pline ("Welcome to the Graveyard!");
X					u.uinyard++;
X				}
X				break;
X			case SWAMP: 
X				if (!u.uinswamp) {
X					pline ("Welcome to the Swamp!");
X					u.uinswamp++;
X				}
X				break;
X			case FORT_KNOX: 
X				if (!u.uinknox) {
X					pline ("Welcome to Fort Knox!");
X					u.uinknox++;
X				}
X				break;
X			default: 
X				break;/* Who knows what more may come */
X		}
X	}
X	if (tmpr -> typ == CORR) {
X		if (u.uinshop)
X			inshop ();/* Outside shop now */
X		u.uinzoo = 0;	/* You left the Zoo ?? */
X		u.uinyard = 0;	/* You left the Graveyard ?? */
X		u.uinswamp = 0;	/* You left the Swamp ?? */
X		u.uinknox = 0;	/* You left Fort Knox ?? */
X	}
X	if (tmpr -> typ == POOL)
X		if (!u.ufloat) {
X			pline ("You fall into a pool!");
X			pline ("You can't swim!");
X			pline ("You drown...");
X			more ();
X			killer = "Pool of water";
X			done (DROWNED);
X		}
X}
X
X/* Stop running if we see something interesting */
Xlookaround () {
X	register        x, y, corrct = 0;
X	register        MONSTER mtmp;
X
X	if (u.ublind || flags.run < 2)
X		return;
X	for (x = u.ux - 1; x <= u.ux + 1; x++)
X		for (y = u.uy - 1; y <= u.uy + 1; y++) {
X			if (x == u.ux && y == u.uy)
X				continue;
X/* Note: we cannot call r_free: perhaps a M is hidden in the wall */
X			if (!levl[x][y].typ)
X				continue;
X			if (mtmp = m_at (x, y))
X				if (!mtmp -> mtame || (x == u.ux + dx &&
X							y == u.uy + dy)) {
X					nomul (0);
X					return;
X				}
X			if (x == u.ux - dx && y == u.uy - dy)
X				continue;
X			if (mtmp)
X				corrct++;
X			else
X				switch (levl[x][y].scrsym) {
X					case '+': 
X						if (x == u.ux || y == u.uy) {
X							nomul (0);
X							return;
X						}
X					case '0': 
X						multi = 0;
X						flags.run = 0;
X						return;
X					case '.': 
X					case '|': 
X					case '-': 
X						break;
X					case '#': 
X						corrct++;
X						break;
X					default: 
X						nomul (0);
X						return;
X				}
X		}
X	if (corrct > 1 && flags.run == 2)
X		nomul (0);
X}
X
Xnomul (nval)
Xregister        nval;
X{
X	if (multi < 0)
X		return;
X	if (flags.mv)
X		pru ();
X	multi = nval;
X	flags.mv = 0;
X	flags.run = 0;
X}
X
Xchar   *
X        parse () {
X	static char     inline[80];
X	register        foo;
X
X	oldux = 0;
X	olduy = 0;
X	flags.move = 1;
X	if (!u.uinvis)
X		curs (u.ux, u.uy + 2);
X	else
X		home ();
X	flush ();
X	while ((foo = getchar ()) >= '0' && foo <= '9')
X		multi += 10 * multi + foo - '0';
X	if (multi) {
X		multi--;
X		save_cm = inline;
X	}
X	inline[0] = foo;
X	inline[1] = 0;
X	if (foo == 'f' || foo == 'F') {
X		inline[1] = getchar ();
X		inline[2] = 0;
X	}
X	if (flags.topl) {
X		home ();
X		cl_end ();
X		flags.topl = 0;
X	}
X	return (inline);
X}
X
Xnomove () {
X	multi = 0;
X	flags.move = 0;
X}
SHAR_EOF
if test 11537 -ne "`wc -c 'hack.move.c'`"
then
	echo shar: error transmitting "'hack.move.c'" '(should have been 11537 characters)'
fi
echo shar: extracting "'hack.name.h'" '(2094 characters)'
if test -f 'hack.name.h'
then
	echo shar: over-writing existing file "'hack.name.h'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.name.h'
X/*
X * Hack.name.h
X */
X
X#define S_ENCH_ARMOR	0
X#define S_DROP		1
X#define S_CURSE_LEV	2
X#define S_REM_CURSE	3
X#define S_ENCH_WEP	4
X#define S_CREAT_MON	5
X#define S_DAM_WEP	6
X#define S_GENOCIDE	7
X#define S_DESTR_ARMOR	8
X#define S_LIGHT		9
X#define S_TELEPORT	10
X#define S_GOLD_DETEC	11
X#define S_IDENTIFY	12
X#define S_MAG_MAP	13
X#define S_FIRE		14
X
X#define P_REST_STR	0
X#define P_BOOZE		1
X#define P_INVIS		2
X#define P_JUICE		3
X#define P_HEALING	4
X#define P_FROZEN	5
X#define P_MONDETEC	6
X#define P_OBJDETEC	7
X#define P_POISON	8
X#define P_CONF		9
X#define P_GAIN_STR	10
X#define P_SPEED		11
X#define P_BLIND		12
X#define P_GAIN_LEV	13
X#define P_EXTRA_HEALING	14
X
X#define Z_LIGHT		0
X#define Z_DETEC		1
X#define Z_CREATE_MON	2
X#define Z_EXHAUST	3
X#define Z_SLOW_MON	4
X#define Z_SPEED_MON	5
X#define Z_UND_TUR	6
X#define Z_POLYMORF	7
X#define Z_CAN		8
X#define Z_TELEPORT	9
X#define Z_DIGGING	10
X#define Z_MAG_MISSILE	11
X#define Z_FIRE		12
X#define Z_SLEEP		13
X#define Z_COLD		14
X#define Z_DEATH		15
X#define Z_CONF_MON	16
X#define Z_CLOSING	17
X
X#define R_ADORNMENT	0
X#define R_TELE		1
X#define R_REGEN		2
X#define R_SEARCH	3
X#define R_SEE_INV	4
X#define R_STEALTH	5
X#define R_FLOAT		6
X#define R_POISON_RES	7
X#define R_AGGRAV_MON	8
X#define R_HUNGER	9
X#define R_FIRE_RES	10
X#define R_COLD_RES	11
X#define R_SHAPE		12
X#define R_GAIN_STR	13
X#define R_DAM_INC	14
X#define R_PROTECTION	15
X
X#define W_ARROW		0
X#define W_SL_BULLET	1
X#define W_CROSS_BOLT	2
X#define W_DART		3
X#define W_MACE		4
X#define W_AXE		5
X#define W_FLAIL		6
X#define W_LONG_SWORD	7
X#define W_TWOH_SWORD	8
X#define W_DAGGER	9
X#define W_SPEAR		10
X#define W_BOW		11
X#define W_SLING		12
X#define W_CROSSBOW	13
X
X#define W_USE_AMMO	11
X#define W_AMMUNITION	3
X
X#define A_PLATE		0
X#define A_SPLINT	1
X#define A_BANDED	2
X#define A_CHAIN		3
X#define A_SCALE		4
X#define A_RING		5
X#define A_STD_LEATHER	6
X#define A_LEATHER	7
X#define A_ELVEN_CLOAK	8
X
X#define F_FOOD		0
X#define F_TRIPE		1
X#define F_PANCAKE	2
X#define F_LIZARD	3
X#define F_COOKIE	4
X#define F_ORANGE	5
X#define F_APPLE		6
X#define F_PEAR		7
X#define F_MELON		8
X#define F_BANANA	9
X#define F_CANDY		10
X#define F_EGG		11
SHAR_EOF
if test 2094 -ne "`wc -c 'hack.name.h'`"
then
	echo shar: error transmitting "'hack.name.h'" '(should have been 2094 characters)'
fi
echo shar: extracting "'hack.office.c'" '(499 characters)'
if test -f 'hack.office.c'
then
	echo shar: over-writing existing file "'hack.office.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.office.c'
X/*
X * Hack.office.c
X */
X
Xstruct tm {			/* see ctime(3) */
X	int     tm_sec;
X	int     tm_min;
X	int     tm_hour;
X	int     tm_mday;
X	int     tm_mon;
X	int     tm_year;
X	int     tm_wday;
X	int     tm_yday;
X	int     tm_isdst;
X};
X
X
X#define SUNDAY 0
X#define SATURDAY 6
X
Xextern struct tm       *localtime ();
X
Xkantoor () {
X	struct tm      *s;
X	long    clock;
X
X	time (&clock);
X	s = localtime (&clock);
X	return (s -> tm_wday != SUNDAY && s -> tm_wday != SATURDAY &&
X			s -> tm_hour <= 17 && s -> tm_hour > 9);
X}
SHAR_EOF
if test 499 -ne "`wc -c 'hack.office.c'`"
then
	echo shar: error transmitting "'hack.office.c'" '(should have been 499 characters)'
fi
echo shar: extracting "'hack.pri.c'" '(8817 characters)'
if test -f 'hack.pri.c'
then
	echo shar: over-writing existing file "'hack.pri.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.pri.c'
X/*
X * Hack.pri.c
X */
X
X#include "hack.h"
X
Xchar    scrlx, scrhx, scrly, scrhy;
X
Xextern short    ospeed;
Xchar    xcurses[200];		/* Contain's curser stuff */
Xchar   *HO, *CL, *CE, *CM, *UP, *BC;
Xchar    PC;
Xextern char    *tgetstr (), *getenv (), *tgoto (), *malloc ();
Xint     putch ();
X /* Corners of new area on screen */
Xextern char     SAVEFILE[];
X
XCOORDINATES ou = {
X	-1, 0
X};				/* Coordinates of @ on screen (if ou.x>=0) */
X
Xextern char    *getenv (), *hu_stat[4];/* In eat.c */
X#ifdef NORMAL_IO
Xchar    obuf[BUFSIZ];
X#endif NORMAL_IO
X
Xstartup () {
X	char   *bp = malloc (1024);
X	char   *atcurs = xcurses;
X
X	if (tgetent (bp, getenv ("TERM")) <= 0)
X		panic (NOCORE, "I know about many terminals but alas, not this one\n");
X	PC = tgetflag ("pc");
X	HO = tgetstr ("ho", &atcurs);
X	CL = tgetstr ("cl", &atcurs);
X	CE = tgetstr ("ce", &atcurs);
X	UP = tgetstr ("up", &atcurs);
X	if (!(BC = tgetstr ("bc", &atcurs))) {
X		if (!tgetflag ("bs"))
X			panic (NOCORE,
X					"You don't have a backspaced terminal\n");
X		BC = (char *) NULL;
X	}
X	if (!(CM = tgetstr ("cm", &atcurs)))
X		panic (NOCORE, "Hack needs cursor addressible terminals\n");
X	else if (!UP || !CL || tgetflag ("os"))
X		panic (NOCORE, "Hack needs `up' and `cl' and no `os'\n");
X	free (bp);
X#ifdef NORMAL_IO
X	setbuf (stdout, obuf);
X#endif NORMAL_IO
X}
X
X/*VARARGS*/
Xpanic (coredump, str, a1, a2, a3, a4, a5, a6)
Xregister char  *str;
X{
X	home ();
X#ifdef NORMAL_IO
X	printf ("ERROR:  ", 10);
X#else
X	WRITE ("ERROR:  ", 10);
X#endif NORMAL_IO
X	printf (str, a1, a2, a3, a4, a5, a6);
X	hackmode (OFF);
X	if (!unlink (SAVEFILE))
X		printf ("Savefile removed.\n");
X	flush ();
X	if (coredump)
X		abort ();
X	exit (2);
X}
X
Xseeatl (x, y, c)
Xregister        x, y, c;
X{
X	if (cansee (x, y))
X		atl (x, y, c);
X}
X
Xcls () {
X	tputs (CL, 0, putch);
X	curx = 1;
X	cury = 1;
X	ou.x = -1;
X	flags.topl = 0;
X}
X
Xhome () {
X	if (HO)
X		tputs (HO, 0, putch);
X	else
X                curs (1,1);
X	curx = 1;
X	cury = 1;
X}
X
Xatl (x, y, ch)
Xregister        x, y;
X{
X	register        PART * crm = &levl[x][y];
X
X	if (crm -> scrsym == ch)
X		return;
X	if (x < 0 || x > 79 || y < 0 || y > 21)
X		panic (CORE, "atl(%d,%d,%c_%d_)", x, y, ch, ch);
X	crm -> scrsym = ch;
X	crm -> new = 1;
X	on (x, y);
X}
X
Xon (x, y)
Xregister        x, y;
X{
X	if (flags.dscr) {
X		if (x < scrlx)
X			scrlx = x;
X		else if (x > scrhx)
X			scrhx = x;
X		if (y < scrly)
X			scrly = y;
X		else if (y > scrhy)
X			scrhy = y;
X	}
X	else {
X		flags.dscr = 1;
X		scrlx = scrhx = x;
X		scrly = scrhy = y;
X	}
X}
X
Xat (x, y, ch)
Xregister        x, y;
Xregister char   ch;
X{
X	if (!ch || x < 0 || x > 79 || y < 0 || y > 21)
X		panic (CORE, "at(%d %d,%d) at %d %d", x, y, ch,
X				u.ux, u.uy);
X	y += 2;
X	curs (x, y);
X	putchar (ch == '\t' ? ' ' : ch);
X	curx++;
X}
X
Xprme () {
X	if (!u.uinvis)
X		at (u.ux, u.uy, '@');
X}
X
Xpru () {
X	prl (u.ux, u.uy);
X}
X
Xprl (x, y) {
X	register        PART * room;
X	register        MONSTER mtmp;
X
X	room = &levl[x][y];
X	if (!room -> typ || (room -> typ < DOOR &&
X				levl[u.ux][u.uy].typ == CORR))
X		return;
X	if ((mtmp = m_at (x, y)) && (!mtmp -> invis || u.ucinvis))
X		atl (x, y,
X				(mtmp -> wormno && (mtmp -> mx != x || mtmp -> my != y)) ?
X				'~' :
X				mtmp -> data -> mlet);
X	else
X		newunseen (x, y);
X}
X
Xnewunseen (x, y)
Xregister        x, y;
X{
X	if (!levl[x][y].seen) {
X		levl[x][y].new = 1;
X		on (x, y);
X	}
X}
X
Xchar
X        news0 (x, y)
Xregister        x, y;
X{
X	register        OBJECT otmp;
X	register        GOLD_TRAP gtmp;
X	PART * room;
X	register char   tmp;
X
X	room = &levl[x][y];
X	if (!u.ublind && (otmp = o_at (x, y)))
X		tmp = otmp -> olet;
X	else if (!u.ublind && g_at (x, y, fgold))
X		tmp = '$';
X	else if (gtmp = g_at (x, y, ftrap)) {
X		if (gtmp -> gflag == MIMIC)
X			tmp = '+';
X		else if (gtmp -> gflag & SEEN)
X			tmp = '^';
X		else
X			tmp = '.';
X	}
X	else if (room -> typ >= 30 && room -> typ <= 41)
X		tmp = '0';
X	else
X		switch (room -> typ) {
X
X			case SDOOR: 
X			case WALL: 
X				if ((room - 1) -> typ == WALL && (room + 1) -> typ
X						== WALL)
X					tmp = '|';
X				else
X					tmp = '-';
X				break;
X
X			case DOOR: 
X				tmp = '+';
X				break;
X
X			case ROOM: 
X				if (x == xupstair && y == yupstair)
X					tmp = '<';
X				else if (x == xdnstair && y == ydnstair)
X					tmp = '>';
X				else if (room -> lit || cansee (x, y) || u.ublind)
X					tmp = '.';
X				else
X					tmp = ' ';
X				break;
X
X			case CORR: 
X				tmp = '#';
X				break;
X
X			case POOL: 
X				tmp = '}';
X				break;
X			case VAULT: 
X				tmp = '-';
X				break;
X
X			default: 
X				tmp = '`';
X				impossible ();
X		}
X	return tmp;
X}
X
Xnewsym (x, y)
Xregister        x, y;
X{
X	atl (x, y, news0 (x, y));
X}
X
Xlevlsym (x, y, c)
Xregister        x, y, c;
X{
X	if (levl[x][y].scrsym == c)
X		newsym (x, y);
X}
X
Xnosee (x, y)
Xregister        x, y;
X{
X	register        PART * room;
X
X	room = &levl[x][y];
X	if (room -> scrsym == '.' && !room -> lit && !u.ublind) {
X		if (room -> new && (x != oldux || y != olduy))
X			room -> new = 0;
X		else {
X			room -> scrsym = ' ';
X			room -> new = 1;
X			on (x, y);
X		}
X	}
X}
X
Xprl1 (x, y)
Xregister        x, y;
X{
X	register        count;
X
X	if (dx) {
X		if (dy) {
X			prl (x - (dx << 1), y);
X			prl (x - dx, y);
X			prl (x, y);
X			prl (x, y - dy);
X			prl (x, y - (dy << 1));
X		}
X		else
X			for (count = -1; count <= 1; ++count)
X				prl (x, y + count);
X	}
X	else
X		for (count = -1; count <= 1; ++count)
X			prl (x + count, y);
X}
X
Xnose1 (x, y)
Xregister        x, y;
X{
X	register        count;
X
X	if (dx)
X		if (dy) {
X			nosee (x, u.uy);
X			nosee (x, u.uy - dy);
X			nosee (x, y);
X			nosee (u.ux - dx, y);
X			nosee (u.ux, y);
X		}
X		else
X			for (count = -1; count <= 1; ++count)
X				nosee (x, y + count);
X	else
X		for (count = -1; count <= 1; ++count)
X			nosee (x + count, y);
X}
X
Xdoreprint () {
X	nomove ();
X	pline ("\200");		/* Michiel: Code for repeating last message */
X}
X
X/* VARARGS1 */
Xpline (line, arg1, arg2, arg3, arg4)
Xregister char  *line;
X{
X	char    pbuf[BUFSZ];
X	static char     prevbuf[BUFSZ];
X
X	if (index (line, '\200'))
X		strcpy (pbuf, prevbuf);
X	else {
X		if (!index (line, '%'))
X			strcpy (pbuf, line);
X		else
X			sprintf (pbuf, line, arg1, arg2, arg3, arg4);
X		if (multi && !strcmp (pbuf, prevbuf))
X			return;
X		strcpy (prevbuf, pbuf);
X	}
X	if (flags.dscr)
X		nscr ();
X	if (flags.topl) {
X		curs (savx, 1);
X		more ();
X	}
X	flags.topl = 1;
X	home ();
X	cl_end ();
X	printf (pbuf);
X	savx = strlen (pbuf);
X	curx = ++savx;
X}
X
Xprustr () {
X	if (u.ustr > 18) {
X		if (u.ustr > 117)
X			printf ("18/00");
X		else
X			printf ("18/%02d", u.ustr - 18);
X	}
X	else
X		printf ("%-5d", u.ustr);
X	curx += 5;
X}
X
Xpmon (mtmp)
Xregister        MONSTER mtmp;
X{
X	if (!mtmp -> invis || u.ucinvis)
X		seeatl (mtmp -> mx, mtmp -> my, mtmp -> data -> mlet);
X}
X
Xdocrt () {
X	cls ();
X	if (u.uswallow) {
X		curs (u.ux - 1, u.uy - 1);
X		printf ("/-\\");
X		curs (u.ux - 1, u.uy);
X		printf ("|@|");
X		curs (u.ux - 1, u.uy + 1);
X		printf ("\\-/");
X		curx = u.ux + 2;
X	}
X	else
X		donscrt (0, 0);	/* a3 */
X	bot ();
X}
X
Xnscr () {
X	register        umv;
X
X	umv = ((ou.x < 0 && !u.uinvis) || (ou.x >= 0 &&
X				(u.uinvis || ou.x != u.ux || ou.y != u.uy)));
X	if (ou.x >= 0 && umv && !levl[ou.x][ou.y].new)
X		newsym (ou.x, ou.y);
X	donscrt (1, umv);
X}
X
Xdonscrt (mode, umv) {		/* mode: 0- docrt(), 1- nscr()  */
X	register        PART * room;
X	register        x, y, ly, hy, lx, hx;
X
X	if (u.uinvis) {
X		if (mode)
X			ou.x = -1;
X	}
X	else {
X		ou.x = u.ux;
X		ou.y = u.uy;
X		if (mode && umv)
X			atl (ou.x, ou.y, '@');
X		else {
X			(room = &levl[ou.x][ou.y]) -> scrsym = '@';
X			if (!mode)
X				room -> seen = 1;
X			else
X				room -> new = 0;
X		}
X	}
X	if (mode) {
X		ly = scrly;
X		hy = scrhy;
X		lx = scrlx;
X		hx = scrhx;
X	}
X	else {
X		ly = 0;
X		hy = 21;
X		lx = 0;
X		hx = 79;
X	}
X	for (y = ly; y <= hy; y++)
X		for (x = lx; x <= hx; x++)
X			if ((room = &levl[x][y]) -> new) {
X				room -> new = 0;
X				at (x, y, room -> scrsym);
X				if (room -> scrsym == ' ') {
X					room -> seen = 0;
X					room -> scrsym = '.';
X				}
X				else
X					room -> seen = 1;
X			}
X			else if (!mode)
X				if (room -> seen)
X					at (x, y, room -> scrsym);
X	flags.dscr = 0;
X	scrhx = 0;
X	scrhy = 0;
X	scrlx = 80;
X	scrly = 22;
X}
X
Xbot () {
X	flags.botl = 0;
X	flags.dhp = 0;
X	flags.dhpmax = 0;
X	flags.dac = 0;
X	flags.dstr = 0;
X	flags.dgold = 0;
X	flags.dhs = 0;
X	curs (1, 24);
X	printf ("Level %-4dGold %-7luHp%4d(%d)",
X			dlevel, u.ugold, u.uhp, u.uhpmax);
X	if (u.uhpmax < 10)
X		printf ("  ");
X	else if (u.uhpmax < 100)
X		putchar (' ');
X	printf ("Ac %-5dStr ", u.uac);
X	prustr ();
X	printf ("  Exp%3d/", u.ulevel);
X	if (u.ulevel < 14)
X		printf ("%-11lu", u.uexp);
X	else
X		printf ("%-11s", "MAX++");
X	printf ("%s", hu_stat[u.uhs]);
X	curx = 78;
X}
X
Xcurs (x, y)
Xregister        x, y;
X{
X	if (y == cury && x == curx)
X		return;		/* Do nothing, gracefully */
X	tputs (tgoto (CM, x - 1, y - 1), 0, putch);
X	flush ();
X	cury = y;
X	curx = x;
X}
X
Xcl_end () {
X	if (CE)
X		tputs (CE, 0, putch);
X	else {
X		printf ("%80s", "");
X		home ();
X	}
X}
X
Xputch (c)
Xchar    c;
X{
X#ifdef NORMAL_IO
X	putchar (c);
X#else
X	WRITE (&c, 1);
X#endif NORMAL_IO
X}
SHAR_EOF
if test 8817 -ne "`wc -c 'hack.pri.c'`"
then
	echo shar: error transmitting "'hack.pri.c'" '(should have been 8817 characters)'
fi
echo shar: extracting "'hack.rip.c'" '(1347 characters)'
if test -f 'hack.rip.c'
then
	echo shar: over-writing existing file "'hack.rip.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.rip.c'
X/*
X * Hack.rip.c
X */
X
X#include <time.h>
X#include "hack.h"
X
Xextern char     plname[];
X
Xstatic char    *rip[] = {
X	"                       ----------",
X	"                      /          \\",
X	"                     /    REST    \\",
X	"                    /      IN      \\",
X	"                   /     PEACE      \\",
X	"                  /                  \\",
X	"                  |                  |",
X	"                  |                  |",
X	"                  |   killed by a    |",
X	"                  |                  |",
X	"                  |       1001       |",
X	"                 *|     *  *  *      | *",
X	"        _________)/\\\\_//(\\/(/\\)/\\//\\/|_)_______",
X	0
X};
X
Xoutrip () {
X	register char **dp = rip;
X	register struct tm     *lt;
X	long    date;
X	char    buffer[BUFSZ];
X	struct tm      *localtime ();
X
X	time (&date);
X	lt = localtime (&date);
X	cls ();
X	strcpy (buffer, plname);
X	center (6, buffer);
X	sprintf (buffer, "%lu Au", u.ugold);
X	center (7, buffer);
X	strcpy (buffer, killer);
X	center (9, buffer);
X	sprintf (buffer, "19%2d", lt -> tm_year);
X	center (10, buffer);
X	curs (1, 8);
X	while (*dp)
X		printf ("%s\n", *dp++);
X	getret ();
X}
X
Xcenter (line, text)
Xregister int    line;
Xregister char  *text;
X{
X	register char  *ip, *op;
X
X	ip = text;
X	op = &rip[line][28 - ((strlen (text) + 1) >> 1)];
X	while (*ip)
X		*op++ = *ip++;
X}
SHAR_EOF
if test 1347 -ne "`wc -c 'hack.rip.c'`"
then
	echo shar: error transmitting "'hack.rip.c'" '(should have been 1347 characters)'
fi
echo shar: extracting "'hack.save.c'" '(5888 characters)'
if test -f 'hack.save.c'
then
	echo shar: over-writing existing file "'hack.save.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.save.c'
X/*
X * Hack.save.c
X */
X
X/*
X * The old version of save () didn't work at all. Many things are changed,
X * but some things are not implemented yet, like saving in a shop, or saving
X * while swallowed or stuck
X */
X
X#include "hack.h"
X#include "hack.dog.h"
X#include <signal.h>
X
X#define MAXLEVEL	40
X
Xextern char     SAVEFILE[], nul[], upxstairs[MAXLEVEL],
X                upystairs[MAXLEVEL], shlevel, vaultflag[MAXLEVEL];
Xextern long     robbed;
Xextern unsigned starved;
Xextern  COORDINATES shk, shd;
Xextern  MONSTER shopkeeper;
Xextern  MONSTER mydogs;
X
Xsave () {
X	register        fd, ofd, tmp;
X	register        OBJECT otmp, otmp2;
X	MONSTER mtmp;
X	int     version = VERSION;
X
X	nomove ();
X	if (shopkeeper && inshproom (u.ux, u.uy)) {
X		pline ("You are not allowed to save in a shop. (Continue or Quit)");
X		return;
X	}
X	else if (u.ustuck || u.uswallow) {
X		pline ("Not implemented when you're stuck or swallowed. (Continue or Quit)");
X		return;
X	}
X	if ((fd = creat (SAVEFILE, 0644)) < 0) {
X		pline ("Cannot creat save file. (Continue or Quit)");
X		return;
X	}
X	signal (SIGINT, SIG_IGN);
X	signal (SIGQUIT, SIG_IGN);
X
X	bwrite (fd, &version, sizeof (version));
X	keepdogs (0);
X	savelev (fd);
X	for (otmp = invent; otmp; otmp = otmp2) {
X		bwrite (fd, otmp, sizeof (struct obj));
X		if (otmp == uarm)
X			bwrite (fd, "a", 1);
X		else if (otmp == uarm2)
X			bwrite (fd, "b", 1);
X		else if (otmp == uwep)
X			bwrite (fd, "w", 1);
X		else if (otmp == uleft)
X			bwrite (fd, "l", 1);
X		else if (otmp == uright)
X			bwrite (fd, "r", 1);
X		else
X			bwrite (fd, "n", 1);
X		otmp2 = otmp -> nobj;
X		ofree (otmp);
X	}
X	bwrite (fd, nul, sizeof (struct obj));
X	bwrite (fd, &flags, sizeof (struct flag));
X	bwrite (fd, &dlevel, sizeof dlevel);
X	bwrite (fd, &moves, sizeof moves);
X	bwrite (fd, &u, sizeof (struct you));
X	bwrite (fd, genocided, sizeof genocided);
X	bwrite (fd, upxstairs, sizeof upxstairs);
X	bwrite (fd, upystairs, sizeof upystairs);
X	bwrite (fd, vaultflag, sizeof vaultflag);
X
X	savenames (fd);
X
X/* SHOP part */
X	bwrite (fd, &shd, sizeof (struct coord));
X	bwrite (fd, &shk, sizeof (struct coord));
X	bwrite (fd, &shlevel, sizeof shlevel);
X	bwrite (fd, &robbed, sizeof robbed);
X
X/* Various globals */
X	bwrite (fd, &starved, sizeof starved);
X	bwrite (fd, &seehx, sizeof seehx);
X	bwrite (fd, &seelx, sizeof seelx);
X	bwrite (fd, &seehy, sizeof seehy);
X	bwrite (fd, &seely, sizeof seely);
X	bwrite (fd, &dx, sizeof dx);
X	bwrite (fd, &dy, sizeof dy);
X	bwrite (fd, &maxdlevel, sizeof maxdlevel);
X
X/* And the dog(s) if any */
X	for (mtmp = mydogs; mtmp; mtmp = mtmp -> nmon)
X		bwrite (fd, mtmp, sizeof (struct monst) +
X			                                        sizeof (struct edog));
X	bwrite (fd, nul, sizeof (struct monst) + sizeof (struct edog));
X
X	callssave (fd);
X
X	cls ();
X	printf ("Saving level ");
X	flush ();
X	for (tmp = 1;; tmp++) {
X		glo (tmp);
X		if ((ofd = open (lock, 0)) < 0)
X			break;
X		getlev (ofd);
X		close (ofd);
X		savelev (fd);
X		printf ("%2d - %s", tmp,
X				(tmp % 10) ? "" : "\n             ");
X		flush ();
X		unlink (lock);
X	}
X
X	close (fd);
X	(*index (lock, '.')) = '\0';/* Remove main lock */
X	unlink (lock);
X	printf ("\n\nSee you around...\n");
X	flush ();
X	hackmode (OFF);
X	exit (0);
X}
X
Xdorecover (fd)
Xregister        fd;
X{
X	register        nfd, tmp;
X	register        OBJECT otmp, olast;
X	MONSTER mtmp;
X	int     version;
X
X	cls ();
X	printf ("Starting up a suspended game....\n");
X	flush ();
X	mread (fd, &version, sizeof (version));
X	if (version != VERSION) {
X		printf ("Sorry, you're savefile is out of date.\n");
X		printf ("I will have to remove it.\n");
X		printf ("Type <space> to continue.");
X		close (fd);
X		unlink (SAVEFILE);
X		flush ();
X		while (getchar () != ' ');
X		return - 1;
X	}
X
X	getlev (fd);
X
X	invent = otmp = newobj ();
X	while (1) {
X		mread (fd, otmp, sizeof (struct obj));
X		if (!otmp -> olet) {
X			if (otmp == invent)
X				invent = 0;
X			else
X				olast -> nobj = 0;
X			ofree (otmp);
X			break;
X		}
X		olast = otmp;
X		olast -> nobj = otmp = newobj ();
X		mread (fd, buf, 1);
X		switch (*buf) {
X			case 'w': 
X				uwep = olast;
X				break;
X			case 'r': 
X				uright = olast;
X				break;
X			case 'l': 
X				uleft = olast;
X				break;
X			case 'a': 
X				uarm = olast;
X				break;
X			case 'b': 
X				uarm2 = olast;
X			case 'n': 
X				break;
X			default: 
X				panic (CORE, "Error reading save file");
X		}
X	}
X	mread (fd, &flags, sizeof (struct flag));
X	mread (fd, &dlevel, sizeof dlevel);
X	mread (fd, &moves, sizeof moves);
X	mread (fd, &u, sizeof (struct you));
X	mread (fd, genocided, sizeof genocided);
X	mread (fd, upxstairs, sizeof upxstairs);
X	mread (fd, upystairs, sizeof upystairs);
X	mread (fd, vaultflag, sizeof vaultflag);
X
X	restnames (fd);
X
X/* Restore shop part */
X	mread (fd, &shd, sizeof (struct coord));
X	mread (fd, &shk, sizeof (shk));
X	mread (fd, &shlevel, sizeof shlevel);
X	mread (fd, &robbed, sizeof robbed);
X
X/* Restore various globals */
X	mread (fd, &starved, sizeof starved);
X	mread (fd, &seehx, sizeof seehx);
X	mread (fd, &seelx, sizeof seelx);
X	mread (fd, &seehy, sizeof seehy);
X	mread (fd, &seely, sizeof seely);
X	mread (fd, &dx, sizeof dx);
X	mread (fd, &dy, sizeof dy);
X	mread (fd, &maxdlevel, sizeof maxdlevel);
X
X/* Let's try the dog again */
X	while (1) {
X		mtmp = newmonst (sizeof (struct edog));
X		mread (fd, mtmp, sizeof (struct monst) +
X			                                        sizeof (struct edog));
X		if (mtmp -> data == 0)
X			break;
X		else {
X			mtmp -> nmon = mydogs;
X			mydogs = mtmp;
X		}
X	}
X	free (mtmp);
X
X	callsrestore (fd);
X
X	printf ("Restoring level ");
X	flush ();
X	for (tmp = 1;; tmp++) {
X		if (getlev (fd))
X			break;
X		glo (tmp);
X		if ((nfd = creat (lock, 0644)) < 0)
X			panic (CORE, "Cannot open temp file %s!\n",
X					lock);
X		savelev (nfd);
X		printf ("%2d - %s", tmp,
X				(tmp % 10) ? "" : "\n                ");
X		flush ();
X		close (nfd);
X	}
X
X	lseek (fd, (long) (sizeof (version)), 0);
X	getlev (fd);
X	close (fd);
X	losedogs ();
X	unlink (SAVEFILE);
X	docrt ();
X	return 1;
X}
SHAR_EOF
if test 5888 -ne "`wc -c 'hack.save.c'`"
then
	echo shar: error transmitting "'hack.save.c'" '(should have been 5888 characters)'
fi
echo shar: extracting "'hack.savelev.c'" '(2130 characters)'
if test -f 'hack.savelev.c'
then
	echo shar: over-writing existing file "'hack.savelev.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.savelev.c'
X/*
X * Hack.savelev.c
X */
X
Xsavelev (fd) {
X	register        MONSTER mtmp, mtmp2;
X	register        GOLD_TRAP gtmp, gtmp2;
X	register        OBJECT otmp, otmp2;
X	register        WORMSEGMENT wtmp, wtmp2;
X	register        tmp;
X	int     minusone = -1;
X
X	if (fd < 0)
X		panic (CORE, "Save on bad file!");
X	bwrite (fd, levl, sizeof (levl));
X	bwrite (fd, &moves, sizeof (unsigned));
X	bwrite (fd, &xupstair, 1);
X	bwrite (fd, &yupstair, 1);
X	bwrite (fd, &xdnstair, 1);
X	bwrite (fd, &ydnstair, 1);
X	for (mtmp = fmon; mtmp; mtmp = mtmp2) {
X		mtmp2 = mtmp -> nmon;
X		bwrite (fd, &mtmp -> mxlth, sizeof (int));
X		bwrite (fd, mtmp, mtmp -> mxlth + sizeof (struct monst));
X
X/* Michiel save stolen objects */
X		if (mtmp -> mstole) {
X			bwrite (fd, mtmp -> mstole, sizeof (struct stole));
X			for (otmp = mtmp -> mstole -> sobj; otmp;
X					otmp = otmp -> nobj)
X				bwrite (fd, otmp, sizeof (struct obj));
X			bwrite (fd, nul, sizeof (struct obj));
X			free (mtmp -> mstole);
X		}
X		else
X			bwrite (fd, nul, sizeof (struct stole));
X		free (mtmp);
X	}
X	bwrite (fd, &minusone, sizeof (int));
X	for (gtmp = fgold; gtmp; gtmp = gtmp2) {
X		gtmp2 = gtmp -> ngen;
X		bwrite (fd, gtmp, sizeof (struct gen));
X		free (gtmp);
X	}
X	bwrite (fd, nul, sizeof (struct gen));
X	for (gtmp = ftrap; gtmp; gtmp = gtmp2) {
X		gtmp2 = gtmp -> ngen;
X		bwrite (fd, gtmp, sizeof (struct gen));
X		free (gtmp);
X	}
X	bwrite (fd, nul, sizeof (struct gen));
X	for (otmp = fobj; otmp; otmp = otmp2) {
X		otmp2 = otmp -> nobj;
X		bwrite (fd, otmp, sizeof (struct obj));
X		ofree (otmp);
X	}
X	bwrite (fd, nul, sizeof (struct obj));
X	bwrite (fd, rooms, sizeof (rooms));
X	bwrite (fd, doors, sizeof (doors));
X	fgold = 0;
X	ftrap = 0;
X	fmon = 0;
X	fobj = 0;
X	bwrite (fd, wsegs, sizeof (wsegs));
X	for (tmp = 1; tmp < 32; tmp++) {
X		for (wtmp = wsegs[tmp]; wtmp; wtmp = wtmp2) {
X			wtmp2 = wtmp -> nseg;
X			bwrite (fd, wtmp, sizeof (struct wseg));
X		}
X		wsegs[tmp] = 0;
X	}
X	bwrite (fd, wgrowtime, sizeof (wgrowtime));
X	shopkeeper = 0;
X}
X
Xbwrite (fd, loc, num)
Xregister        fd, num;
Xregister char  *loc;
X{
X	if (write (fd, loc, num) != num)
X		panic (CORE, "Cannot write %d bytes to file #%d", num,
X				fd);
X}
SHAR_EOF
if test 2130 -ne "`wc -c 'hack.savelev.c'`"
then
	echo shar: error transmitting "'hack.savelev.c'" '(should have been 2130 characters)'
fi
echo shar: extracting "'hack.shk.c'" '(10486 characters)'
if test -f 'hack.shk.c'
then
	echo shar: over-writing existing file "'hack.shk.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.shk.c'
X/*
X * Hack.shk.c
X */
X
X#include "hack.h"
X
X#define BILLSZ  200
X#define ONBILL    1
X#define NOTONBILL 0
X#define GDIST(x, y)     ((x - gx)*(x - gx) + (y - gy)*(y - gy) )
X
Xstruct {
X	OBJECT op;
Xunsigned        useup:                 1;
Xunsigned        bquan:                 5;
X	unsigned        price;
X}       bill[BILLSZ];
X
XMONSTER shopkeeper;
X
Xstruct permonst shk_pm = {
X	"shopkeeper", '@', 10, 12, 0, 4, 8, 0
X};
X
Xlong    robbed = 0, total;
X
X/*
X * shoproom = index in rooms; set by inshop()
X * shlevel  = last level we initialized shopkeeper
X */
X
Xchar    billct = 0, shoproom, shlevel;
Xchar   *shopnam[] = {
X	"engagement ring", "walking cane", "antique weapon",
X	"delicatessen", "second hand book", "liquor",
X	"used armor", "assorted antiques"
X};
X
XCOORDINATES shk, shd;
X /* Usual position shopkeeper;position shop door */
X
X#define SHOP_NAME               shopnam[rooms[shoproom].rtype - 8]
X
Xshkdead () {
X	shopkeeper = 0;
X	rooms[shoproom].rtype = 0;
X	setpaid ();
X}
X
Xsetpaid () {
X	register        tmp;
X	register        OBJECT obj;
X
X	for (obj = invent; obj; obj = obj -> nobj)
X		obj -> unpaid = 0;
X	for (tmp = 0; tmp < billct; tmp++)
X		if (bill[tmp].useup)
X			ofree (bill[tmp].op);
X	billct = 0;
X}
X
Xaddupbill () {			/* Delivers result in total */
X	register        ct = billct;
X
X	total = 0;
X	while (ct--)
X		total += bill[ct].price;
X}
X
Xinshproom (x, y)
Xregister        x, y;		/* a3 */
X{
X	return (inroom (x, y) == shoproom);
X}
X
Xinshop () {
X	register        tmp = inroom (u.ux, u.uy);
X
X	if (tmp < 0 || rooms[tmp].rtype < 8) {
X		u.uinshop = 0;
X		if (billct) {
X			pline ("Somehow you escaped the shop without paying!");
X			addupbill ();
X		    pline ("You stole for a total worth of %u zorkmids.",
X			  total);
X			robbed += total;
X			setpaid ();
X		}
X	}
X	else {
X		shoproom = tmp;
X		if (shlevel != dlevel)
X			shopinit ();
X		if (!u.uinshop) {
X			pline ("%s to Dirk's %s shop!",
X					(shopkeeper -> angry) ?
X					"You're not that welcome" : "Welcome",
X					SHOP_NAME);
X			++u.uinshop;
X		}
X	}
X	return (u.uinshop);
X}
X
X/* Called by useup and dothrow only */
Xonbill (obj)
Xregister        OBJECT obj;
X{
X	register        tmp;
X
X	for (tmp = 0; tmp < billct; tmp++)
X		if (bill[tmp].op == obj) {
X			bill[tmp].useup = 1;
X			obj -> unpaid = 0;/* only for doinvbill */
X			return (ONBILL);
X		}
X	return (NOTONBILL);
X}
X
Xdopay () {
X	register unsigned       tmp;
X	char    buffer[BUFSZ];
X
X	multi = 0;
X	if (!inshop ()) {
X		flags.move = 0;
X		pline ("You are not in a shop.");
X		return;
X	}
X
X	if (!shopkeeper || !inshproom (shopkeeper -> mx,
X				shopkeeper -> my)) {
X		pline ("There is nobody here to receive your payment.");
X		return;
X	}
X	if (!billct) {
X		pline ("You do not owe the shopkeeper anything.");
X		if (!u.ugold) {
X			pline ("Moreover, you have no money.");
X			return;
X		}
X		if (robbed) {
X			pline ("But since the shop has been robbed recently");
X			pline ("You %srepay the shopkeeper's expenses.", (u.ugold < robbed) ?
X					"partially " : "");
X			u.ugold -= robbed;
X			if (u.ugold < 0)
X				u.ugold = 0;
X			flags.dgold = 1;
X			robbed = 0;
X			return;
X		}
X		if (shopkeeper -> angry) {
X			pline ("But in order to appease the angry shopkeeper,");
X			if (u.ugold >= 1000L) {
X				tmp = 1000;
X				pline ("You give him 1000 gold pieces.");
X			}
X			else {
X				tmp = (int) u.ugold;
X				pline ("You give him all your money.");
X			}
X			u.ugold -= (long) tmp;
X			flags.dgold = 1;
X			if (rn2 (3)) {
X				pline ("The shopkeeper calms down.");
X				shopkeeper -> angry = 0;
X			}
X			else
X				pline ("The shopkeeper is as angry as ever.");
X		}
X		return;
X	}
X
X	while (billct) {
X		billct--;
X		bill[billct].op -> unpaid = 0;
X		doname (bill[billct].op, buffer);
X		tmp = bill[billct].price;
X		if (shopkeeper -> angry)
X			tmp += tmp / 3;
X		if (u.ugold < tmp) {
X			++bill[billct].op -> unpaid;
X			billct++;
X			pline ("You don't have gold enough to pay %s.",
X					buffer);
X			return;
X		}
X		u.ugold -= tmp;
X		flags.dgold = 1;
X		pline ("You bought %s for %d gold pieces.", buffer, tmp);
X		if (bill[billct].useup)
X			ofree (bill[billct].op);
X	}
X	pline ("Thank you for shopping in Dirk's %s store!",
X			SHOP_NAME);
X	shopkeeper -> angry = 0;
X}
X
Xpaybill () {			/* Called after dying (or quitting) with
X				   nonempty bill */
X	if (shopkeeper) {
X		addupbill ();
X		if (total > u.ugold) {
X			u.ugold = 0;
X			if (invent)
X				pline ("The shopkeeper comes and takes all your possessions.");
X		}
X		else {
X			u.ugold -= total;
X			pline ("The shopkeeper comes and takes the %d zorkmids you owed him.",
X					total);
X		}
X	}
X	more ();
X}
X
Xaddtobill (obj)
Xregister        OBJECT obj;
X{
X	if (!inshop ())
X		return;
X	if (billct == BILLSZ) {
X		pline ("You got that for free!");
X		return;
X	}
X	bill[billct].op = obj;
X	bill[billct].bquan = obj -> quan;
X	bill[billct].useup = 0;
X	bill[billct++].price = getprice (obj);
X	obj -> unpaid = 1;
X}
X
Xsubfrombill (obj)
Xregister        OBJECT obj;
X{
X	register        tmp;
X	register        OBJECT otmp;
X
X	if (!inshop ())
X		return;
X	for (tmp = 0; tmp < billct; tmp++)
X		if (bill[tmp].op == obj) {
X			obj -> unpaid = 0;
X			if (bill[tmp].bquan != obj -> quan) {
X				bill[tmp].op = otmp = newobj ();
X				*otmp = *obj;
X				otmp -> quan = (bill[tmp].bquan -=
X						obj -> quan);
X				bill[tmp].price = bill[tmp].price *
X						  otmp -> quan;
X				bill[tmp].price = bill[tmp].price /
X					  (otmp -> quan + obj -> quan);
X				bill[tmp].useup = 1;
X				return;
X			}
X			billct--;
X			bill[tmp] = bill[billct];
X			return;
X		}
X/* I dropped something of my own, wanting to sell it */
X	if (shopkeeper -> msleep || shopkeeper -> mfroz ||
X			!inshproom (shopkeeper -> mx, shopkeeper -> my) ||
X			robbed || u.ux == shk.x && u.uy == shk.y ||
X			u.ux == shd.x && u.uy == shd.y)
X		return;
X	tmp = getprice (obj);
X	if (shopkeeper -> angry) {
X		tmp /= 3;
X		shopkeeper -> angry = 0;
X	}
X	else
X		tmp >>= 1;
X	if (tmp < 2)
X		tmp = 2;
X	u.ugold += tmp;
X	flags.dgold = 1;
X	doname (obj, buf);
X	pline ("You sold %s and got %d gold pieces.", buf, tmp);
X}
X
Xdoinvbill () {
X	register unsigned       tmp, cnt = 0;
X
X	for (tmp = 0; tmp < billct; tmp++)
X		if (bill[tmp].useup) {
X			if (!cnt && !flags.oneline) {
X				getret ();
X				cls ();
X				printf ("\n\nUnpaid articles already used up:\n\n");
X			}
X			strcpy (buf, "* -  ");
X			doname (bill[tmp].op, &buf[5]);
X			for (cnt = 0; buf[cnt]; cnt++);
X			while (cnt < 50)
X				buf[cnt++] = ' ';
X			sprintf (&buf[cnt], " %5d zorkmids",
X					bill[tmp].price);
X			if (flags.oneline)
X				pline (buf);
X			else
X				printf ("%s\n", buf);
X			if (!cnt % 20)
X				getret ();
X		}
X}
X
Xgetprice (obj)
Xregister        OBJECT obj;
X{
X	register        tmp, ac;
X
X	switch (obj -> olet) {
X		case '"': 
X			tmp = rnd (500);
X			break;
X		case '=': 
X		case '/': 
X			tmp = rnd (100);
X			break;
X		case '?': 
X		case '!': 
X			tmp = rnd (50);
X			break;
X		case '*': 
X			tmp = rnd (6);
X			break;
X		case '%': 
X			tmp = rnd (5 + 2000 / realhunger ());
X			break;
X		case '[': 
X			ac = obj -> spe;
X			tmp = (100 + ac * ac * rnd (10 + ac)) / 10;
X			break;
X		case ')': 
X			if (obj -> otyp <= W_AMMUNITION)
X				tmp = rnd (10);
X			else if (obj -> otyp == W_LONG_SWORD || obj -> otyp ==
X					W_TWOH_SWORD)
X				tmp = rnd (150);
X			else
X				tmp = rnd (75);
X			break;
X		case '_': 
X		default: 
X			tmp = 1000;
X	}
X	return (10 * obj -> quan * tmp);
X}
X
Xrealhunger () {			/* not completely foolproof (??) */
X	register        tmp = u.uhunger;
X	register        OBJECT otmp = invent;
X
X	while (otmp) {
X		if (otmp -> olet == '%' && !otmp -> unpaid)
X			tmp += foods[otmp -> otyp].nutrition;
X		otmp = otmp -> nobj;
X	}
X	return tmp;
X}
X
Xshopinit () {
X	register        MKROOM * sroom = &rooms[shoproom];
X	register        i, j, x, y;
X
X	shlevel = dlevel;
X	shd = doors[sroom -> fdoor];
X	shk.x = shd.x;
X	shk.y = shd.y;
X	if (shk.x == sroom -> lx - 1)
X		shk.x++;
X	else if (shk.x == sroom -> hx + 1)
X		shk.x--;
X	else if (shk.y == sroom -> ly - 1)
X		shk.y++;
X	else if (shk.y == sroom -> hy + 1)
X		shk.y--;
X	else {
X		sroom -> rtype = 0;
X		pline ("Where is shopdoor?");
X		impossible ();
X		return;
X	}
X	if (shopkeeper)
X		return;		/* We have been on this level before */
X	if (makemon (&shk_pm))
X		panic (CORE, "Cannot create shopkeeper?");
X	shopkeeper = fmon;
X	shopkeeper -> angry = u.uhcursed;
X	if (m_at (shk.x, shk.y) || (shk.x == u.ux && shk.y == u.uy)) {
X	/* (a3)`mnexto(shopkeeper)' is fout gaan */
X		prl (shk.x, shk.y);
X		for (i = -1; i < 2; i++)
X			for (j = -1; j < 2; j++)
X				if (levl[x = shk.x + i][y = shk.y + j].typ ==
X						ROOM)
X					if (!m_at (x, y)) {
X						fmon -> mx = x;
X						fmon -> my = y;
X						pmon (shopkeeper);
X						return;
X					}
X		fmon -> mx = shk.x;
X		fmon -> my = shk.y;
X		return;		/* bovenop een ander monster */
X	}
X	else {
X		fmon -> mx = shk.x;
X		fmon -> my = shk.y;
X	}
X	pmon (shopkeeper);
X}
X
Xsetangry () {
X	if (shopkeeper -> data -> mlet == '@' && !shopkeeper -> angry) {
X		pline ("The shopkeeper gets angry.");
X		++shopkeeper -> angry;
X	}
X}
X
Xshk_move () {
X	register        MONSTER mtmp;
X	char    gx, gy, omx, omy, cnt, appr,
X	        nix, niy, ddx, ddy, zx, zy, num;
X
X	omx = shopkeeper -> mx;
X	omy = shopkeeper -> my;
X	if (!u.uinshop && inshproom (omx, omy) &&
X			levl[omx][omy].typ == ROOM)
X		return NOMOVE;
X	if (shopkeeper -> angry && dist (omx, omy) < 3) {
X		hitu (shk_pm.mhd, d (shk_pm.damn, shk_pm.damd),
X				shk_pm.mname);
X		return NOMOVE;
X	}
X	appr = 1;
X	if ((shopkeeper -> angry) && !u.uinvis) {
X		gx = u.ux;	/* Fred */
X		gy = u.uy;
X	}
X	else if (shk.x == omx && shk.y == omy && !billct &&
X				!shopkeeper -> angry &&
X				(!robbed || (u.ux == shd.x && u.uy == shd.y)) &&
X			dist (omx, omy) < 3) {
X		appr = 0;
X		gx = 0;
X		gy = 0;
X	}
X	else {
X		gx = shk.x;
X		gy = shk.y;
X	}
X	cnt = 0;
X	if (omx == gx && omy == gy)
X		return NOMOVE;
X	if (shopkeeper -> mconf)
X		appr = 0;
X	nix = omx;
X	niy = omy;
X	for (ddx = -1; ddx <= 1; ddx++)
X		for (ddy = -1; ddy <= 1; ddy++) {
X			zx = omx + ddx;
X			zy = omy + ddy;
X			num = levl[zx][zy].typ;/* a3 */
X			if ((ddx || ddy) && (num == ROOM || !inshproom (omx, omy)
X						&& (num == CORR || num == DOOR)) &&
X					(shopkeeper -> mconf ||
X						((zx != u.ux || zy != u.uy) && !m_at (zx, zy))) &&
X					(!appr && !rn2 (++cnt) || appr && GDIST (zx, zy) <
X						GDIST (nix, niy))) {
X				nix = zx;
X				niy = zy;
X			}
X		}
X	if (nix != omx || niy != omy) {
X		if (shopkeeper -> mconf && (mtmp = m_at (nix, niy))) {
X			if (hitmm (shopkeeper, mtmp) == 1 && rn2 (3)
X					&& hitmm (mtmp, shopkeeper) == DEAD)
X				return DEAD;
X			return NOMOVE;
X		}
X		shopkeeper -> mx = nix;
X		shopkeeper -> my = niy;
X/* The shopkeeper might have been turned into an X */
X		levlsym (omx, omy, shopkeeper -> data -> mlet);
X		pmon (shopkeeper);
X		return MOVE;
X	}
X	return NOMOVE;
X}
SHAR_EOF
if test 10486 -ne "`wc -c 'hack.shk.c'`"
then
	echo shar: error transmitting "'hack.shk.c'" '(should have been 10486 characters)'
fi
#	End of shell archive
exit 0