Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

PC/IX Hack (3 of 5)

2 views
Skip to first unread message

pet...@pbear.uucp

unread,
May 28, 1985, 6:06:00 PM5/28/85
to

#!/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.h
# hack.invent.c
# hack.invinit.c
# hack.io.c
# hack.lev.c
# hack.main.c
# hack.mkobj.c
# hack.mon.c
# hack.mon.do.c
# This archive created: Tue May 28 17:52:45 1985
export PATH; PATH=/bin:$PATH
echo shar: extracting "'hack.h'" '(6911 characters)'
if test -f 'hack.h'
then
echo shar: over-writing existing file "'hack.h'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.h'
X/*
X * Hack.h
X */
X
X/* #define NORMAL_IO */
X#ifdef NORMAL_IO
X
X#include <stdio.h>
X#define flush() fflush( stdout )
X
X#else
X
X#undef putchar
X#undef getchar
X#define NULL 0
X#define STDOUT 0 /* Defines print in I/O packet */
X
X#endif NORMAL_IO
X
X#include "envir.h"
X#include "hack.name.h"
Xchar *strchr();
X#define index(s,c) strchr(s,c)
X
Xlong pow ();
X
X#define BUFSZ 256
X
X
X/* Arguments for panic to give just an error message or a core dump */
X#define NOCORE 0
X#define CORE 1
X
X#define ON 1
X#define OFF 0
X
X#define WALL 1
X#define SDOOR 2
X#define DOOR 3
X#define CORR 4
X#define ROOM 5
X#define POOL 7
X#define VAULT 9
X
X#define TRAPNUM 9
X
X#define MSLOW 1
X#define MFAST 2
X
X#define BEAR 0
X#define ARROW 1
X#define DART 2
X#define TDOOR 3
X#define TELE 4
X#define PIT 5
X#define SLPTRP 6
X#define PIERC 7
X#define MIMIC 8
X#define SEEN 32
X
X#define UWEP 0
X#define UARM 1
X#define UARM2 2
X#define ULEFT 3
X#define URIGHT 4
X
X#define POTN 1
X#define SCRN 2
X#define WANN 4
X#define RINN 8
X
X#define UNC 1 /* unCoff(): */
X#define COFF 0
X
X#define SETC 1 /* setCon(): */
X#define CON 0
X
X#define IT1 1
X#define THEIT2 2 /* kluns */
X
X#define CHOKED 0
X#define DIED 1
X#define STARVED 2
X#define DROWNED 3
X#define QUIT 4 /* Michiel args how you died */
X#define ESCAPED 5
X
X#define NOMOVE 0
X#define MOVE 1
X#define DEAD 2
X
X#define MISS 0
X#define HIT 1
X#define KILL 2
X
X
X
Xtypedef struct func_tab {
X char f_char;
X int (*f_funct) ();
X} FUNCTIONS;
Xextern FUNCTIONS list[];
X
X
X
Xstruct rm {
X unsigned scrsym;
X unsigned typ;
X unsigned new: 1;
X unsigned seen: 1;
X unsigned lit: 1;
X};
Xtypedef struct rm PART;
Xextern PART levl[80][22];
X
X
X
X
Xstruct mkroom {
X char lx, hx, ly, hy, rtype, rlit, doorct, fdoor;
X};
Xtypedef struct mkroom MKROOM;
Xextern MKROOM rooms[15];
X
X
X
X#define DOORMAX 100
Xstruct coord {
X char x, y;
X};
Xtypedef struct coord COORDINATES;
Xextern COORDINATES doors[DOORMAX];
X
X
X
Xstruct food {
X char *foodnam, prob, delay;
X int nutrition;
X};
Xtypedef struct food *FOOD;
Xextern struct food foods[];
X
X
X
Xstruct armor {
X char *armnam, prob, delay, a_ac, a_can;
X};
Xtypedef struct armor *ARMOR;
Xextern struct armor armors[];
X
X
X
X
X
Xstruct weapon {
X char *wepnam, prob, wsdam, wldam;
X};
Xtypedef struct weapon *WEAPON;
Xextern struct weapon weapons[];
X
X
X
X
Xstruct permonst {
X char *mname, mlet, mhd, mmove, ac, damn, damd;
X unsigned pxlth;
X};
Xtypedef struct permonst *MONSTDATA;
Xextern struct permonst mon[8][7];
X#define PM_MIMIC &mon[5][2]
X#define PM_PIERC &mon[2][3]
X#define PM_DEMON &mon[7][6]
X#define PM_CHAM &mon[6][6]
X
X
X
X
Xstruct obj {
X struct obj *nobj;
X char otyp;
X int spe;
X unsigned ox: 7;
X unsigned oy: 5;
X unsigned olet: 7;
X unsigned quan: 5;
X unsigned known: 1;
X unsigned cursed: 1;
X unsigned unpaid: 1;
X};
Xtypedef struct obj *OBJECT;
Xextern OBJECT fobj, invent, uwep, uarm, uarm2, uleft, uright;
X
X
X
Xstruct stole {
X OBJECT sobj;
X unsigned sgold;
X};
Xtypedef struct stole *STOLE;
X
X
Xstruct monst {
X struct monst *nmon;
X MONSTDATA data;
X STOLE mstole;
X char mx, my;
X int mhp, orig_hp;
X unsigned invis: 1;
X unsigned cham: 1;
X unsigned angry: 1; /* Michiel: only for shopkeeper */
X unsigned ale: 1; /* Michiel: is it an ale?? */
X unsigned mspeed: 2;
X unsigned msleep: 1;
X unsigned mfroz: 1;
X unsigned mconf: 1;
X unsigned mflee: 1;
X unsigned mcan: 1;
X unsigned mtame: 1;
X unsigned wormno: 5;
X unsigned mxlth;
X char mextra[1];
X};
Xtypedef struct monst *MONSTER;
Xextern MONSTER fmon, shopkeeper, vaultkeeper;
Xextern struct permonst treasurer;
X
XMONSTER m_at ();
X
X
X
Xstruct wseg {
X struct wseg *nseg;
X char wx, wy;
X};
X
Xtypedef struct wseg *WORMSEGMENT;
X
X#define newseg() (alloc( sizeof(struct wseg) )->Wseg)
X
X
Xstruct gen {
X struct gen *ngen;
X char gx, gy;
X unsigned gflag;
X};
Xtypedef struct gen *GOLD_TRAP;
Xextern GOLD_TRAP fgold, ftrap;
X
XGOLD_TRAP g_at ();
XOBJECT o_at (), getobj ();
X
X
Xstruct flag {
X unsigned topl: 1;
X unsigned botl: 1;
X /* faint:1, screen:1, */
X unsigned oneline: 1;
X unsigned next: 1;
X unsigned move: 1;
X unsigned mv: 1;
X unsigned run: 2;
X unsigned dgold: 1;
X unsigned dhp: 1;
X unsigned dhpmax: 1;
X unsigned dstr: 1;
X unsigned dac: 1;
X unsigned dulev: 1;
X unsigned dexp: 1;
X unsigned dhs: 1;
X unsigned dscr: 1;
X};
Xtypedef struct flag FLAG;
Xextern FLAG flags;
X
Xstruct you {
X char ux, uy, ustr, ustrmax, udaminc, uac;
X int uhunger;
X unsigned ufast: 7;
X unsigned uconfused: 6;
X unsigned uinvis: 6;
X unsigned ulevel: 5;
X unsigned utrap: 3;
X unsigned upit: 1;
X unsigned uinshop: 1;
X unsigned uinzoo: 1;
X unsigned uinyard: 1;
X unsigned uinswamp: 1;
X unsigned uinknox: 1;
X unsigned umconf: 1;
X unsigned uhcursed: 1;
X unsigned ufireres: 1;
X unsigned ucoldres: 1;
X unsigned utel: 1;
X unsigned upres: 1;
X unsigned ustelth: 1;
X unsigned uagmon: 1;
X unsigned ufeed: 1;
X unsigned usearch: 1;
X unsigned ucinvis: 1;
X unsigned uregen: 1;
X unsigned ufloat: 1;
X unsigned uswallow: 1;
X unsigned uswldtim: 4;
X unsigned ucham: 1;
X unsigned uhs: 2;
X unsigned ublind;
X short uhp, uhpmax;
X long ugold, uexp, urexp;
X MONSTER ustuck;
X};
Xtypedef struct you YOU;
Xextern YOU u;
X
X
X
Xextern char *wepnam[], *pottyp[], *scrtyp[], *traps[],
X *wantyp[], *ringtyp[], *potcol[], *scrnam[],
X *wannam[], *rinnam[], wdam[], oiden[],
X *potcall[], *scrcall[], *wandcall[], *ringcall[],
X curx, cury, savx,
X xdnstair, ydnstair, xupstair, yupstair,
X seehx, seelx, seehy, seely,
X *save_cm, *killer, dlevel, maxdlevel,
X dx, dy, buf[], lock[],
X genocided[60], oldux, olduy, wizard;
X
Xextern unsigned moves;
X
Xextern multi;
X
X#define newmonst(xl) (alloc( xl + sizeof(struct monst) )->Mtmp )
X#define newobj() (alloc( sizeof(struct obj) )->Otmp )
X#define newgen() (alloc( sizeof(struct gen) )->Gtmp )
X#define newstole() (alloc( sizeof(struct stole) )->Stmp )
X
X
X#define CHAR_NULL (char *)NULL
X#define OBJ_NULL (struct obj *)NULL
X#define TRAP_NULL (struct gen *)NULL
X#define MON_NULL (struct monst *)NULL
X#define STOLE_NULL (struct stole *)NULL
X
X#ifndef SHOW
Xunion PTRS {
X GOLD_TRAP Gtmp;
X MONSTER Mtmp;
X OBJECT Otmp;
X STOLE Stmp;
X WORMSEGMENT Wseg;
X char *Val;
X};
X
Xextern union PTRS * alloc ();
X#endif SHOW
SHAR_EOF
if test 6911 -ne "`wc -c 'hack.h'`"
then
echo shar: error transmitting "'hack.h'" '(should have been 6911 characters)'
fi
echo shar: extracting "'hack.invent.c'" '(5532 characters)'
if test -f 'hack.invent.c'
then
echo shar: over-writing existing file "'hack.invent.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.invent.c'
X/*
X * Hack.invent.c
X */
X
X#include "hack.h"
X
X#define NOT_AT 0
X#define NO_OBJ 0
X
Xextern WORMSEGMENT wsegs[32];
X
Xextern OBJECT yourinvent0;
X
XOBJECT addinv (obj)
Xregister OBJECT obj;
X{
X register OBJECT otmp;
X
X for (otmp = invent; otmp; otmp = otmp -> nobj) {
X if (otmp -> otyp == obj -> otyp && otmp -> olet == obj -> olet
X && !obj -> unpaid && !otmp -> unpaid &&
X ((obj -> otyp < F_COOKIE &&
X obj -> olet == ')' &&
X obj -> quan + otmp -> quan < 32 &&
X obj -> spe == otmp -> spe) ||
X index ("%?!*", otmp -> olet))) {
X otmp -> quan += obj -> quan;
X ofree (obj);
X return otmp;
X }
X if (!otmp -> nobj) {
X otmp -> nobj = obj;
X obj -> nobj = 0;
X return obj;
X }
X }
X invent = obj;
X obj -> nobj = 0;
X return obj;
X}
X
Xuseup (obj)
Xregister OBJECT obj;
X{
X register OBJECT otmp;
X
X if (obj -> quan > 1) {
X obj -> quan--;
X return;
X }
X if (obj == invent)
X invent = invent -> nobj;
X else {
X for (otmp = invent; otmp -> nobj != obj;
X otmp = otmp -> nobj);
X otmp -> nobj = obj -> nobj;
X }
X if (!onbill (obj))
X ofree (obj);
X}
X
Xdelobj (obj)
Xregister OBJECT obj;
X{
X freeobj (obj);
X ofree (obj);
X}
X
Xofree (obj)
Xregister OBJECT obj;
X{
X if (obj > yourinvent0)
X free (obj);
X}
X
X/* Unlink obj from chain starting with fobj */
X
Xfreeobj (obj)
Xregister OBJECT obj;
X{
X register OBJECT otmp;
X
X if (obj == fobj)
X fobj = fobj -> nobj;
X else {
X for (otmp = fobj; otmp -> nobj != obj; otmp = otmp -> nobj)
X if (!otmp)
X panic (CORE, "Try to free non-existing object");
X otmp -> nobj = obj -> nobj;
X }
X}
X
Xdeltrap (trap)
Xregister GOLD_TRAP trap;
X{
X register GOLD_TRAP gtmp;
X
X if (trap == ftrap)
X ftrap = ftrap -> ngen;
X else {
X for (gtmp = ftrap; gtmp -> ngen != trap;
X gtmp = gtmp -> ngen);
X gtmp -> ngen = trap -> ngen;
X }
X free (trap);
X}
X
XMONSTER m_at (x, y)
Xregister x, y;
X{
X register MONSTER mtmp;
X register WORMSEGMENT wtmp;
X
X for (mtmp = fmon; mtmp; mtmp = mtmp -> nmon) {
X if (mtmp -> mx == x && mtmp -> my == y)
X return (mtmp);
X if (mtmp -> wormno)
X for (wtmp = wsegs[mtmp -> wormno]; wtmp;
X wtmp = wtmp -> nseg)
X if (wtmp -> wx == x && wtmp -> wy == y)
X return (mtmp);
X }
X return (NOT_AT);
X}
X
XOBJECT o_at (x, y)
Xregister x, y;
X{
X register OBJECT otmp;
X
X for (otmp = fobj; otmp; otmp = otmp -> nobj)
X if (otmp -> ox == x && otmp -> oy == y)
X return (otmp);
X return (NOT_AT);
X}
X
XGOLD_TRAP g_at (x, y, ptr)
Xregister x, y;
Xregister GOLD_TRAP ptr;
X{
X while (ptr) {
X if (ptr -> gx == x && ptr -> gy == y)
X return (ptr);
X ptr = ptr -> ngen;
X }
X return (NOT_AT);
X}
X
XOBJECT getobj (let, word)
Xregister char *let, *word;
X{
X register OBJECT otmp;
X register char ilet, ilet1, ilet2;
X char buffer[BUFSZ], allowall = 0;
X register foo = 0, foo2;
X
X if (*let == '#') {
X let++;
X allowall++;
X }
X ilet = 'a';
X for (otmp = invent; otmp; otmp = otmp -> nobj) {
X if (!let || index (let, otmp -> olet))
X buffer[foo++] = ilet;
X if (ilet == 'z')
X ilet = 'A';
X else
X ilet++;
X }
X buffer[foo] = 0;
X if (foo > 5) { /* Compactify string */
X foo = foo2 = 1;
X ilet2 = buffer[0];
X ilet1 = buffer[1];
X while (ilet = buffer[++foo2] = buffer[++foo]) {
X if (ilet == ilet1 + 1) {
X if (ilet1 == ilet2 + 1)
X buffer[foo2 - 1] = ilet1 = '-';
X else if (ilet2 == '-') {
X buffer[--foo2] = ++ilet1;
X continue;
X }
X }
X ilet2 = ilet1;
X ilet1 = ilet;
X }
X }
X if (!foo && !allowall) {
X pline ("You don't have anything to %s.", word);
X return (NO_OBJ);
X }
X for (;;) {
X pline ((foo) ? "What do you want to %s [%s or ?]? " :
X "What do you want to %s? ", word, buffer);
X flags.topl = 0;
X flush ();
X ilet = getchar ();
X if (ilet == '\33' || ilet == ' ' || ilet == '\n')
X if (strcmp (word, "identify"))
X return (NO_OBJ);
X else
X continue;/* sukkel */
X if (ilet == '?')
X doinv (foo ? let : 0, 0);
X else {
X if (ilet >= 'A' && ilet <= 'Z')
X ilet += 26 - 'A';
X else
X ilet -= 'a';
X for (otmp = invent; otmp && ilet; ilet--,
X otmp = otmp -> nobj);
X if (!otmp) {
X pline ("You don't have that object.");
X continue;
X }
X break;
X }
X }
X if (!allowall && let && !index (let, otmp -> olet)) {
X pline ("That is a silly thing to %s.", word);
X return (NO_OBJ);
X }
X return (otmp);
X}
X
Xprinv (obj)
Xregister OBJECT obj;
X{
X register OBJECT otmp;
X register char ilet = 'a';
X
X for (otmp = invent; otmp != obj; otmp = otmp -> nobj)
X if (++ilet > 'z')
X ilet = 'A';
X prname (obj, ilet, 1);
X}
X
Xprname (obj, let, onelin)
Xregister OBJECT obj;
Xregister char let;
X{
X char li[BUFSZ];
X
X doname (obj, buf);
X sprintf (li, "%c - %s.", let, buf);
X if (onelin)
X pline (li);
X else
X printf ("%s\n", li);
X}
X
Xddoinv () {
X nomove ();
X if (!invent)
X pline ("You are empty handed.");
X else
X doinv (0, 1);
X}
X
X/*
X * Page inventory done by Fred
X *
X */
X
Xdoinv (str, opt)
Xregister char *str;
Xint opt;
X{
X register OBJECT otmp;
X register char ilet = 'a';
X register int count = 1;
X int ct = 0;
X
X if (!flags.oneline)
X for (otmp = invent; otmp; otmp = otmp -> nobj)
X if (!str || index (str, otmp -> olet))
X ct++;
X if (ct > 1)
X cls ();
X for (otmp = invent; otmp; otmp = otmp -> nobj) {
X if (!str || index (str, otmp -> olet)) {
X prname (otmp, ilet, ct <= 1);
X count++;
X }
X if (++ilet > 'z')
X ilet = 'A';
X if (!(count % 22) && otmp -> nobj) {
X getret ();
X cls (); /* M. F. Page listing */
X }
X }
X if (!str && opt)
X doinvbill ();
X if (ct > 1) {
X getret ();
X docrt ();
X }
X}
SHAR_EOF
if test 5532 -ne "`wc -c 'hack.invent.c'`"
then
echo shar: error transmitting "'hack.invent.c'" '(should have been 5532 characters)'
fi
echo shar: extracting "'hack.invinit.c'" '(649 characters)'
if test -f 'hack.invinit.c'
then
echo shar: over-writing existing file "'hack.invinit.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.invinit.c'
X/*
X * Hack.invinit.c
X */
X
X#include "hack.h"
X
X/*
X * struct obj {
X * struct obj *nobj;
X * char otyp, spe;
X * ox, oy, olet, quan, known, cursed, unpaid
X * };
X */
X
Xstruct obj arrows0 = {
X (struct obj *)0,
X W_ARROW, 0, 0, 0, ')', 25, 1, 0, 0 /* 25 +0 arrows */
X};
X
Xstruct obj bow0 = {
X &arrows0,
X W_BOW, 1, 0, 0, ')', 1, 1, 0, 0 /* +1 bow */
X};
X
Xstruct obj mace0 = {
X &bow0,
X W_MACE, 1, 0, 0, ')', 1, 1, 0, 0 /* +1 mace */
X};
X
Xstruct obj uarm0 = {
X &mace0,
X A_RING, 4, 0, 0, '[', 1, 1, 0, 0 /* +1 ring mail */
X};
X
Xstruct obj food0 = {
X &uarm0,
X F_FOOD, 0, 0, 0, '%', 2, 1, 0, 0 /* 2 food rations */
X};
X
Xstruct obj *yourinvent0 = &food0;
SHAR_EOF
if test 649 -ne "`wc -c 'hack.invinit.c'`"
then
echo shar: error transmitting "'hack.invinit.c'" '(should have been 649 characters)'
fi
echo shar: extracting "'hack.io.c'" '(1559 characters)'
if test -f 'hack.io.c'
then
echo shar: over-writing existing file "'hack.io.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.io.c'
X/*
X * Hack.io.c
X */
X
X#include "hack.h"
X#include <termio.h>
X
Xshort ospeed; /* Used by tputs */
X
Xgetlin (str)
Xregister char *str;
X{
X register char *ostr = str;
X
X flags.topl = 0;
X flush ();
X for (;;) {
X *str = getchar ();
X if (*str == '\b') {
X if (str != ostr) {
X str--;
X write (1, "\b \b", 3);
X }
X else
X write (1, "\7", 1);
X }
X else if (*str == '\n') {
X *str = 0;
X return;
X }
X else if (*str >= ' ') {
X write (1, str, 1);
X str++;
X }
X }
X}
X
Xgetret () {
X printf ("\nHit space to continue: ");
X flush ();
X while (getchar () != ' ');
X}
X
Xstruct termio ttyo;
Xh_io_init() {
X ioctl(1, TCGETA, &ttyo);
X}
X
X
X/*
X * Put together cbreak-mode and echo --- Michiel
X */
X
X int speed_table[] = { 0, 50, 75, 110, 134, 150, 200, 300, 600,
X 1200, 1800, 2400, 4800, 9600, 0, 0 };
X
Xhackmode (x)
Xregister x;
X{
X struct termio ttyp;
X
X ioctl (1, TCGETA, &ttyp);/* Use of basic functions */
X ospeed = ttyp.c_cflag & 017; /* mask out other bits */
X ospeed = speed_table[ospeed];
X if (x) {
X ttyp.c_lflag &= ~ (ECHO | ICANON);
X ttyp.c_cc[4]=0;
X ttyp.c_cc[5]=0; /* set min and time to 0 */
X }
X else {
X ttyp.c_lflag = ttyo.c_lflag; /* reset back to original */
X ttyp.c_cc[4]=ttyo.c_cc[4]; /* set EOF */
X ttyp.c_cc[5]=ttyo.c_cc[5]; /* set EOL */
X }
X if (ioctl (1, TCSETA, &ttyp) < 0) {
X printf ("ERROR: Cannot change tty");
X exit (1);
X }
X}
X
Xmore () {
X printf (" --More--");
X flush ();
X while (getchar () != ' ');
X flags.topl = 0;
X}
X
X#ifndef NORMAL_IO
Xgetchar () {
X char c;
X
X read (0, &c, 1);
X return (c);
X}
X#endif NORMAL_IO
SHAR_EOF
if test 1559 -ne "`wc -c 'hack.io.c'`"
then
echo shar: error transmitting "'hack.io.c'" '(should have been 1559 characters)'
fi
echo shar: extracting "'hack.lev.c'" '(4721 characters)'
if test -f 'hack.lev.c'
then
echo shar: over-writing existing file "'hack.lev.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.lev.c'
X/*
X * Hack.lev.c
X */
X
X#include "hack.h"
X#include <signal.h>
X
X#define MAXLEVEL 40
X#define ERROR 1
X#define OK 0
X
Xextern char *itoa (), nul[], upxstairs[MAXLEVEL], upystairs[MAXLEVEL];
X
Xextern WORMSEGMENT wsegs[32], wheads[32];
Xextern unsigned wgrowtime[32];
Xextern struct permonst pm_ghost;
X
X#include "hack.savelev.c"
X
Xstruct permonst pm_ale = {
X "giant eel", ';', 15, 6, -3, 3, 6, 0
X};
X
Xgetlev (fd) {
X register MONSTER mtmp;
X register GOLD_TRAP gtmp;
X register OBJECT otmp;
X register WORMSEGMENT wtmp;
X int tmp, xl;
X unsigned tmoves, omoves;
X STOLE stmp;
X
X if (fd < 0 || read (fd, levl, sizeof (levl)) != sizeof (levl))
X return ERROR;
X fmon = 0;
X fobj = 0;
X fgold = 0;
X ftrap = 0;
X shopkeeper = 0;
X vaultkeeper = 0;
X mread (fd, &omoves, sizeof (unsigned));
X mread (fd, &xupstair, 1);
X mread (fd, &yupstair, 1);
X mread (fd, &xdnstair, 1);
X mread (fd, &ydnstair, 1);
X if (omoves)
X tmoves = (moves > omoves) ? moves - omoves : 0;
X for (;;) {
X mread (fd, &xl, sizeof (int));
X if (xl == -1)
X break;
X mtmp = newmonst (xl);
X mread (fd, mtmp, xl + sizeof (struct monst));
X
X/* Michiel restore stolen objects */
X stmp = newstole ();
X mread (fd, stmp, sizeof (struct stole));
X if (stmp -> sgold || stmp -> sobj) {
X mtmp -> mstole = stmp;
X mtmp -> mstole -> sobj = 0;
X for (;;) {
X otmp = newobj ();
X mread (fd, otmp, sizeof (struct obj));
X if (!otmp -> olet)
X break;
X otmp -> nobj = mtmp -> mstole -> sobj;
X mtmp -> mstole -> sobj = otmp;
X }
X ofree (otmp);
X }
X else
X free (stmp);
X/* Regenerate animals if you've been on another level */
X if (omoves) {
X if (!index (genocided, mtmp -> data -> mlet)) {
X if (index ("ViT", mtmp -> data -> mlet))
X mtmp -> mhp += mtmp -> mhp + tmoves;
X else
X mtmp -> mhp += tmoves / 20;
X if (mtmp -> mhp > mtmp -> orig_hp)
X mtmp -> mhp = mtmp -> orig_hp;
X if (mtmp -> data -> mlet == '@') {
X if (*mtmp -> data -> mname == 's')
X shopkeeper = mtmp;
X else if (*mtmp -> data -> mname == 'v')
X vaultkeeper = mtmp;
X }
X mtmp -> nmon = fmon;
X fmon = mtmp;
X }
X }
X else { /* Convert code from MKLEV */
X if (mtmp -> mhp == 10)
X mtmp -> data = &pm_ghost;
X else if (mtmp -> ale)
X mtmp -> data = &pm_ale;
X else
X mtmp -> data = &mon[mtmp -> mhp][mtmp -> orig_hp];
X if (mtmp -> data -> mlet == 'D')
X mtmp -> mhp = 80;
X else
X mtmp -> mhp = mtmp -> data -> mhd ?
X d (mtmp -> data -> mhd, 8) : rnd (4);
X mtmp -> orig_hp = mtmp -> mhp;
X mtmp -> cham = (mtmp -> data -> mlet == ':');
X mtmp -> invis = (mtmp -> data -> mlet == 'I');
X if (mtmp -> data -> mlet == 'w' &&
X getwn (mtmp))
X initworm (mtmp);
X mtmp -> nmon = fmon;
X fmon = mtmp;
X }
X }
X for (;;) {
X gtmp = newgen ();
X mread (fd, gtmp, sizeof (struct gen));
X if (!gtmp -> gx)
X break;
X gtmp -> ngen = fgold;
X fgold = gtmp;
X }
X for (;;) {
X mread (fd, gtmp, sizeof (struct gen));
X if (!gtmp -> gx)
X break;
X gtmp -> ngen = ftrap;
X ftrap = gtmp;
X gtmp = newgen ();
X }
X free (gtmp);
X for (;;) {
X otmp = newobj ();
X mread (fd, otmp, sizeof (struct obj));
X if (!otmp -> olet)
X break;
X otmp -> nobj = fobj;
X fobj = otmp;
X }
X ofree (otmp);
X mread (fd, rooms, sizeof (rooms));
X mread (fd, doors, sizeof (doors));
X if (!omoves)
X return OK; /* From MKLEV */
X mread (fd, wsegs, sizeof (wsegs));
X for (tmp = 1; tmp < 32; tmp++)
X if (wsegs[tmp]) {
X wheads[tmp] = wsegs[tmp] = wtmp = newseg ();
X for (;;) {
X mread (fd, wtmp, sizeof (struct wseg));
X if (!wtmp -> nseg)
X break;
X wheads[tmp] -> nseg = wtmp = newseg ();
X wheads[tmp] = wtmp;
X }
X }
X mread (fd, wgrowtime, sizeof (wgrowtime));
X return OK;
X}
X
Xmread (fd, buffer, len)
Xregister fd, len;
Xregister char *buffer;
X{
X register rlen;
X
X if ((rlen = read (fd, buffer, len)) != len)
X panic (CORE, "Read %d instead of %d bytes from file #%d\n",
X rlen, len, fd);
X}
X
Xmklev () {
X register fd;
X char type[2];
X
X#ifndef DEBUG
X if (getbones ()) {
X sleep (2);
X goto Z;
X }
X#endif DEBUG
X if (flags.next) {
X flags.next = 0;
X type[0] = 'b';
X }
X else if (dlevel < rn1 (3, MAXLEVEL - 3))
X type[0] = 'a';
X else {
X type[0] = 'n';
X flags.next = 1;
X }
X type[1] = '\0';
X hackexec (0, "./mklev", lock, type, itoa (dlevel), genocided,
X wizard ? "w" : "", NULL);
X if ((fd = open (lock, 0)) < 0) {
X pline ("Can't open %s! Second try.", lock);
X flush ();
X hackexec (0, "./mklev", lock, type, itoa (dlevel), genocided,
X wizard ? "w" : "", NULL);
X if ((fd = open (lock, 0)) < 0)
X panic (NOCORE, "Mklev error no level");
X }
X getlev (fd);
X close (fd);
XZ:
X if (!upxstairs[dlevel] && !upystairs[dlevel]) {
X upxstairs[dlevel] = xupstair;
X upystairs[dlevel] = yupstair;
X }
X}
SHAR_EOF
if test 4721 -ne "`wc -c 'hack.lev.c'`"
then
echo shar: error transmitting "'hack.lev.c'" '(should have been 4721 characters)'
fi
echo shar: extracting "'hack.main.c'" '(5621 characters)'
if test -f 'hack.main.c'
then
echo shar: over-writing existing file "'hack.main.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.main.c'
X/*
X * Hack.main.c
X */
X
X#include <signal.h>
X#include "hack.h"
X
X#define exception( id ) ( id == uid )
X#define HUISJES 2201
X#define WILDE 2216
X
Xextern char *hu_stat[4], *getenv (), *malloc (), *parse ();
X
Xint rfile;
X
XCOORDINATES doors[DOORMAX];
X
XPART levl[80][22];
XMKROOM rooms[15];
XMONSTER fmon = 0;
XGOLD_TRAP fgold = 0, ftrap = 0;
XFLAG flags;
XYOU u;
XOBJECT fobj = 0, invent, uwep, uarm,
Xuarm2 = 0, uright = 0, uleft = 0;
X
Xextern OBJECT yourinvent0;
Xextern struct obj mace0, uarm0;
X
Xchar nul[20]; /* Contains zeros */
X/* Lock contains 'pid'.dlevel */
Xchar plname[10], lock[16], wizard,
X curx, cury, savx,
X xupstair, yupstair, xdnstair, ydnstair,
X *save_cm = 0, *killer, *nomvmsg, dlevel = 0,
X dx, dy, buf[BUFSZ], genocided[60],
X SAVEFILE[37] = SAVEDIR;
X
Xunsigned moves = 1;
X
Xint multi = 0, done1 (), hangup (), hackpid;
Xint uid;
X
Xmain (argc, argv)
Xchar *argv[];
X{
X int fd;
X char *getlogin();
X register char *yourname = getlogin ();
X
X uid = getuid ();
X /*
X * Check on UID's
X */
X
X/* if (kantoor () && !exception (HUISJES) && !exception (WILDE)) {
X printf ("Sorry, You can't play hack now\n" );
X flush ();
X exit (0);
X } */
X
X if (!access (LOCK, 0) && strcmp (WIZARD, yourname)) {
X printf ("Sorry, I'm busy with debugging.\nTry again later.\n");
X flush ();
X exit (0);
X }
X h_io_init(); /* grab copy of termio struct */
X strncpy (plname, yourname, sizeof (plname) - 1);
X#ifdef WIZARD
X while (argc > 1 && **++argv == '-') {
X switch (argv[0][1]) {
X case 'w':
X if (!exception (HUISJES) && !exception (WILDE) && strcmp (yourname, WIZARD))
X printf ("Sorry\n");
X else {
X strcpy (plname, "wizard");
X wizard++;
X }
X break;
X default:
X printf ("Unknown option: %s\n", *argv);
X }
X flush ();
X }
X#endif WIZARD
X
X if (chdir (PLAYGROUND) < 0)
X panic (NOCORE, "Cannot chdir to %s!", PLAYGROUND);
X if ((rfile = open (RECORD, 2)) < 0)
X panic (NOCORE, "Can't open %s!", RECORD);
X setuid (getuid ());
X umask (0);
X srand (hackpid = getpid ());
X startup ();
X signal (SIGHUP, hangup);
X signal (SIGINT, done1);
X hackmode (ON);
X if (!wizard) {
X cls ();
X flush ();
X }
X strcat (SAVEFILE, plname);
X fd = open (SAVEFILE, 0);
X if (fd >= 0) {
X if (dorecover (fd) < 0)
X goto normalplay;
X flags.move = 0;
X }
X else {
Xnormalplay:
X shuffle ();
X invent = yourinvent0;
X uwep = &mace0;
X uarm = &uarm0;
X u.uac = 6; /* 10 - uarm->spe */
X u.ulevel = 1;
X u.uhunger = 900;
X u.uhpmax = u.uhp = 12;
X u.ustrmax = u.ustr = rn2 (20) ? 16 : rn1 (7, 14);
X flags.move = 1;
X dodown (); /* a3 */
X cls ();
X setCon (SETC);
X flags.botl = 1;
X makedog ();
X }
X for (;;) {
X if (flags.move) {
X if (!u.ufast || moves % 2 == 0) {
X if (fmon)
X movemon ();
X if (!rn2 (70)) {
X makemon (0);
X fmon -> mx = 0;
X fmon -> my = 0;
X rloc (fmon);
X seeatl (fmon -> mx, fmon -> my,
X fmon -> data -> mlet);
X }
X }
X if (u.ufast && !--u.ufast)
X pline ("You feel yourself slowing down");
X if (u.uconfused && !--u.uconfused)
X pline ("You feel less confused now");
X if (u.ublind && !--u.ublind) {
X pline ("You can see again");
X if (!u.uswallow)
X setCon (SETC);
X }
X if (u.uinvis && !--u.uinvis) {
X if (!u.uswallow)
X on (u.ux, u.uy);
X pline ("You are no longer invisible");
X }
X ++moves;
X if (u.uhp <= 0) {
X pline ("You die...");
X more ();
X done (DIED);
X }
X if (u.uhp < u.uhpmax) {
X if (u.ulevel > 9) {
X if (u.uregen || moves % 3 == 0) {
X flags.dhp = 1;
X u.uhp +=
X rnd (u.ulevel - 9);
X if (u.uhp > u.uhpmax)
X u.uhp = u.uhpmax;
X }
X }
X else if (u.uregen || moves %
X (22 - (u.ulevel << 1)) == 0) {
X flags.dhp = 1;
X u.uhp++;
X }
X }
X if (u.utel && !rn2 (85))
X tele ();
X if (u.usearch)
X dosearch ();
X gethungry ();
X }
X flags.move = 1;
X if (flags.dscr && !flags.mv)
X nscr ();
X if (flags.botl)
X bot ();
X else if (flags.dgold) {
X flags.dgold = 0;
X curs (16, 24);
X curx = 21;
X printf ("%-5u", u.ugold);
X }
X if (flags.dhp) {
X flags.dhp = 0;
X curs (26, 24);
X curx = 29;
X printf ("%3d", u.uhp);
X }
X if (flags.dhpmax) {
X flags.dhpmax = 0;
X curs (30, 24);
X printf ("%d)", u.uhpmax);
X if (u.uhpmax < 100)
X putchar (' ');
X curx = (u.uhpmax < 10) ? 33 : 34;
X }
X if (flags.dac) {
X flags.dac = 0;
X curs (37, 24);
X printf ("%-3d", u.uac);
X curx = 40;
X }
X if (flags.dstr) {
X flags.dstr = 0;
X curs (46, 24);
X prustr ();
X curx = 51;
X }
X if (flags.dulev) {
X flags.dulev = 0;
X curs (57, 24);
X printf ("%2d", u.ulevel);
X curx = 59;
X }
X if (flags.dexp) {
X flags.dexp = 0;
X curs (60, 24);
X if (u.ulevel < 14)
X printf ("%-5u", u.uexp);
X else
X printf ("MAX++");
X curx = 65;
X }
X if (flags.dhs) {
X flags.dhs = 0;
X curs (71, 24);
X printf (hu_stat[u.uhs]);
X curx = 79;
X }
X if (multi < 0) {
X if (!++multi) {
X pline (nomvmsg ? nomvmsg :
X "You can move again.");
X nomvmsg = 0;
X }
X }
X else {
X if (multi) {
X lookaround ();
X if (!multi) {
X flags.move = 0;
X continue;
X }
X if (flags.mv) {
X if (multi < 80 && !--multi) {
X flags.mv = 0;
X flags.run = 0;
X }
X domove ();
X }
X else {
X --multi;
X rhack (save_cm);
X }
X }
X else
X rhack (parse ());
X }
X }
X}
X
Xglo (n)
Xregister n; /* Construct the string `hackpid.n' */
X{
X/*
X register char *tf = lock;
X
X while( *tf && *tf != '.' )
X tf++;
X *tf++ = '.';
X sprintf( tf, "%d", n );
X*/
X sprintf (lock, "%d.%d", hackpid, n);
X}
X
Ximpossible () {
X pline ("Program in disorder - perhaps you'd better Quit");
X}
X
SHAR_EOF
if test 5621 -ne "`wc -c 'hack.main.c'`"
then
echo shar: error transmitting "'hack.main.c'" '(should have been 5621 characters)'
fi
echo shar: extracting "'hack.mkobj.c'" '(4439 characters)'
if test -f 'hack.mkobj.c'
then
echo shar: over-writing existing file "'hack.mkobj.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.mkobj.c'
X/*
X * Hack.mkobj.c
X */
X
X#include "hack.h"
X#include "hack.vars.h"
X
Xmkfood () {
X register FOOD fp;
X register i = rn2 (100);
X
X fp = &foods[0];
X while ((i -= fp -> prob) >= 0)
X fp++;
X return (fp - foods);
X}
X
Xmkarm () {
X register ARMOR ap;
X register i = rn2 (100);
X
X ap = &armors[0];
X while ((i -= ap -> prob) >= 0)
X ap++;
X return (ap - armors);
X}
X
Xmkwep () {
X register WEAPON wp;
X register i = rn2 (100);
X
X wp = &weapons[0];
X while ((i -= wp -> prob) >= 0)
X wp++;
X return (wp - weapons);
X}
X
Xchar mkobjstr[] = "))[[!!!!????%%%%//=**";
X
Xmkobj (let)
Xregister let;
X{
X register OBJECT otmp;
X
X otmp = newobj ();
X otmp -> nobj = fobj;
X fobj = otmp;
X otmp -> known = 0;
X otmp -> cursed = 0;
X otmp -> spe = 0;
X otmp -> unpaid = 0;
X otmp -> quan = 1;
X if (!let)
X let = mkobjstr[rn2 (sizeof (mkobjstr) - 1)];
X otmp -> olet = let;
X switch (let) {
X
X case ')':
X otmp -> otyp = mkwep ();
X if (otmp -> otyp <= W_AMMUNITION)
X otmp -> quan = rn1 (6, 6);
X if (!rn2 (11))
X otmp -> spe = rnd (3);
X else if (!rn2 (10)) {
X otmp -> cursed = 1;
X otmp -> spe = -rnd (3);
X }
X break;
X
X case '*':
X otmp -> otyp = rn2 (SIZE (potcol));
X otmp -> quan = rn2 (6) ? 1 : 2;
X break;
X
X case '[':
X otmp -> otyp = mkarm ();
X if (!rn2 (8))
X otmp -> cursed = 1;
X if (!rn2 (10))
X otmp -> spe = rnd (3);
X else if (!rn2 (9)) {
X otmp -> spe = -rnd (3);
X otmp -> cursed = 1;
X }
X otmp -> spe += 10 - armors[otmp -> otyp].a_ac;
X break;
X
X case '!':
X otmp -> otyp = rn2 (SIZE (pottyp));
X break;
X
X case '?':
X otmp -> otyp = rn2 (SIZE (scrtyp));
X break;
X
X case '%':
X otmp -> otyp = mkfood ();
X otmp -> quan = rn2 (6) ? 1 : 2;
X break;
X
X case '/':
X otmp -> otyp = rn2 (SIZE (wantyp));
X if (otmp -> otyp == Z_DEATH)
X otmp -> otyp = rn2 (SIZE (wantyp));
X otmp -> spe = rn1 (5, (otmp -> otyp <= Z_CREATE_MON) ?
X 11 : 4);
X /* detection and light and create monster */
X break;
X
X case '=':
X otmp -> otyp = rn2 (SIZE (ringtyp));
X if (otmp -> otyp >= R_GAIN_STR) {
X if (!rn2 (3)) {
X otmp -> spe = -rnd (2);
X otmp -> cursed = 1;
X break;
X }
X else
X otmp -> spe = rnd (2);
X }
X else if (otmp -> otyp == R_TELE ||
X otmp -> otyp == R_AGGRAV_MON ||
X otmp -> otyp == R_HUNGER)
X otmp -> cursed = 1;
X break;
X
X default:
X panic (CORE, "Impossible mkobj");
X }
X}
X
Xshufl (base, num)
Xregister char *base[];
Xregister num;
X{
X char **tmp, *tmp1;
X int curnum;
X
X for (curnum = num - 1; curnum > 0; curnum--) {
X tmp = &base[rn2 (curnum)];
X tmp1 = *tmp;
X *tmp = base[curnum];
X base[curnum] = tmp1;
X }
X}
X
Xshuffle () {
X shufl (wannam, SIZE (wantyp));
X shufl (potcol, SIZE (potcol));
X shufl (rinnam, SIZE (ringtyp));
X shufl (scrnam, SIZE (scrtyp));
X}
X
Xsavenames (fd)
Xregister fd;
X{
X bwrite (fd, oiden, sizeof oiden);
X bwrite (fd, potcol, sizeof potcol);
X bwrite (fd, scrnam, sizeof scrnam);
X bwrite (fd, wannam, sizeof wannam);
X bwrite (fd, rinnam, sizeof rinnam);
X}
X
Xrestnames (fd)
Xregister fd;
X{
X mread (fd, oiden, sizeof oiden);
X mread (fd, potcol, sizeof potcol);
X mread (fd, scrnam, sizeof scrnam);
X mread (fd, wannam, sizeof wannam);
X mread (fd, rinnam, sizeof rinnam);
X}
X
X/* Restore the names we have given to things */
Xcallsrestore (fd)
Xregister fd;
X{
X restcalls (fd, potcall, SIZE (pottyp));
X restcalls (fd, wandcall, SIZE (wantyp));
X restcalls (fd, ringcall, SIZE (ringtyp));
X restcalls (fd, scrcall, SIZE (scrtyp));
X}
X
X/* Save things we have given names to */
Xcallssave (fd)
Xregister fd;
X{
X savecalls (fd, potcall, SIZE (pottyp));
X savecalls (fd, wandcall, SIZE (wantyp));
X savecalls (fd, ringcall, SIZE (ringtyp));
X savecalls (fd, scrcall, SIZE (scrtyp));
X}
X
Xsavecalls (fd, strings, max)
Xchar *strings[];
Xregister int max, fd;
X{
X register teller;
X
X for (teller = 0; teller < max; ++teller) {
X if (strings[teller])
X bwrite (fd, strings[teller],
X strlen (strings[teller]) + 1);
X else
X bwrite (fd, "\0", 1);
X }
X}
X
Xrestcalls (fd, strings, max)
Xregister int fd, max;
Xchar *strings[];
X{
X register teller;
X char *str;
X int cnt;
X char buffer[BUFSZ];
X
X str = NULL;
X for (teller = 0; teller < max; ++teller) {
X cnt = -1;
X do {
X ++cnt;
X mread (fd, str, 1);
X buffer[cnt] = *str;
X } while (*str != '\0');
X if (cnt) {
X strings[teller] = alloc (strlen (buffer) + 1) -> Val;
X strcpy (strings[teller], buffer);
X }
X }
X}
SHAR_EOF
if test 4439 -ne "`wc -c 'hack.mkobj.c'`"
then
echo shar: error transmitting "'hack.mkobj.c'" '(should have been 4439 characters)'
fi
echo shar: extracting "'hack.mon.c'" '(10311 characters)'
if test -f 'hack.mon.c'
then
echo shar: over-writing existing file "'hack.mon.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.mon.c'
X/*
X * Hack.mon.c
X */
X
X/* Contains various monster routines */
X
X#include "hack.h"
X
Xextern char WCLEV[], STOPGLOW[];
X
Xdist (x, y)
Xregister x, y;
X{
X x -= u.ux;
X y -= u.uy;
X return (x * x + y * y);
X}
X
Xr_free (x, y, mtmp)
Xregister x, y;
Xregister MONSTER mtmp;
X{
X if (mtmp -> ale)
X return (levl[x][y].typ == POOL);
X else
X return (levl[x][y].typ > SDOOR &&
X (x != u.ux || y != u.uy) && levl[x][y].typ < POOL);
X /* DOOR,CORR,ROOM */
X}
X
X
X/* Puts m next to u, or anywhere if there isn't room there */
Xmnexto (mtmp)
XMONSTER mtmp;
X{
X register x, y, z;
X struct {
X char zx, zy;
X } foo[15], *tfoo;
X int range;
X
X tfoo = foo;
X range = 1;
X do { /* Full kludge action */
X for (y = 0; y < 2; y++)
X for (x = u.ux - range; x <= u.ux + range; x++) {
X z = range;
X if (!y)
X z = -z;
X if (test (x, z += u.uy)) {
X tfoo -> zx = x;
X tfoo++ -> zy = z;
X if (tfoo == &foo[15])
X goto foofull;
X }
X }
X for (x = 0; x < 2; x++)
X for (y = u.uy + 1 - range; y < u.uy + range;
X y++) {
X z = range;
X if (!x)
X z = -z;
X if (test (z += u.ux, y)) {
X tfoo -> zx = z;
X tfoo++ -> zy = y;
X if (tfoo == &foo[15])
X goto foofull;
X }
X }
X range++;
X } while (tfoo == foo);
Xfoofull:
X tfoo = &foo[rn2 (tfoo - foo)];
X mtmp -> mx = tfoo -> zx;
X mtmp -> my = tfoo -> zy;
X pmon (mtmp);
X if (mtmp -> data -> mlet == 'w')
X initworm (mtmp);
X}
X
Xrloc (mtmp)
XMONSTER mtmp;
X{
X register tx, ty;
X register char ch = mtmp -> data -> mlet;
X
X if (ch == 'w' && mtmp -> mx)
X return; /* Do not relocate worms */
X levlsym (mtmp -> mx, mtmp -> my, ch);
X if (mtmp -> ale) {
X do {
X tx = rn1 (77, 2);
X ty = rn2 (22);
X /* until CORR,DORR,or ROOM; or... */
X } while (levl[tx][ty].typ != POOL || m_at (tx, ty) ||
X (tx == u.ux && ty == u.uy));
X }
X else {
X do {
X tx = rn1 (77, 2);
X ty = rn2 (22);
X /* until CORR,DORR,or ROOM; or... */
X } while (levl[tx][ty].typ < DOOR || m_at (tx, ty) ||
X (tx == u.ux && ty == u.uy)
X || levl[tx][ty].typ >= 7);
X }
X mtmp -> mx = tx;
X mtmp -> my = ty;
X pmon (mtmp);
X if (ch == 'w')
X initworm (mtmp);
X}
X
Xtest (x, y) {
X if (x <= 0 || x > 78 || y <= 0 || y > 20)
X return 0;
X if (m_at (x, y) || levl[x][y].typ < DOOR || levl[x][y].typ >= 7)
X return 0;
X return 1;
X}
X
Xpoisoned (string, pname)
Xregister char *string, *pname;
X{
X pseebl ("%s was poisoned!", string);
X if (u.upres) {
X pline ("The poison doesn't seem to affect you.");
X return;
X }
X
X switch (rn2 (6)) {
X case 0:
X u.uhp = 0;
X break;
X case 1:
X case 2:
X case 3:
X losestr (rn1 (3, 3));
X break;
X case 4:
X case 5:
X losehp (rn1 (10, 6), pname);
X return;
X }
X
X if (u.uhp <= 0)
X killer = pname;
X}
X
Xsteal (mtmp)
XMONSTER mtmp;
X{
X register OBJECT otmp, ot1;
X register tmp;
X
X for (otmp = invent, tmp = 0; otmp -> nobj; otmp = otmp -> nobj, tmp++);
X
X tmp = rn2 (tmp);
X otmp = invent;
X if (!tmp)
X invent = invent -> nobj;
X else {
X for (; otmp && tmp; tmp--, otmp = otmp -> nobj);
X ot1 = otmp -> nobj;
X otmp -> nobj = ot1 -> nobj;/* rm obj from invent */
X otmp = ot1;
X }
X if (otmp == uarm || otmp == uarm2) {
X u.uac += otmp -> spe;
X if (otmp == uarm)
X uarm = uarm2;
X uarm2 = 0;
X flags.dac = 1;
X }
X else if (otmp == uwep)
X uwep = 0;
X else if (otmp == uleft) {
X uleft = 0;
X doring (otmp, OFF);
X }
X else if (otmp == uright) {
X uright = 0;
X doring (otmp, OFF);
X }
X doname (otmp, buf);
X pline ("She stole %s.", buf);
X stlobj (mtmp, otmp);
X}
X
Xstlobj (mtmp, otmp)
Xregister MONSTER mtmp;
Xregister OBJECT otmp;
X{
X otmp -> nobj = 0; /* Michiel: dog and two objects? */
X if (mtmp -> mstole) {
X otmp -> nobj = mtmp -> mstole -> sobj;
X mtmp -> mstole -> sobj = otmp;
X return;
X } /* Michiel save stolen object */
X else {
X mtmp -> mstole = newstole ();
X mtmp -> mstole -> sobj = otmp;
X mtmp -> mstole -> sgold = 0;
X }
X}
X
Xdelmon (mtmp)
Xregister MONSTER mtmp;
X{
X unstuck (mtmp); /* a3 */
X relmon (mtmp);
X if (mtmp == shopkeeper)
X shkdead ();
X if (mtmp == vaultkeeper) {
X mtmp -> data -> mmove = -1;
X vaultkeeper = 0;
X }
X if (mtmp -> wormno)
X wormdead (mtmp);
X free (mtmp);
X}
X
Xrelmon (mtmp)
Xregister MONSTER mtmp;
X{
X register MONSTER mtmp2;
X
X if (mtmp == fmon)
X fmon = fmon -> nmon;
X else {
X for (mtmp2 = fmon; mtmp2 -> nmon != mtmp; mtmp2 = mtmp2 -> nmon);
X mtmp2 -> nmon = mtmp -> nmon;
X }
X}
X
X/* Release the objects the killed animal has stolen */
Xrelobj (mtmp)
Xregister MONSTER mtmp;
X{
X register GOLD_TRAP gtmp;
X register tmp = 0;
X OBJECT otmp, otmp2;
X
X if (mtmp -> mstole) { /* Michiel drop stolen obj or gold */
X if (mtmp -> mstole -> sgold)
X tmp = mtmp -> mstole -> sgold;
X else {
X otmp = mtmp -> mstole -> sobj;
X do {
X otmp -> ox = mtmp -> mx;
X otmp -> oy = mtmp -> my;
X otmp2 = otmp;
X otmp = otmp -> nobj;
X } while (otmp);
X otmp2 -> nobj = fobj;
X fobj = mtmp -> mstole -> sobj;
X if (mtmp -> data -> mlet != 'd')
X seeatl (otmp -> ox, otmp -> oy, otmp -> olet);
X }
X free (mtmp -> mstole);
X mtmp -> mstole = NULL;
X }
X if (mtmp -> data -> mlet == 'L') {
X gtmp = newgen ();
X gtmp -> ngen = fgold;
X gtmp -> gx = mtmp -> mx;
X gtmp -> gy = mtmp -> my;
X if (dlevel)
X gtmp -> gflag = tmp + d (dlevel, 30);
X else
X gtmp -> gflag = tmp + d (maxdlevel, 30);
X fgold = gtmp;
X seeatl (mtmp -> mx, mtmp -> my, '$');
X }
X}
X
X/* a3 */
Xunstuck (mtmp)
Xregister MONSTER mtmp;
X{
X if (mtmp == u.ustuck) {
X if (u.uswallow) {
X u.uswallow = 0;
X u.uswldtim = 0;
X docrt ();
X setCon (SETC);/* Try a3 */
X }
X u.ustuck = 0;
X }
X}
X
Xkilled (mtmp)
Xregister MONSTER mtmp;
X{
X register tmp;
X
X unstuck (mtmp);
X levlsym (mtmp -> mx, mtmp -> my, mtmp -> data -> mlet);
X if (mtmp -> cham)
X mtmp -> data = (PM_CHAM);
X pseebl ("You destroy %s!", mtmp -> data -> mname);
X if (!u.ublind && u.umconf) {
X pline (STOPGLOW);
X u.umconf = 0;
X }
X tmp = mtmp -> data -> mhd;
X tmp *= tmp;
X ++tmp;
X if (mtmp -> data -> ac < 3)
X tmp += (7 - mtmp -> data -> ac) << 1;
X if (index ("AcsSDXaeRTVWU&In:P", mtmp -> data -> mlet))
X tmp += mtmp -> data -> mhd << 1;
X if (index ("DeV&P", mtmp -> data -> mlet))
X tmp += 7 * mtmp -> data -> mhd;
X if (mtmp -> data -> mhd > 6)
X tmp += 50;
X if (mtmp -> ale)
X tmp += 1000;
X relobj (mtmp);
X if ((index ("NTV&", mtmp -> data -> mlet) || !rn2 (5)) && !mtmp -> ale
X && levl[mtmp -> mx][mtmp -> my].typ > SDOOR) {
X /* Mimic in wall? */
X mkobj (0);
X fobj -> ox = mtmp -> mx;
X fobj -> oy = mtmp -> my;
X if (!u.ublind)
X atl (mtmp -> mx, mtmp -> my, fobj -> olet);
X }
X delmon (mtmp);
X u.urexp += tmp << 2;
X u.uexp += tmp;
X flags.dexp = 1;
X while (u.uexp >= 10L * pow (u.ulevel - 1)) {
X pline (WCLEV, ++u.ulevel);
X tmp = rnd (10);
X if (tmp < 3)
X tmp = rnd (10);
X u.uhpmax += tmp;
X u.uhp += tmp;
X flags.dhp = 1;
X flags.dhpmax = 1;
X flags.dulev = 1;
X }
X}
X
X#define TBLIND 5
X#define NOTEST 6
X
X/*VARARGS*/
Xpsee (mode, x, y, str, name, arg)/* Str bevat %s */
Xregister char *str, *name, *arg;
X{
X char *a1, *a2;
X
X a1 = "the %s";
X a2 = "the %s";
X if (mode == TBLIND) {
X if (u.ublind)
X a1 = "it";
X }
X else if (mode != NOTEST && !cansee (x, y))
X switch (mode) {
X case IT1:
X a1 = "it";
X break;
X case THEIT2:
X a2 = "it";
X break;
X case 0:
X return 0;
X default:
X pline ("Bad(%d) mode in psee", mode);
X }
X sprintf (buf, str, a1, a2);
X if (*buf >= 'a' && *buf <= 'z')
X *buf += 'A' - 'a';
X pline (buf, name, arg);
X return 1;
X}
X
X/*VARARGS*/
Xp2xthe (str, name, arg)
Xregister char *str, *name, *arg;
X{
X psee (NOTEST, 0, 0, str, name, arg);
X}
X
Xpseebl (str, name)
Xregister char *str, *name;
X{
X psee (TBLIND, 0, 0, str, name, NULL);
X}
X
Xrescham () { /* Force all chameleons to become normal */
X register MONSTER mtmp;
X
X for (mtmp = fmon; mtmp; mtmp = mtmp -> nmon)
X if (mtmp -> cham) {
X mtmp -> cham = 0;
X if (u.uswallow && u.ustuck == mtmp) {
X unstuck (mtmp);
X mnexto (mtmp);
X }
X newcham (mtmp, PM_CHAM);
X }
X}
X
X/* Make a chameleon look like a new monster */
Xnewcham (mtmp, mdat)
Xregister MONSTER mtmp;
Xregister MONSTDATA mdat;
X{
X register mhp, hpn, hpd;
X
X if (mdat == mtmp -> data)
X return; /* Still the same monster */
X if (u.uswallow && mdat -> mlet == 'w')
X return;
X if (mtmp -> wormno)
X wormdead (mtmp);/* Throw tail away */
X hpn = mtmp -> mhp;
X hpd = mtmp -> data -> mhd << 3;
X mtmp -> data = mdat;
X mtmp -> invis = 0;
X mtmp -> mtame = 0;
X mhp = mdat -> mhd << 3;
X/* New hp: same fraction of max as before */
X mtmp -> mhp = 2 + (hpn * mhp) / hpd;
X hpn = mtmp -> orig_hp;
X mtmp -> orig_hp = 2 + (hpn * mhp) / hpd;
X if (mdat -> mlet == 'I') {
X ++mtmp -> invis;
X if (cansee (mtmp -> mx, mtmp -> my))
X prl (mtmp -> mx, mtmp -> my);
X }
X if (mdat -> mlet == 'w' && getwn (mtmp))
X initworm (mtmp);
X if (u.uswallow && mtmp == u.ustuck &&
X !index (",'P", mdat -> mlet)) {
X unstuck (mtmp);
X mnexto (mtmp);
X }
X pmon (mtmp);
X}
X
Xmakemon (ptr)
Xregister MONSTDATA ptr;
X{
X register MONSTER mtmp;
X
X if (!ptr) {
X do
X ptr = &mon[rn2 (dlevel / 3 + 1) % 8][rn2 (7)];
X while (index (genocided, ptr -> mlet));
X }
X else {
X if (index (genocided, ptr -> mlet)) {
X if (!u.ublind)
X p2xthe ("%s vanishes!", ptr -> mname);
X return 1;
X }
X }
X mtmp = newmonst (ptr -> pxlth);
X mtmp -> nmon = fmon;
X fmon = mtmp;
X mtmp -> mstole = 0;
X mtmp -> invis = 0;
X mtmp -> cham = 0;
X mtmp -> msleep = 0;
X mtmp -> mfroz = 0;
X mtmp -> mconf = 0;
X mtmp -> mflee = 0;
X mtmp -> mtame = 0;
X mtmp -> mspeed = 0;
X mtmp -> mcan = 0;
X mtmp -> angry = 0;
X mtmp -> mxlth = 0;
X mtmp -> ale = 0;
X mtmp -> data = ptr;
X switch (ptr -> mlet) {
X case 'I':
X ++mtmp -> invis;
X break;
X case 'L':
X mtmp -> msleep = u.uhcursed;
X break;
X case ':':
X ++mtmp -> cham;
X if (!u.ucham)
X newcham (mtmp, &mon[rn1 (6, 2)][rn2 (7)]);
X break;
X case ';':
X mtmp -> ale = 1;
X break;
X }
X if (ptr -> mlet != 'w' || !getwn (mtmp))
X mtmp -> wormno = 0;
X mtmp -> mhp = rnd (4);
X if (ptr -> mhd)
X mtmp -> mhp = d (ptr -> mhd, 8);
X mtmp -> orig_hp = mtmp -> mhp;
X return 0;
X}
X
Xsomegold () {
X return ((u.ugold < 100L) ? u.ugold :
X (u.ugold > 10000L) ? rnd (10000) : rnd ((int) u.ugold));
X}
X
Xmkmonat (ptr, x, y)
Xregister MONSTDATA ptr;
Xregister x, y;
X{
X if (makemon (ptr))
X return;
X if (x == u.ux && y == u.uy)
X mnexto (fmon);
X else {
X atl (x, y, ptr -> mlet);
X fmon -> mx = x;
X fmon -> my = y;
X }
X}
SHAR_EOF
if test 10311 -ne "`wc -c 'hack.mon.c'`"
then
echo shar: error transmitting "'hack.mon.c'" '(should have been 10311 characters)'
fi
echo shar: extracting "'hack.mon.do.c'" '(12240 characters)'
if test -f 'hack.mon.do.c'
then
echo shar: over-writing existing file "'hack.mon.do.c'"
fi
sed 's/^X//' << \SHAR_EOF > 'hack.mon.do.c'
X/*
X * Hack.mon.do.c
X */
X
X/* Contains monster control routines */
X
X#include "hack.h"
X
Xextern MONSTER bhit ();
X
Xmovemon () {
X register MONSTER mtmp, mtmp2;
X
X for (mtmp = fmon; mtmp; mtmp = mtmp2) {
X mtmp2 = mtmp -> nmon;
X if (mtmp -> mspeed != MSLOW || moves % 2 == 0)
X if (dochug (mtmp))
X continue;/* Monster died */
X if (mtmp -> mspeed == MFAST)
X if (dochug (mtmp))
X continue;
X
X/* If we left the room: make monsters invis, even if they didn't move */
X
X if (!cansee (mtmp -> mx, mtmp -> my))
X levlsym (mtmp -> mx, mtmp -> my, mtmp -> data -> mlet);
X if (mtmp -> wormno && mtmp -> data -> mlet == 'w')
X wormsee (mtmp -> wormno);
X }
X}
X
Xjustswld (mtmp)
Xregister MONSTER mtmp;
X{
X newsym (mtmp -> mx, mtmp -> my);
X mtmp -> mx = u.ux;
X mtmp -> my = u.uy;
X u.ustuck = mtmp;
X at (u.ux, u.uy, mtmp -> data -> mlet);
X pseebl ("%s swallows you!", mtmp -> data -> mname);
X more ();
X u.uswallow = 1;
X docrt ();
X}
X
Xyouswld (mtmp, dam, die)
Xregister MONSTER mtmp;
Xregister dam, die;
X{
X pseebl ("%s digests you!", killer = mtmp -> data -> mname);
X if (dam > 0) {
X u.uhp -= dam;
X flags.dhp = 1;
X }
X if (u.uswldtim++ == die) {
X pline ("It totally digests you!");
X u.uhp = 0;
X }
X}
X
Xx2hitu (mlev, x, name)
Xregister mlev, x;
Xregister char *name; /* a3 */
X{
X register i;
X
X for (i = 0; i < 2; i++)
X hitu (mlev, (x < 0) ? d (2, x) : (x == 0) ? d (3, 4) :
X rnd (x), name);
X}
X
Xdochug (mtmp)
Xregister MONSTER mtmp;
X{
X register MONSTDATA mdat;
X register tmp = 0, ctmp;
X
X if (mtmp -> mhp <= 0 && !mtmp -> mtame)
X return 1; /* Killed by dog or ? */
X if (mtmp -> cham && !rn2 (6))
X newcham (mtmp, &mon[rn1 (6, 2)][rn2 (7)]);
X mdat = mtmp -> data;
X /*
X if( mdat->mhd < 0 )
X panic( CORE, "Bad(%d)monster %c", mdat->mhd,
X mdat->mlet );
X */
X if ((moves % 20 == 0 || index ("ViT", mdat -> mlet)) &&
X mtmp -> mhp < mtmp -> orig_hp)
X mtmp -> mhp++; /* Regenerate monsters */
X if (mtmp -> mfroz)
X return 0; /* Frozen monsters don't do anything */
X if (mtmp -> msleep) {
X /* Wake up a monster, or get out of here */
X if (cansee (mtmp -> mx, mtmp -> my) && !u.ustelth &&
X (!rn2 (7) || u.uagmon))
X mtmp -> msleep = 0;
X else
X return 0;
X }
X
X/* Confused monsters get unconfused with small probability */
X
X if (mtmp -> mconf && !rn2 (50))
X mtmp -> mconf = 0;
X if (mdat -> mmove >= rnd (12) && (mtmp -> mflee || mtmp -> mconf ||
X dist (mtmp -> mx, mtmp -> my) > 2 || mtmp -> mtame ||
X mtmp == shopkeeper) && (tmp = m_move (mtmp, 0)) &&
X mdat -> mmove <= 12)
X return (tmp == 2);
X /* Move monsters and exit if rate<=12 */
X if (tmp == 2)
X return 1; /* Monster died moving */
X
X if (!index ("Ea", mdat -> mlet) && dist (mtmp -> mx, mtmp -> my) < 3
X && !mtmp -> mtame && mtmp != shopkeeper && u.uhp > 0) {
X nomul (tmp = 0);
X if (u.uswallow) {
X if (mtmp != u.ustuck)
X if (mdat -> mmove - 12 > rnd (12))
X tmp = m_move (mtmp, 1);
X }
X else if (!index ("&DyF", mdat -> mlet)) {
X if (mtmp -> ale && cansee (mtmp -> mx, mtmp -> my)) {
X mtmp -> invis = 0;
X pmon (mtmp);
X }
X tmp = hitu (mdat -> mhd, d (mdat -> damn, mdat -> damd),
X mdat -> mname);
X }
X
X/* Increase chance of hitting (no damage) for L and R */
X if (index ("LR", mdat -> mlet) && hitu (5, 0, mdat -> mname))
X tmp++;
X
X ctmp = (tmp && !mtmp -> mcan && (!uarm ||
X armors[uarm -> otyp].a_can < rnd (3)));
X
X switch (mdat -> mlet) {
X
X case ';':
X if (mtmp -> mcan)
X break;
X if (!u.ustuck && !rn2 (20)) {
X p2xthe ("%s swings itself around you!",
X mdat -> mname);
X u.ustuck = mtmp;
X }
X else if (u.ustuck == mtmp && ctmp) {
X p2xthe ("%s drowns you...", mdat -> mname);
X more ();
X done (DROWNED);
X }
X break;
X
X case '&':
X if (!mtmp -> mcan && !rn2 (15)) {
X makemon (PM_DEMON);
X mnexto (fmon);
X }
X else {
X x2hitu (10, -6, mdat -> mname);
X x2hitu (10, 3, mdat -> mname);
X hitu (10, rn1 (4, 2), mdat -> mname);
X }
X break;
X
X case ',':
X case '\'':
X if (u.uswallow)
X if (mdat -> mlet == ',')
X youswld (mtmp, 4 + u.uac, 5);
X else
X youswld (mtmp, rnd (6), 7);
X else if (tmp)
X justswld (mtmp);
X break;
X
X case 'A':
X if (ctmp && rn2 (2)) {
X pline ("You feel weaker!");
X losestr (1);
X }
X break;
X
X case 'C':
X case 'Y':
X hitu (4, rnd (6), mdat -> mname);
X break;
X
X case 'c':
X if (ctmp && !rn2 (5)) {
X pline ("You get turned to stone!");
X u.uhp = 0;
X }
X break;
X
X case 'D':
X if (rn2 (6) || mtmp -> mcan) {
X hitu (10, d (3, 10), mdat -> mname);
X x2hitu (10, 8, mdat -> mname);
X break;
X }
X pseebl ("%s breathes fire!", mdat -> mname);
X buzz (Z_FIRE, mtmp -> mx, mtmp -> my,
X u.ux - mtmp -> mx,
X u.uy - mtmp -> my);
X break;
X
X case 'd':
X hitu (6, d (2, 4), mdat -> mname);
X break;
X
X case 'e':
X hitu (10, d (3, 6), mdat -> mname);
X break;
X
X case 'F':
X if (mtmp -> mcan)
X break;
X pseebl ("%s explodes!", mdat -> mname);
X if (u.ucoldres)
X pline ("You don't seem affected by it.");
X else {
X if (17 - (u.ulevel >> 1) > rnd (20)) {
X pline ("You get blasted!");
X tmp = 6;
X }
X else {
X pline ("You duck the blast...");
X tmp = 3;
X }
X losehp (d (tmp, 6), mdat -> mname);
X }
X cmdel (mtmp);
X return 1;
X
X case 'g':
X if (!ctmp || multi < 0 || rn2 (6))
X break;
X pseebl ("You are frozen by %ss juices", "cube'");
X nomul (-rnd (10));
X break;
X
X case 'h':
X if (!ctmp || multi < 0 || rn2 (5))
X break;
X pseebl ("You are put to sleep by %ss bite!",
X "homunculus'");
X nomul (-rnd (10));
X break;
X
X case 'j':
X tmp = hitu (4, rnd (3), mdat -> mname);
X tmp &= hitu (4, rnd (3), mdat -> mname);
X if (tmp)
X x2hitu (4, 4, mdat -> mname);
X break;
X
X case 'k':
X if ((hitu (4, rnd (4), mdat -> mname) || !rn2 (3))
X && ctmp)
X poisoned ("bee's sting", mdat -> mname);
X break;
X
X case 'L':
X if (ctmp && u.ugold && rn2 (2)) {
X u.ugold -= (ctmp = somegold ());
X pline ("Your purse feels lighter.");
X flags.dgold = 1;
X
X /* Michiel save stolen gold */
X if (mtmp -> mstole)
X mtmp -> mstole -> sgold += ctmp;
X else {
X mtmp -> mstole = newstole ();
X mtmp -> mstole -> sobj = 0;
X mtmp -> mstole -> sgold = ctmp;
X }
X mtmp -> mflee = 1;
X rloc (mtmp);
X }
X break;
X
X case 'N':
X if (ctmp && invent && rn2 (2)) {
X steal (mtmp);
X rloc (mtmp);
X mtmp -> mflee = 1;
X }
X break;
X
X case 'n':
X x2hitu (11, -6, mdat -> mname);
X break;
X
X case 'o':
X hitu (5, rnd (6), mdat -> mname);
X /* tmp= ?? */
X if (hitu (5, rnd (6), mdat -> mname) && ctmp &&
X !u.ustuck && rn2 (2)) {
X u.ustuck = mtmp;
X pseebl ("%s has grabbed you!",
X mdat -> mname);
X u.uhp -= d (2, 8);
X break;
X }
X if (u.ustuck == mtmp) {
X pline ("You are being crushed.");
X u.uhp -= d (2, 8);
X }
X break;
X
X case 'P':
X if (u.uswallow)
X youswld (mtmp, d (2, 4), 12);
X else if (ctmp && !rn2 (4))
X justswld (mtmp);
X else
X hitu (15, d (2, 4), mdat -> mname);
X break;
X
X case 'Q':
X x2hitu (3, 2, mdat -> mname);
X break;
X
X case 'R':
X if (ctmp && uarm && uarm -> otyp < A_STD_LEATHER
X && uarm -> spe > -2) {
X pline ("Your armor rusts!");
X --uarm -> spe;
X u.uac++;
X flags.dac = 1;
X }
X break;
X
X case 'S':
X if (ctmp && !rn2 (8))
X poisoned ("snake's bite", mdat -> mname);
X break;
X
X case 's':
X if (tmp && !rn2 (8))
X poisoned ("scorpion's sting",
X mdat -> mname);
X x2hitu (5, 8, mdat -> mname);
X break;
X
X case 'T':
X x2hitu (6, 6, mdat -> mname);
X break;
X
X case 'U':
X x2hitu (9, 0, mdat -> mname);/* 0: d(3,4) */
X break;
X
X case 'v':
X if (ctmp && !u.ustuck)
X u.ustuck = mtmp;
X break;
X
X case 'V':
X if (tmp)
X u.uhp -= 4;
X if (rn2 (3))
X break;
X V:
X if (ctmp) {/* hit by V or W */
X if (u.ulevel > 1)
X pline ("Goodbye level %d.",
X u.ulevel--);
X else
X u.uhp = 0;
X ctmp = rnd (10);
X u.uhp -= ctmp;
X u.uhpmax -= ctmp;
X u.uexp = 10L * pow (u.ulevel - 1) - 1L;
X flags.dhp = 1;
X flags.dhpmax = 1;
X flags.dulev = 1;
X flags.dexp = 1;
X }
X break;
X
X case 'W':
X if (rn2 (5))
X break;
X goto V;
X case 'w':
X if (tmp)
X wormhit (mtmp);
X break;
X case 'X':
X for (tmp = 0; tmp < 3; tmp++)
X hitu (8, rnd (3), mdat -> mname);
X break;
X
X case 'y':
X if (mtmp -> mcan)
X break;
X cmdel (mtmp);
X if (!u.ublind) {
X pline ("You are blinded by a blast of light!");
X u.ublind = d (4, 12);
X unCoff (COFF, 0);
X }
X return 1;
X } /* switch */
X
X if (u.uhp <= 0)
X killer = mdat -> mname;
X }
X else if (mtmp -> ale && cansee (mtmp -> mx, mtmp -> my)) {
X mtmp -> invis = 1;
X newsym (mtmp -> mx, mtmp -> my);
X }
X/* Extra movement for fast monsters */
X if (mdat -> mmove - 12 > rnd (12))
X tmp = m_move (mtmp, 1);
X return (tmp == 2);
X}
X
Xcmdel (mtmp)
Xregister MONSTER mtmp;
X{
X register char mx = mtmp -> mx, my = mtmp -> my;
X
X delmon (mtmp);
X if (cansee (mx, my))
X newsym (mx, my);
X}
X
Xinrange (mtmp)
Xregister MONSTER mtmp;
X{
X int zx, zy;
X register char tx = u.ux - mtmp -> mx, ty = u.uy - mtmp -> my;
X
X/* This mess figures out if the person is within 8 */
X if ((!tx && abs (ty) < 8) || (!ty && abs (tx) < 8) ||
X (abs (tx) == abs (ty) && abs (tx) < 8)) {
X if (tx == 0)
X zx = 0;
X else
X zx = tx / abs (tx);
X if (ty == 0)
X zy = 0;
X else
X zy = ty / abs (ty);
X/* If we don't save dx and dy a capital move may screw up: */
X tx = dx;
X ty = dy;
X if (bhit (zx, zy, 8) == mtmp)
X buzz (Z_FIRE, mtmp -> mx, mtmp -> my, dx, dy);
X dx = zx;
X dy = zy;
X }
X}
X
Xm_move (mtmp, after)
Xregister MONSTER mtmp;
X{
X register MONSTER mtmp2;
X register nix, niy, omx, omy, appr, nearer, cnt, zx, zy;
X char ddx, ddy, mmoved = 0;
X
X/* My dog gets a special treatment */
X if (mtmp -> mtame)
X return dog_move (mtmp, after);
X
X if (u.uswallow)
X return (1); /* a3 */
X/* Likewise for shopkeeper */
X if (mtmp == shopkeeper)
X return shk_move ();
X if (mtmp == vaultkeeper && !mtmp -> angry)
X return (0);
X
X if (mtmp -> data -> mlet == 't' && !rn2 (19)) {
X if (rn2 (2)) {
X ddx = mtmp -> mx;
X ddy = mtmp -> my;
X mnexto (mtmp);/* Doesn't change old position */
X levlsym (ddx, ddy, 't');
X }
X else
X rloc (mtmp);/* Rloc does */
X return 1;
X }
X if (!mtmp -> mcan)
X switch (mtmp -> data -> mlet) {
X case 'D':
X inrange (mtmp);
X break;
X case 'U':
X if (!rn2 (10) && !u.uconfused &&
X cansee (mtmp -> mx, mtmp -> my)) {
X pline ("You are confused!");
X u.uconfused = d (3, 4);
X }
X if (!mtmp -> mflee && u.uswallow &&
X u.ustuck != mtmp)
X return 1;
X }
X appr = 1;
X if (mtmp -> mflee)
X appr = -1;
X if (mtmp -> mconf || u.uinvis || (index ("BI", mtmp -> data -> mlet) &&
X !rn2 (3)))
X appr = 0;
X omx = mtmp -> mx;
X omy = mtmp -> my;
X nix = omx;
X niy = omy;
X cnt = 0;
X for (ddx = -1; ddx <= 1; ddx++)
X for (ddy = -1; ddy <= 1; ddy++)
X if (r_free (zx = omx + ddx, zy = omy + ddy, mtmp)
X && (ddx || ddy)
X && !(ddx && ddy && (levl[omx][omy].typ == DOOR ||
X levl[zx][zy].typ == DOOR))) {
X if (!mtmp -> mconf && m_at (zx, zy))
X continue;
X nearer = (dist (zx, zy) < dist (nix, niy));
X if ((appr > 0 && nearer) || (appr < 0 &&
X !nearer) ||
X (!mmoved && mtmp -> wormno) ||
X (!appr && !rn2 (++cnt))) {
X nix = zx;
X niy = zy;
X mmoved++;
X }
X }
X if (mmoved) {
X if (mtmp -> mconf && (mtmp2 = m_at (nix, niy))) {
X if (hitmm (mtmp, mtmp2) == 1 && rn2 (4) &&
X hitmm (mtmp2, mtmp) == 2)
X return 2;
X return 0;
X }
X if (!mtmp -> ale) {
X mtmp -> mx = nix;
X mtmp -> my = niy;
X }
X else if (levl[nix][niy].typ == POOL) {
X mtmp -> mx = nix;
X mtmp -> my = niy;
X }
X
X if (mtmp -> wormno && mtmp -> data -> mlet == 'w')
X worm_move (mtmp);
X }
X else {
X if (!rn2 (10) && index ("tNL", mtmp -> data -> mlet)) {
X rloc (mtmp);
X return 0;
X }
X if (mtmp -> wormno)
X worm_nomove (mtmp);
X }
X if (mmoved || !cansee (omx, omy))
X levlsym (omx, omy, mtmp -> data -> mlet);
X pmon (mtmp);
X return (mmoved);
X}
SHAR_EOF
if test 12240 -ne "`wc -c 'hack.mon.do.c'`"
then
echo shar: error transmitting "'hack.mon.do.c'" '(should have been 12240 characters)'
fi
# End of shell archive
exit 0
0 new messages