[comp.sources.games] v07i057: NetHack3 - display oriented dungeons & dragons

billr@saab.CNA.TEK.COM (Bill Randle) (07/25/89)

Submitted-by: Izchak Miller <izchak@linc.cis.upenn.edu>
Posting-number: Volume 7, Issue 57
Archive-name: NetHack3/Part02



#! /bin/sh
# This is a shell archive.  Remove anything before this line, then unpack
# it by saving it into a file and typing "sh file".  To overwrite existing
# files, type "sh file -c".  You can also feed this as standard input via
# unshar, or by typing "sh <file", e.g..  If this archive is complete, you
# will see the following message at the end:
#		"End of archive 2 (of 38)."
# Contents:  src/o_init.c src/zap.c
# Wrapped by billr@saab on Sun Jul 23 21:32:46 1989
PATH=/bin:/usr/bin:/usr/ucb ; export PATH
if test -f 'src/o_init.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'src/o_init.c'\"
else
echo shar: Extracting \"'src/o_init.c'\" \(7223 characters\)
sed "s/^X//" >'src/o_init.c' <<'END_OF_FILE'
X/*	SCCS Id: @(#)o_init.c	3.0	88/07/06
X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
X/* NetHack may be freely redistributed.  See license for details. */
X
X#include	"hack.h"		/* for typedefs */
X
X/* note that NROFOBJECTS is the number of legal objects, which does not count
X * the strange object and null object that take up positions 0 and NROFOBJECTS+1
X * in the objects array
X */
X#define TOTAL_OBJS	(NROFOBJECTS+2)
X
Xconst char obj_symbols[] = {
X	ILLOBJ_SYM, AMULET_SYM, FOOD_SYM, WEAPON_SYM, TOOL_SYM,
X	BALL_SYM, CHAIN_SYM, ROCK_SYM, ARMOR_SYM,
X	POTION_SYM, SCROLL_SYM, WAND_SYM,
X#ifdef SPELLS
X	SPBOOK_SYM,
X#endif
X	RING_SYM, GEM_SYM, 0 };
X
Xint bases[sizeof(obj_symbols)] = DUMMY;
Xstatic int disco[TOTAL_OBJS] = DUMMY;
X
Xint
Xletindex(let) register char let; {
Xregister int i = 0;
Xregister char ch;
X	while((ch = obj_symbols[i++]) != 0)
X		if(ch == let) return(i);
X	return(0);
X}
X
Xstatic void
Xsetgemprobs()
X{
X	register int j,first;
X#ifdef STRONGHOLD
X	int level = (dlevel > MAXLEVEL) ? MAXLEVEL : dlevel;
X#endif
X
X	first = bases[letindex(GEM_SYM)];
X
X#ifdef STRONGHOLD
X	for(j = 0; j < 9-level/3; j++)
X#else
X	for(j = 0; j < 9-dlevel/3; j++)
X#endif
X		objects[first+j].oc_prob = 0;
X	first += j;
X	if(first >= LAST_GEM || first > NROFOBJECTS ||
X	    objects[first].oc_olet != GEM_SYM ||
X	    objects[first].oc_name == NULL)
X		Printf("Not enough gems? - first=%d j=%d LAST_GEM=%d\n",
X			first, j, LAST_GEM);
X	for(j = first; j < LAST_GEM; j++)
X		objects[j].oc_prob = (180+j-first)/(LAST_GEM-first);
X}
X
X/* shuffle descriptions on objects o_low to o_high */
Xstatic void
Xshuffle(o_low, o_high, domaterial)
X
X	register int o_low, o_high;
X	register boolean domaterial;
X{
X	register int i, j;
X	char *desc;
X	int tmp;
X
X	for(j=o_low; j <= o_high; j++) {
X		i = o_low + rn2(j+1-o_low);
X		desc = objects[j].oc_descr;
X		objects[j].oc_descr = objects[i].oc_descr;
X		objects[i].oc_descr = desc;
X		/* shuffle discovery list */
X		tmp = disco[j];
X		disco[j] = disco[i];
X		disco[i] = tmp;
X		/* shuffle material */
X		if(domaterial) {
X			tmp = objects[j].oc_material;
X			objects[j].oc_material = objects[i].oc_material;
X			objects[i].oc_material = tmp;
X		}
X	}
X}
X
Xvoid
Xinit_objects(){
Xregister int i, j, first, last, sum, end;
Xregister char let;
X
X	/* bug fix to prevent "initialization error" abort on Intel Xenix.
X	 * reported by mikew@semike
X	 */
X	for(i = 0; i != sizeof(obj_symbols); i++)
X		bases[i] = 0;
X	for(i = 0; i != TOTAL_OBJS; i++)
X		disco[i] = i;
X
X	/* init base; if probs given check that they add up to 1000,
X	   otherwise compute probs; shuffle descriptions */
X	end = TOTAL_OBJS;
X	first = 0;
X	while( first < end ) {
X		let = objects[first].oc_olet;
X		last = first+1;
X		while(last < end && objects[last].oc_olet == let
X				 && objects[last].oc_name != NULL) last++;
X		i = letindex(let);
X		if((!i && let != ILLOBJ_SYM && let != '.') || bases[i] != 0)
X			error("initialization error for %c", let);
X		bases[i] = first;
X
X		if(let == GEM_SYM) setgemprobs();
X	check:
X		sum = 0;
X		for(j = first; j < last; j++) sum += objects[j].oc_prob;
X		if(sum == 0) {
X			for(j = first; j < last; j++)
X			    objects[j].oc_prob = (1000+j-first)/(last-first);
X			goto check;
X		}
X		if(sum != 1000)
X			error("init-prob error for %c (%d%%)", let, sum);
X
X		if(objects[first].oc_descr != NULL &&
X		   let != TOOL_SYM && let != WEAPON_SYM && let != ARMOR_SYM) {
X
X			/* shuffle, also some additional descriptions */
X			while(last < end && objects[last].oc_olet == let)
X				last++;
X			j = last;
X			if (let == GEM_SYM) {
X			    while(--j > first)
X				/* NOTE:  longest color name must be default */
X				if(!strcmp(objects[j].oc_name,"turquoise")) {
X				    if(rn2(2)) /* change from green? */
X					Strcpy(objects[j].oc_descr, blue);
X				} else if (!strcmp(objects[j].oc_name,"aquamarine")) {
X				    if(rn2(2)) /* change from green? */
X					Strcpy(objects[j].oc_descr, blue);
X				} else if (!strcmp(objects[j].oc_name,"fluorite")) {
X				    switch (rn2(4)) { /* change from violet? */
X					case 0:  break;
X					case 1:
X					    Strcpy(objects[j].oc_descr, blue);
X					    break;
X					case 2:
X					    Strcpy(objects[j].oc_descr, white);
X					    break;
X					case 3:
X					    Strcpy(objects[j].oc_descr, green);
X					    break;
X					}
X				}
X			} else {
X			    if (let == AMULET_SYM || let == POTION_SYM)
X				j--;  /* THE amulet doesn't have description */
X			    /* and water is always "clear" - 3. */
X			    shuffle(first, --j, TRUE);
X			}
X		}
X		first = last;
X	}
X
X	/* shuffle the helmets */
X	shuffle(HELMET, HELM_OF_TELEPATHY, FALSE);
X
X	/* shuffle the gloves */
X	shuffle(LEATHER_GLOVES, GAUNTLETS_OF_DEXTERITY, FALSE);
X
X	/* shuffle the cloaks */
X	shuffle(CLOAK_OF_PROTECTION, CLOAK_OF_DISPLACEMENT, FALSE);
X
X	/* shuffle the boots */
X	shuffle(SPEED_BOOTS, LEVITATION_BOOTS, FALSE);
X}
X
Xvoid
Xoinit()			/* level dependent initialization */
X{
X	setgemprobs();
X}
X
Xvoid
Xsavenames(fd)
Xregister int fd;
X{
X	register int i;
X	unsigned int len;
X	struct objclass *now = &objects[0];
X	bwrite(fd, (genericptr_t)&now, sizeof now);
X	bwrite(fd, (genericptr_t)bases, sizeof bases);
X	bwrite(fd, (genericptr_t)disco, sizeof disco);
X	bwrite(fd, (genericptr_t)objects, sizeof(struct objclass) * TOTAL_OBJS);
X	/* as long as we use only one version of Hack we
X	   need not save oc_name and oc_descr, but we must save
X	   oc_uname for all objects */
X	for(i=0; i < TOTAL_OBJS; i++) {
X		if(objects[i].oc_uname) {
X			len = strlen(objects[i].oc_uname)+1;
X			bwrite(fd, (genericptr_t)&len, sizeof len);
X			bwrite(fd, (genericptr_t)objects[i].oc_uname, len);
X		}
X	}
X}
X
Xvoid
Xrestnames(fd)
Xregister int fd;
X{
X	register int i;
X	unsigned int len;
X	struct objclass *then;
X	long differ;
X	mread(fd, (genericptr_t) &then, sizeof then);
X	mread(fd, (genericptr_t) bases, sizeof bases);
X	mread(fd, (genericptr_t) disco, sizeof disco);
X	mread(fd, (genericptr_t) objects, sizeof(struct objclass) * TOTAL_OBJS);
X#ifndef MSDOS
X	differ = (genericptr_t)&objects[0] - (genericptr_t)then;
X#else
X	differ = (long)&objects[0] - (long)then;
X#endif
X	for(i=0; i < TOTAL_OBJS; i++) {
X		if (objects[i].oc_name) {
X#ifndef MSDOS
X			objects[i].oc_name += differ;
X#else
X			objects[i].oc_name =
X			    (char *)((long)(objects[i].oc_name) + differ);
X#endif
X		}
X		if (objects[i].oc_descr) {
X#ifndef MSDOS
X			objects[i].oc_descr += differ;
X#else
X			objects[i].oc_descr =
X			    (char *)((long)(objects[i].oc_descr) + differ);
X#endif
X		}
X		if (objects[i].oc_uname) {
X			mread(fd, (genericptr_t) &len, sizeof len);
X			objects[i].oc_uname = (char *) alloc(len);
X			mread(fd, (genericptr_t)objects[i].oc_uname, len);
X		}
X	}
X}
X
Xstatic boolean
Xinteresting_to_discover(i)
Xregister int i;
X{
X    return objects[i].oc_uname != NULL ||
X		(objects[i].oc_name_known && objects[i].oc_descr != NULL);
X}
X
Xint
Xdodiscovered()				/* free after Robert Viduya */
X{
X    register int i, dis;
X    int	ct = 0;
X    char class = -1;
X
X    cornline(0, "Discoveries");
X
X    for (i = 0; i <= NROFOBJECTS; i++) {
X	if (interesting_to_discover(dis = disco[i])) {
X	    ct++;
X	    if (objects[dis].oc_olet != class) {
X		class = objects[dis].oc_olet;
X		cornline(1, let_to_name(class));
X	    }
X	    cornline(1, typename(dis));
X	}
X    }
X    if (ct == 0) {
X	You("haven't discovered anything yet...");
X	cornline(3, NULL);
X    } else
X	cornline(2, NULL);
X
X    return 0;
X}
END_OF_FILE
if test 7223 -ne `wc -c <'src/o_init.c'`; then
    echo shar: \"'src/o_init.c'\" unpacked with wrong size!
fi
# end of 'src/o_init.c'
fi
if test -f 'src/zap.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'src/zap.c'\"
else
echo shar: Extracting \"'src/zap.c'\" \(44087 characters\)
sed "s/^X//" >'src/zap.c' <<'END_OF_FILE'
X/*	SCCS Id: @(#)zap.c	3.0	88/10/25
X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
X/* NetHack may be freely redistributed.  See license for details. */
X
X#include "hack.h"
X
X#if defined(ALTARS) && defined(THEOLOGY)
Xstatic boolean priesthit = FALSE;
X#endif
X
Xconst char *fl[]= {
X	"magic missile",	/* Wands must be 0-9 */
X	"bolt of fire",
X	"sleep ray",
X	"bolt of cold",
X	"death ray",
X	"bolt of lightning",
X	"",
X	"",
X	"",
X	"",
X
X	"magic missile",	/* Spell equivalents must be 10-19 */
X	"fireball",
X	"sleep ray",
X	"cone of cold",
X	"finger of death",
X	"bolt of lightning",
X	"",
X	"",
X	"",
X	"",
X
X	"blast of missiles",	/* Dragon breath equivalents 20-29*/
X	"blast of fire",
X	"blast of sleeping gas",
X	"blast of frost",
X	"blast of disintegration",
X	"blast of lightning",
X	"blast of poison gas",
X	"blast of acid",
X	"",
X	""
X};
X
X/* Routines for IMMEDIATE wands and spells. */
X/* bhitm: monster mtmp was hit by the effect of wand or spell otmp */
Xstatic int
Xbhitm(mtmp, otmp)
Xregister struct monst *mtmp;
Xregister struct obj *otmp;
X{
X	wakeup(mtmp);
X	switch(otmp->otyp) {
X	case WAN_STRIKING:
X#ifdef SPELLS
X	case SPE_FORCE_BOLT:
X#endif
X		if(u.uswallow || rnd(20) < 10+mtmp->data->ac) {
X			register int tmp = d(2,12);
X			hit((otmp->otyp == WAN_STRIKING) ? "wand" : "spell", mtmp, exclam(tmp));
X			(void) resist(mtmp, otmp->olet, tmp, TELL);
X		} else miss((otmp->otyp == WAN_STRIKING) ? "wand" : "spell", mtmp);
X		break;
X	case WAN_SLOW_MONSTER:
X#ifdef SPELLS
X	case SPE_SLOW_MONSTER:
X#endif
X		if(! resist(mtmp, otmp->olet, 0, NOTELL))
X			if (mtmp->mspeed == MFAST) mtmp->mspeed = 0;
X			else mtmp->mspeed = MSLOW;
X		break;
X	case WAN_SPEED_MONSTER:
X		if (!resist(mtmp, otmp->olet, 0, NOTELL))
X			if (mtmp->mspeed == MSLOW) mtmp->mspeed = 0;
X			else mtmp->mspeed = MFAST;
X		break;
X	case WAN_UNDEAD_TURNING:
X#ifdef SPELLS
X	case SPE_TURN_UNDEAD:
X#endif
X		if(is_undead(mtmp->data)) {
X
X			if(!resist(mtmp, otmp->olet, rnd(8), NOTELL))
X				mtmp->mflee = 1;
X		}
X		break;
X	case WAN_POLYMORPH:
X#ifdef SPELLS
X	case SPE_POLYMORPH:
X#endif
X		if(!resist(mtmp, otmp->olet, 0, NOTELL))
X		    if( newcham(mtmp, (struct permonst *)0) )
X			if (!Hallucination)
X			    makeknown(otmp->otyp);
X		break;
X	case WAN_CANCELLATION:
X#ifdef SPELLS
X	case SPE_CANCELLATION:
X#endif
X		if(!resist(mtmp, otmp->olet, 0, NOTELL)) {
X		  if (is_were(mtmp->data) && mtmp->data->mlet != S_HUMAN)
X		    were_change(mtmp);
X#ifdef GOLEMS
X		  if (mtmp->data == &mons[PM_CLAY_GOLEM]) {
X		    if (!Blind)
X		      pline("Some writing vanishes from %s's head!",
X			mon_nam(mtmp));
X		    killed(mtmp);
X		  }
X		  else
X#endif /* GOLEMS */
X		    mtmp->mcan = 1;
X		}
X		break;
X	case WAN_TELEPORTATION:
X#ifdef SPELLS
X	case SPE_TELEPORT_AWAY:
X#endif
X#if defined(ALTARS) && defined(THEOLOGY)
X		if(mtmp->ispriest && in_temple(mtmp->mx, mtmp->my)) {
X		    kludge("%s resists your magic!", Monnam(mtmp));
X		    wakeup(mtmp);
X		    break;
X		}
X#endif
X		rloc(mtmp);
X		break;
X	case WAN_MAKE_INVISIBLE:
X		mtmp->minvis = 1;
X		break;
X	case WAN_NOTHING:
X		break;
X#ifdef PROBING
X	case WAN_PROBING:
X		makeknown(otmp->otyp);
X		mstatusline(mtmp);
X		break;
X#endif
X	case WAN_OPENING:
X	case WAN_LOCKING:
X#ifdef SPELLS
X	case SPE_KNOCK:
X	case SPE_WIZARD_LOCK:
X#endif
X		break;
X	default:
X		impossible("What an interesting effect (%u)", otmp->otyp);
X	}
X	return 0;
X}
X
Xstruct monst *
Xrevive(obj,ininv)
Xregister struct obj *obj;
Xboolean ininv;
X{
X	register struct monst *mtmp;
X
X	if(obj->otyp == CORPSE) {
X		int montype,x,y,nl;
X		char buf[BUFSZ];
X
X		if (nl = obj->onamelth) Strcpy(buf, ONAME(obj));
X		montype = obj->corpsenm;
X		if (ininv) {
X			x = u.ux; y = u.uy;
X			useup(obj);
X		} else {
X			x = obj->ox; y = obj->oy;
X			useupf(obj);
X		}
X		if (cant_create(&montype)) { /* will make zombie instead */
X			mtmp = makemon(&mons[PM_HUMAN_ZOMBIE], x, y);
X			if (mtmp) {
X				mtmp->mhp = mtmp->mhpmax = 100;
X				mtmp->mspeed = MFAST;
X			}
X		} else {
X#ifdef ARMY
X			if (is_mercenary(&mons[montype]))
X				montype = PM_UNARMORED_SOLDIER;
X#endif
X			mons[montype].pxlth += nl;
X			mtmp = mkmon_at(mons[montype].mname, x, y);
X			mons[montype].pxlth -= nl;
X			if (mtmp) {
X				/* Monster retains its name */
X				mtmp->mnamelth = nl;
X				if (nl) Strcpy(NAME(mtmp), buf);
X				/* No inventory for newly revived monsters */
X				while(obj = (mtmp->minvent)) {
X					mtmp->minvent = obj->nobj;
X					free((genericptr_t)obj);
X				}
X			}
X		}
X	}
X	return mtmp;
X}
X
Xstatic const char charged_objs[] = { WAND_SYM, WEAPON_SYM, ARMOR_SYM, 0 };
X
Xstatic void
Xcancel_item(obj)
Xregister struct obj *obj;
X{
X	if(obj->spe &&
X	  !(obj->otyp == AMULET_OF_YENDOR ||
X	    obj->otyp == WAN_CANCELLATION || /* can't cancel cancellation */
X	    obj->otyp == TIN || obj->otyp == EGG ||
X	    obj->otyp == STATUE ||
X#ifdef MAIL
X	    obj->otyp == SCR_MAIL ||
X#endif
X	    obj->otyp == KEY || obj->otyp == SKELETON_KEY ||
X	    obj->otyp == LARGE_BOX || obj->otyp == CHEST))
X		obj->spe = (obj->olet == WAND_SYM) ? -1 : 0;
X	if (obj->olet == SCROLL_SYM
X#ifdef MAIL
X	    && obj->otyp != SCR_MAIL
X#endif
X	   )
X	    obj->otyp = SCR_BLANK_PAPER;
X	if (obj->olet == POTION_SYM && obj->otyp > POT_BOOZE)
X	    obj->otyp = (obj->otyp==POT_SICKNESS) ? POT_FRUIT_JUICE : POT_WATER;
X	    /* sickness is "biologically contaminated" fruit juice; cancel it
X	     * and it just becomes fruit juice...
X	     */
X	obj->blessed = obj->cursed = FALSE;
X}
X
Xstatic int
Xbhito(obj, otmp)	/* object obj was hit by the effect of wand otmp */
Xregister struct obj *obj, *otmp;	/* returns TRUE if sth was done */
X{
X	register int res = 1;
X	struct obj *otmp2;
X
X	if(obj == uball || obj == uchain)
X		res = 0;
X	else
X	switch(otmp->otyp) {
X	case WAN_POLYMORPH:
X#ifdef SPELLS
X	case SPE_POLYMORPH:
X#endif
X#ifdef MAIL
X		/* You can't send yourself 100 mail messages and then
X		 * polymorph them into useful scrolls
X		 */
X		if (obj->otyp == SCR_MAIL) obj->spe = 1;
X#endif
X		/* preserve symbol and quantity */
X		otmp2 = mkobj_at(obj->olet, obj->ox, obj->oy);
X		otmp2->quan = obj->quan;
X
X		/* keep special fields (including charges on wands) */
X		if (index(charged_objs, otmp2->olet)) otmp2->spe = obj->spe;
X
X		/* Amulet gets cheap   stewr 870807 */
X		if (obj->otyp == AMULET_OF_YENDOR) otmp2->spe = -1;
X
X		/* Wands of wishing max 3 stewr 870808 */
X		if ((otmp2->otyp == WAN_WISHING)
X		    && (obj->spe > 3)) otmp2->spe = 3;
X
X		otmp2->cursed = obj->cursed;
X		otmp2->blessed = obj->blessed;
X		otmp2->rustfree = obj->rustfree;
X
X		/* Keep chest/box traps and poisoned ammo if we may */
X		if (obj->otrapped && Is_box(otmp2))
X			otmp2->otrapped = 1;
X		if (obj->opoisoned && 
X		    (otmp2->olet == WEAPON_SYM && otmp2->otyp <= SHURIKEN))
X			otmp2->opoisoned = 1;
X
X		/* Turn dragon corpses into dragon armors */
X		if (obj->otyp == CORPSE && obj->corpsenm >= PM_GREY_DRAGON
X				&& obj->corpsenm <= PM_YELLOW_DRAGON) {
X			if (!rn2(10)) { /* Random failure */
X				otmp2->otyp = TIN;
X				otmp2->known = otmp2->dknown = 1;
X			} else {
X				otmp2->otyp = DRAGON_SCALE_MAIL;
X				otmp2->olet = ARMOR_SYM;
X				otmp2->spe = 0;
X				otmp2->rustfree = 1;
X				otmp2->quan = 1;
X				otmp2->cursed = 0;
X			}
X			otmp2->corpsenm = obj->corpsenm;
X		}
X
X		/* update the weight */
X		otmp2->owt = weight(otmp2);
X		delobj(obj);
X		break;
X	case WAN_STRIKING:
X#ifdef SPELLS
X	case SPE_FORCE_BOLT:
X#endif
X		if(obj->otyp == BOULDER)
X			fracture_rock(obj);
X		else if(obj->otyp == STATUE)
X			(void) break_statue(obj);
X		else
X			res = 0;
X		break;
X	case WAN_CANCELLATION:
X#ifdef SPELLS
X	case SPE_CANCELLATION:
X#endif
X		cancel_item(obj);
X		break;
X	case WAN_TELEPORTATION:
X#ifdef SPELLS
X	case SPE_TELEPORT_AWAY:
X#endif
X		rloco(obj);
X		break;
X	case WAN_MAKE_INVISIBLE:
X		obj->oinvis = 1;
X		break;
X	case WAN_UNDEAD_TURNING:
X#ifdef SPELLS
X	case SPE_TURN_UNDEAD:
X#endif
X		res = !!revive(obj,FALSE);
X		break;
X	case WAN_OPENING:
X	case WAN_LOCKING:
X#ifdef SPELLS
X	case SPE_KNOCK:
X	case SPE_WIZARD_LOCK:
X#endif
X		if(Is_box(obj))
X			res = boxlock(obj, otmp);
X		else
X			res = 0;
X		if (res /* && obj->olet == WAND_SYM */)
X			makeknown(obj->otyp);
X		break;
X	case WAN_SLOW_MONSTER:		/* no effect on objects */
X#ifdef SPELLS
X	case SPE_SLOW_MONSTER:
X#endif
X	case WAN_SPEED_MONSTER:
X	case WAN_NOTHING:
X#ifdef PROBING
X	case WAN_PROBING:
X#endif
X		res = 0;
X		break;
X	default:
X		impossible("What an interesting effect (%u)", otmp->otyp);
X	}
X	return(res);
X}
X
X/*
X * zappable - returns 1 if zap is available, 0 otherwise.
X *	      it removes a charge from the wand if zappable.
X * added by GAN 11/03/86
X */
Xint
Xzappable(wand)
Xregister struct obj *wand;
X{
X	if(wand->spe < 0 || (wand->spe == 0 && rn2(121)))
X		return 0;
X	if(wand->spe == 0)
X		You("wrest one more spell from the worn-out wand.");
X	wand->spe--;
X	return 1;
X}
X
X/*
X * zapnodir - zaps an NODIR wand.
X * added by GAN 11/03/86
X */
Xvoid
Xzapnodir(wand)
Xregister struct obj *wand;
X{
X	switch(wand->otyp){
X		case WAN_LIGHT:
X			litroom(TRUE);
X			break;
X		case WAN_SECRET_DOOR_DETECTION:
X			if(!findit()) return;
X			break;
X		case WAN_CREATE_MONSTER:
X			{ register int cnt = 1;
X			if(!rn2(23)) cnt += rn2(7) + 1;
X			while(cnt--)
X			    (void) makemon((struct permonst *) 0, u.ux, u.uy);
X			}
X			break;
X		case WAN_WISHING:
X
X			if(u.uluck + rn2(5) < 0) {
X				pline("Unfortunately, nothing happens.");
X				break;
X			}
X			makewish();
X			break;
X	}
X	if(!objects[wand->otyp].oc_name_known) {
X			makeknown(wand->otyp);
X			more_experienced(0,10);
X	}
X}
X
Xstatic void
Xbackfire(otmp)
X
X	register struct obj * otmp;
X{
X	pline("The %s suddenly explodes!", xname(otmp));
X	losehp(d(otmp->spe+2,6), "exploding wand");
X	useup(otmp);
X}
X
Xstatic const char zap_syms[] = { WAND_SYM, 0 };
X
Xint
Xdozap()
X{
X	register struct obj *obj;
X	int	damage;
X
X	obj = getobj(zap_syms, "zap");
X	if(!obj) return(0);
X
X	check_unpaid(obj);
X
X	/* zappable addition done by GAN 11/03/86 */
X	if(!zappable(obj)) pline(nothing_happens);
X	else if(obj->cursed && !rn2(100)) {
X		backfire(obj);	/* the wand blows up in your face! */
X		return(1);
X	} else if(!(objects[obj->otyp].bits & NODIR) && !getdir(1)) {
X		if (!Blind)
X		    pline("The %s glows and fades.", xname(obj));
X		/* make him pay for knowing !NODIR */
X	} else if(!u.dx && !u.dy && !u.dz && !(objects[obj->otyp].bits & NODIR)) {
X	    if((damage = zapyourself(obj)))
X		losehp(damage,"self-inflicted injury");
X	}
X	else {
X		weffects(obj);
X#if defined(ALTARS) && defined(THEOLOGY)
X		if(priesthit) ghod_hitsu();
X		priesthit = FALSE;
X#endif
X	}
X	if (obj->spe < 0) {
X	    pline ("The %s %sturns to dust.",
X		   xname(obj), Blind ? "" : "glows violently, then ");
X	    useup(obj);
X	}
X	return(1);
X}
X
Xint
Xzapyourself(obj)
X	register struct obj	*obj;
X{
X	struct obj	*otmp;
X	int	damage = 0;
X
X	switch(obj->otyp) {
X		case WAN_STRIKING:
X#ifdef SPELLS
X		case SPE_FORCE_BOLT:
X#endif
X		    if(Antimagic) {
X			shieldeff(u.ux, u.uy);
X			pline("Boing!");
X		    } else {
X			You("magically bash yourself!");
X			damage=d(8,6);
X		    }
X		    break;
X		case WAN_LIGHTNING:
X		    makeknown(WAN_LIGHTNING);
X		    if (!Shock_resistance) {
X			pline("Idiot!  You've shocked yourself!");
X			damage = d(12,6);
X		    } else {
X			shieldeff(u.ux, u.uy);
X			You("zap yourself, but seem unharmed.");
X#ifdef POLYSELF
X#ifdef GOLEMS
X			ugolemeffects(AD_ELEC, d(12,6));
X#endif /* GOLEMS */
X#endif
X		    }
X		    if(!Blind) {
X			    You("are blinded by the flash!");
X			    make_blinded((long)rnd(100),FALSE);
X		    }
X		    break;
X		case WAN_FIRE:
X		    makeknown(WAN_FIRE);
X#ifdef SPELLS
X		case SPE_FIREBALL:
X#endif
X#ifdef MUSIC
X		case FIRE_HORN:
X#endif
X		    pline("You've set light to yourself!");
X		    if (Fire_resistance) {
X			shieldeff(u.ux, u.uy);
X			You("feel mildly hot.");
X#ifdef POLYSELF
X#ifdef GOLEMS
X			ugolemeffects(AD_FIRE, d(12,6));
X#endif /* GOLEMS */
X#endif
X		    } else
X			damage = d(12,6);
X		    destroy_item(SCROLL_SYM, AD_FIRE);
X		    destroy_item(POTION_SYM, AD_FIRE);
X#ifdef SPELLS
X		    destroy_item(SPBOOK_SYM, AD_FIRE);
X#endif
X		    break;
X		case WAN_COLD:
X		    makeknown(WAN_COLD);
X#ifdef SPELLS
X		case SPE_CONE_OF_COLD:
X#endif
X#ifdef MUSIC
X		case FROST_HORN:
X#endif
X		    if (Cold_resistance) {
X			shieldeff(u.ux, u.uy);
X			You("feel mildly chilly.");
X#ifdef POLYSELF
X#ifdef GOLEMS
X			ugolemeffects(AD_COLD, d(12,6));
X#endif /* GOLEMS */
X#endif
X		    } else {
X			You("imitate a popsicle!");
X			damage = d(12,6);
X		    }
X		    destroy_item(POTION_SYM, AD_COLD);
X		    break;
X		case WAN_MAGIC_MISSILE:
X		    makeknown(WAN_MAGIC_MISSILE);
X#ifdef SPELLS
X		case SPE_MAGIC_MISSILE:
X#endif
X		    if(Antimagic) {
X			shieldeff(u.ux, u.uy);
X			pline("The missiles bounce!");
X		    } else {
X			damage = d(4,6);
X			pline("Idiot!  You've shot yourself!");
X		    }
X		    break;
X		case WAN_POLYMORPH:
X#ifdef POLYSELF
X		    makeknown(WAN_POLYMORPH);
X#endif
X#ifdef SPELLS
X		case SPE_POLYMORPH:
X#endif
X#ifdef POLYSELF
X		    polyself();
X#else
X		    You("shudder for a moment.");
X#endif
X		    break;
X		case WAN_CANCELLATION:
X#ifdef SPELLS
X		case SPE_CANCELLATION:
X#endif
X#ifdef POLYSELF
X#ifdef GOLEMS
X		    if (u.umonnum == PM_CLAY_GOLEM) {
X			if (!Blind)
X			    pline("Some writing vanishes from your head!");
X			rehumanize();
X			break;
X		    }
X#endif /* GOLEMS */
X#endif
X		    for(otmp = invent; otmp; otmp = otmp->nobj)
X			cancel_item(otmp);
X#ifdef POLYSELF
X		    if(u.mtimedone) rehumanize();
X#endif
X		    flags.botl = 1;  /* because of potential AC change */
X		    find_ac();
X		    break;
X	       case WAN_MAKE_INVISIBLE:
X		    if (!Invisible) makeknown(WAN_MAKE_INVISIBLE);
X		    HInvis |= INTRINSIC;
X		    if (!See_invisible) newsym(u.ux, u.uy);
X		    break;
X	       case WAN_SPEED_MONSTER:
X		    if (!(Fast & INTRINSIC)) {
X			Fast |= INTRINSIC;
X			You("seem to be moving faster.");
X			makeknown(WAN_SPEED_MONSTER);
X		    }
X		    break;
X	       case WAN_SLEEP:
X		    makeknown(WAN_SLEEP);
X#ifdef SPELLS
X		case SPE_SLEEP:
X#endif
X		    if(Sleep_resistance) {
X			shieldeff(u.ux, u.uy);
X			You("don't feel sleepy!");
X		    } else {
X			pline("The sleep ray hits you!");
X			nomul(-rn2(50));
X		    }
X		    break;
X		case WAN_SLOW_MONSTER:
X#ifdef SPELLS
X		case SPE_SLOW_MONSTER:
X#endif
X		    if(Fast & (TIMEOUT | INTRINSIC)) {
X			Fast &= ~(TIMEOUT | INTRINSIC);
X			You("seem to be moving slower.");
X		    }
X		    break;
X		case WAN_TELEPORTATION:
X#ifdef SPELLS
X		case SPE_TELEPORT_AWAY:
X#endif
X		    tele();
X		    break;
X		case WAN_DEATH:
X#ifdef SPELLS
X		case SPE_FINGER_OF_DEATH:
X#endif
X#ifdef POLYSELF
X		    if (is_undead(uasmon)) {
X			pline((obj->otyp == WAN_DEATH) ?
X			  "The wand shoots an apparently harmless beam at you."
X			  : "You seem no deader than before.");
X			break;
X		    }
X#endif
X		    killer = "death ray";
X		    You("irradiate yourself with pure energy!");
X		    You("die.");
X		    makeknown(WAN_DEATH);
X			/* They might survive with an amulet of life saving */
X		    done("died");
X		    break;
X#ifdef SPELLS
X		case SPE_TURN_UNDEAD:
X#endif
X		case WAN_UNDEAD_TURNING:
X#ifdef POLYSELF
X		    if (is_undead(uasmon)) {
X			Printf("You feel frightened and %sstunned.",
X			     Stunned ? "even more " : "");
X			make_stunned(HStun + rnd(30), FALSE);
X		    }
X#endif
X		    break;
X#ifdef SPELLS
X		case SPE_DIG:
X		case SPE_DETECT_UNSEEN:
X#endif
X		case WAN_DIGGING:
X		case WAN_NOTHING:
X		case WAN_OPENING:
X		case WAN_LOCKING:
X#ifdef SPELLS
X		case SPE_KNOCK:
X		case SPE_WIZARD_LOCK:
X#endif
X		    break;
X#ifdef PROBING
X		case WAN_PROBING:
X		    makeknown(WAN_PROBING);
X		    ustatusline();
X		    break;
X#endif
X		default: impossible("object %d used?",obj->otyp);
X	}
X	return(damage);
X}
X
X/* called for various wand and spell effects - M. Stephenson */
Xvoid
Xweffects(obj)
Xregister struct	obj	*obj;
X{
X	xchar zx,zy;
X
X	if(objects[obj->otyp].bits & IMMEDIATE) {
X	    if(u.uswallow)	(void)bhitm(u.ustuck, obj);
X	    else if(u.dz) {
X		if(u.dz > 0 && levl[u.ux][u.uy].omask) {
X		    register struct obj *otmp,*otmp2;
X
X		    /* changed by GAN to hit all objects there */
X		    for(otmp = fobj; otmp ; otmp = otmp2) {
X			otmp2 = otmp->nobj;
X			/* save pointer as bhito may destroy otmp */
X			if(otmp->ox == u.ux && otmp->oy == u.uy)
X			    (void) bhito(otmp, obj);
X		    }
X		}
X	    } else if((obj->otyp == WAN_OPENING) ||
X#ifdef SPELLS
X		      (obj->otyp == SPE_KNOCK) ||
X		      (obj->otyp == SPE_WIZARD_LOCK) ||
X#endif
X		      (obj->otyp == WAN_LOCKING)) {
X		    (void)bhit(u.dx,u.dy,rn1(8,6),0,bhitm,bhito,obj);
X#ifdef STRONGHOLD
X	    } else if(obj->otyp == WAN_STRIKING
X#ifdef SPELLS
X		      || obj->otyp == SPE_FORCE_BOLT
X#endif /* SPELLS /**/
X		      ) {
X		    int x,y;
X		    x = u.ux + u.dx;
X		    y = u.uy + u.dy;
X		    if (find_drawbridge(&x,&y))
X			destroy_drawbridge(x,y);
X
X		    else (void) bhit(u.dx,u.dy,rn1(8,6),0,bhitm,bhito,obj);
X#endif /* STRONGHOLD /**/
X	    } else  (void) bhit(u.dx,u.dy,rn1(8,6),0,bhitm,bhito,obj);
X	} else {
X	    switch(obj->otyp){
X		case WAN_LIGHT:
X#ifdef SPELLS
X		case SPE_LIGHT:
X#endif
X			litroom(TRUE);
X			break;
X		case WAN_SECRET_DOOR_DETECTION:
X#ifdef SPELLS
X		case SPE_DETECT_UNSEEN:
X#endif
X			if(!findit()) return;
X			break;
X		case WAN_CREATE_MONSTER:
X			{ register int cnt = 1;
X			if(!rn2(23)) cnt += rn2(7) + 1;
X			while(cnt--)
X			    (void) makemon((struct permonst *) 0, u.ux, u.uy);
X			}
X			break;
X		case WAN_WISHING:
X			if(u.uluck + rn2(5) < 0) {
X			    pline("Unfortunately, nothing happens.");
X			    break;
X			}
X			makewish();
X			break;
X		case WAN_DIGGING:
X#ifdef SPELLS
X		case SPE_DIG:
X#endif
X			/* Original effect (approximately):
X			 * from CORR: dig until we pierce a wall
X			 * from ROOM: piece wall and dig until we reach
X			 * an ACCESSIBLE place.
X			 * Currently: dig for digdepth positions;
X			 * also down on request of Lennart Augustsson.
X			 */
X			{ register struct rm *room;
X			  register int digdepth,dlx,dly;
X			  register boolean shopdoor = FALSE;
X			if(u.uswallow) {
X				register struct monst *mtmp = u.ustuck;
X
X				You("pierce %s's stomach wall!",
X					mon_nam(mtmp));
X				mtmp->mhp = 1;	/* almost dead */
X				unstuck(mtmp);
X				mnexto(mtmp);
X				break;
X			}
X			if(u.dz) {
X			    if(u.dz < 0) {
X				You("loosen a rock from the ceiling.");
X				pline("It falls on your %s!",
X					body_part(HEAD));
X				losehp(1, "falling rock");
X				(void) mksobj_at((int)ROCK, u.ux, u.uy);
X				fobj->quan = 1;
X				stackobj(fobj);
X				if(Invisible) newsym(u.ux, u.uy);
X			    } else {
X				dighole();
X			    }
X			    break;
X			}
X			zx = u.ux+u.dx;
X			zy = u.uy+u.dy;
X			digdepth = 8 + rn2(18);
X			Tmp_at2(-1, '*');	/* open call */
X			while(--digdepth >= 0) {
X			    if(!isok(zx,zy)) break;
X			    room = &levl[zx][zy];
X			    Tmp_at2(zx,zy);
X			    if(is_maze_lev) {
X				if(IS_WALL(room->typ)) {
X				    if(room->diggable == W_DIGGABLE)
X					room->typ = ROOM;
X				    else if(!Blind)
X					pline("The wall glows then fades.");
X				    break;
X				}
X				if(room->typ == STONE) {
X				    if(room->diggable == W_DIGGABLE)
X					room->typ = CORR;
X				    else if (!Blind)
X					pline("The rock glows then fades.");
X				    break;
X				}
X			    } else
X				if(IS_ROCK(room->typ))
X				    if(may_dig(zx,zy))
X					if(IS_WALL(room->typ) ||
X						room->typ == SDOOR) {
X					    room->typ = DOOR;
X					    room->doormask = D_NODOOR;
X					    if(in_shop(zx,zy)) {
X						shopdoor = TRUE;
X						dlx = zx;
X						dly = zy;
X					    }
X					    digdepth -= 2;
X					} else {
X					    room->typ = CORR;
X					    digdepth--;
X					}
X				    else
X					break;
X				else if(room->typ == DOOR &&
X					(room->doormask & (D_LOCKED | D_CLOSED))) {
X				    room->doormask = D_NODOOR;
X				    if(in_shop(zx,zy)) {
X					shopdoor = TRUE;
X					dlx = zx;
X					dly = zy;
X				    }
X				    digdepth -= 2;
X				}
X			    mnewsym(zx,zy);
X			    zx += u.dx;
X			    zy += u.dy;
X			}
X			mnewsym(zx,zy);	/* not always necessary */
X			Tmp_at2(-1,-1);	/* closing call */
X			if(shopdoor && !in_shop(u.ux, u.uy))
X				pay_for_door(dlx, dly, "destroy");
X			break;
X			}
X		default:
X#ifdef SPELLS
X			if((int) obj->otyp >= SPE_MAGIC_MISSILE) {
X
X			    buzz((int) obj->otyp - SPE_MAGIC_MISSILE + 10,
X				 (int)u.ulevel / 2 + 1, u.ux, u.uy, u.dx, u.dy);
X			} else
X#endif
X
X			    buzz((int) obj->otyp - WAN_MAGIC_MISSILE, 6,
X				 u.ux, u.uy, u.dx, u.dy);
X			break;
X		}
X		if(!objects[obj->otyp].oc_name_known) {
X			makeknown(obj->otyp);
X			more_experienced(0,10);
X		}
X	}
X	return;
X}
X
Xchar *
Xexclam(force)
Xregister int force;
X{
X	/* force == 0 occurs e.g. with sleep ray */
X	/* note that large force is usual with wands so that !! would
X		require information about hand/weapon/wand */
X	return( (force < 0) ? "?" : (force <= 4) ? "." : "!" );
X}
X
Xvoid
Xhit(str,mtmp,force)
Xregister char *str;
Xregister struct monst *mtmp;
Xregister char *force;		/* usually either "." or "!" */
X{
X	if(!cansee(mtmp->mx,mtmp->my) || !flags.verbose) pline("The %s hits it.", str);
X	else pline("The %s hits %s%s", str, mon_nam(mtmp), force);
X}
X
Xvoid
Xmiss(str,mtmp)
Xregister char *str;
Xregister struct monst *mtmp;
X{
X	pline("The %s misses %s.", str,
X	      (cansee(mtmp->mx,mtmp->my) && flags.verbose) ? mon_nam(mtmp) : "it");
X}
X
X/* bhit: called when a weapon is thrown (sym = obj->olet) or when an
X   IMMEDIATE wand is zapped (sym = 0); the weapon falls down at end of
X   range or when a monster is hit; the monster is returned, and bhitpos
X   is set to the final position of the weapon thrown; the ray of a wand
X   may affect several objects and monsters on its path - for each of
X   these an argument function is called. */
X/* check !u.uswallow before calling bhit() */
X
Xstruct monst *
Xbhit(ddx,ddy,range,sym,fhitm,fhito,obj)
Xregister int ddx,ddy,range;		/* direction and range */
Xchar sym;				/* symbol displayed on path */
Xint (*fhitm)(), (*fhito)();		/* fns called when mon/obj hit */
Xstruct obj *obj;			/* 2nd arg to fhitm/fhito */
X{
X	register struct monst *mtmp;
X	register struct obj *otmp;
X	register int typ;
X
X	bhitpos.x = u.ux;
X	bhitpos.y = u.uy;
X
X	if(sym) {
X		tmp_at(-1, sym);	/* open call */
X		tmp_at(-3, (int)AT_OBJ);
X	}
X	while(range-- > 0) {
X		bhitpos.x += ddx;
X		bhitpos.y += ddy;
X		typ = levl[bhitpos.x][bhitpos.y].typ;
X#ifdef STRONGHOLD
X		if(IS_DRAWBRIDGE(typ))
X		    switch (obj->otyp) {
X			case WAN_OPENING:
X# ifdef SPELLS
X			case SPE_KNOCK:
X# endif
X			    (void) open_drawbridge(bhitpos.x,bhitpos.y);
X			    break;
X			case WAN_LOCKING:
X# ifdef SPELLS
X			case SPE_WIZARD_LOCK:
X# endif
X			    (void) close_drawbridge(bhitpos.x,bhitpos.y);
X		    }
X#endif /* STRONGHOLD /**/
X		if(levl[bhitpos.x][bhitpos.y].mmask){
X			mtmp = m_at(bhitpos.x,bhitpos.y);
X			if(sym) {
X				tmp_at(-1, -1);	/* close call */
X				return(mtmp);
X			}
X			(*fhitm)(mtmp, obj);
X			range -= 3;
X		}
X		/* modified by GAN to hit all objects */
X		if(fhito && levl[bhitpos.x][bhitpos.y].omask){
X		    int hitanything = 0;
X		    otmp = fobj;
X		    /* Fix for polymorph bug, Tim Wright */
X		    while(otmp) { /* was a "for" loop.  */
X			register struct obj *next_obj;
X
X			next_obj = otmp->nobj;
X			if(otmp->ox == bhitpos.x && otmp->oy == bhitpos.y)
X			    hitanything += (*fhito)(otmp, obj);
X			otmp = next_obj;
X		    }
X		    if(hitanything)	range--;
X		}
X		if(IS_DOOR(typ) || typ == SDOOR) {
X		    switch (obj->otyp) {
X			case WAN_OPENING:
X			case WAN_LOCKING:
X#ifdef SPELLS
X			case SPE_KNOCK:
X			case SPE_WIZARD_LOCK:
X#endif
X			    if (doorlock(obj,bhitpos.x,bhitpos.y))
X				    makeknown(obj->otyp);
X			    break;
X		    }
X		}
X		if(!ZAP_POS(typ) || (IS_DOOR(typ) &&
X		   (levl[bhitpos.x][bhitpos.y].doormask & (D_LOCKED | D_CLOSED)))
X		  ) {
X			bhitpos.x -= ddx;
X			bhitpos.y -= ddy;
X			break;
X		}
X		if(sym) tmp_at(bhitpos.x, bhitpos.y);
X#ifdef SINKS
X		if(sym && IS_SINK(typ))
X			break;	/* physical objects fall onto sink */
X#endif
X	}
X
X	/* leave last symbol unless in a pool */
X	if(sym)
X	   tmp_at(-1, is_pool(bhitpos.x,bhitpos.y) ? -1 : 0);
X	return (struct monst *)0;
X}
X
Xstruct monst *
Xboomhit(dx, dy)
Xint dx, dy;
X{
X	register int i, ct;
X	char sym = ')';
X
X	bhitpos.x = u.ux;
X	bhitpos.y = u.uy;
X
X	for(i=0; i<8; i++) if(xdir[i] == dx && ydir[i] == dy) break;
X	tmp_at(-1, sym);	/* open call */
X	tmp_at(-3, (int)AT_OBJ);
X	for(ct=0; ct<10; ct++) {
X		if(i == 8) i = 0;
X		sym = ')' + '(' - sym;
X		tmp_at(-2, sym);	/* change let call */
X		dx = xdir[i];
X		dy = ydir[i];
X		bhitpos.x += dx;
X		bhitpos.y += dy;
X		if(levl[bhitpos.x][bhitpos.y].mmask){
X			tmp_at(-1,-1);
X			return(m_at(bhitpos.x,bhitpos.y));
X		}
X		if(!ZAP_POS(levl[bhitpos.x][bhitpos.y].typ)) {
X			bhitpos.x -= dx;
X			bhitpos.y -= dy;
X			break;
X		}
X		if(bhitpos.x == u.ux && bhitpos.y == u.uy) { /* ct == 9 */
X			if(rn2(20) >= ACURR(A_DEX)){ /* we hit ourselves */
X				(void) thitu(10, rnd(10), "boomerang");
X				break;
X			} else {	/* we catch it */
X				tmp_at(-1,-1);
X				pline("Skillfully, you catch the boomerang.");
X				return(&youmonst);
X			}
X		}
X		tmp_at(bhitpos.x, bhitpos.y);
X		if(ct % 5 != 0) i++;
X#ifdef SINKS
X		if(IS_SINK(levl[bhitpos.x][bhitpos.y].typ))
X			break;	/* boomerang falls on sink */
X#endif
X	}
X	tmp_at(-1, -1);	/* do not leave last symbol */
X	return (struct monst *)0;
X}
X
Xstatic uchar
Xdirlet(dx, dy)
Xregister int dx, dy;
X{
X	return
X	    (dx == dy) ? LSLANT_SYM :
X	    (dx && dy) ? RSLANT_SYM :
X	    dx ? HBEAM_SYM : VBEAM_SYM;
X}
X
Xstatic int
Xzhit(mon, type, nd)			/* returns damage to mon */
Xregister struct monst *mon;
Xregister int type, nd;
X{
X	register int tmp = 0;
X	register int abstype = abs(type) % 10;
X
X	switch(abstype) {
X	case 0:			/* magic missile */
X		tmp = d(nd,6);
X		break;
X	case 1:			/* fire */
X		if(resists_fire(mon->data)) {
X		    shieldeff(mon->mx, mon->my);
X		    break;
X		}
X		tmp = d(nd,6);
X		if(resists_cold(mon->data)) tmp += 7;
X		break;
X	case 2:			/* sleep */
X		tmp = 0;
X		if(resists_sleep(mon->data) ||
X		   resist(mon, (type == 2) ? WAND_SYM : '\0', 0, NOTELL))
X			shieldeff(mon->mx, mon->my);
X		else	mon->mfroz = 1;
X		break;
X	case 3:			/* cold */
X		if(resists_cold(mon->data)) {
X		    shieldeff(mon->mx, mon->my);
X		    break;
X		}
X		tmp = d(nd,6);
X		if(resists_fire(mon->data)) tmp += d(nd, 3);
X		break;
X	case 4:			/* death/disintegration */
X		if(abs(type) != 24) {	/* death */
X		    if(is_undead(mon->data)) {
X			shieldeff(mon->mx, mon->my);
X			break;
X		    }
X		    type = 0; /* so they don't get saving throws */
X		}
X		tmp = mon->mhp+1;
X		break;
X	case 5:			/* lightning */
X		if(resists_elec(mon->data)) {
X		    shieldeff(mon->mx, mon->my);
X		    break;
X		}
X		tmp = d(nd,6);
X		{
X			register unsigned rnd_tmp = rnd(50);
X			mon->mcansee = 0;
X			if((mon->mblinded + rnd_tmp) > 127)
X				mon->mblinded = 127;
X			else mon->mblinded += rnd_tmp;
X		}
X		break;
X	case 6:			/* poison */
X		if(resists_poison(mon->data)) {
X		    shieldeff(mon->mx, mon->my);
X		    break;
X		}
X		tmp = d(nd,6);
X		break;
X	case 7:			/* acid */
X		if(resists_acid(mon->data)) {
X		    shieldeff(mon->mx, mon->my);
X		    break;
X		}
X		tmp = d(nd,6);
X		break;
X	}
X	if (type >= 0)
X	    if (resist(mon, (type < 10) ? WAND_SYM : '\0', 0, NOTELL)) tmp /= 2;
X	mon->mhp -= tmp;
X	return(tmp);
X}
X
X/*
X * burn scrolls on floor at position x,y
X * return the number of scrolls burned
X */
Xstatic int
Xburn_floor_scrolls(x, y)
Xint x, y;
X{
X	register struct obj *obj, *obj2;
X	register int scrquan, i, cnt = 0;
X
X	if(levl[x][y].omask)
X	for(obj = fobj; obj; obj = obj2) {
X	    obj2 = obj->nobj;
X	    /* Bug fix - KAA */
X	    if(obj->ox == x && obj->oy == y && obj->olet == SCROLL_SYM) {
X		scrquan = obj->quan;
X		for(i = 1; i <= scrquan ; i++)
X		    if(!rn2(3))  {
X			cnt++;
X			if(in_shop(u.ux, u.uy))
X				addtobill(obj, FALSE);
X			useupf(obj);
X		    }
X	    }
X	}
X	return(cnt);
X}
X
X/* type == 0 to 9     : you shooting a wand */
X/* type == 10 to 19   : you casting a spell */
X/* type == 20 to 29   : you breathing as a monster */
X/* type == -10 to -19   : monster casting spell */
X/* type == -20 to -29 : monster breathing at you */
X/* called with dx = dy = 0 with vertical bolts */
Xvoid
Xbuzz(type,nd,sx,sy,dx,dy)
Xregister int type, nd;
Xregister xchar sx,sy;
Xregister int dx,dy;
X{
X	int abstype = abs(type) % 10;
X	register char *fltxt = fl[abs(type)];
X	struct rm *lev;
X	xchar range, olx, oly;
X	struct monst *mon;
X	register boolean bodyhit = FALSE;
X	register boolean shopdoor = FALSE;
X
X	if(u.uswallow) {
X		register int tmp;
X
X		if(type < 0) return;
X		tmp = zhit(u.ustuck, type, nd);
X		if(!u.ustuck)	u.uswallow = 0;
X		else	pline("The %s rips into %s%s",
X				fltxt, mon_nam(u.ustuck), exclam(tmp));
X		if (u.ustuck->mhp < 1)
X			killed(u.ustuck);
X		return;
X	}
X	if(type < 0) pru();
X	range = rn1(7,7);
X	Tmp_at2(-1, (int) dirlet(dx,dy));	/* open call */
X#ifdef MSDOSCOLOR
X	Tmp_at2(-3, (int)(abstype == 1 ? AT_RED :	/* fire */
X			  abstype == 3 || abstype == 5 ? AT_WHITE :	/* cold/elec */
X			  AT_ZAP);
X#endif
X	while(range-- > 0) {
X		sx += dx;
X		sy += dy;
X		if((lev = &levl[sx][sy])->typ) Tmp_at2(sx,sy);
X		else {
X			int bounce = 0;
X			if(cansee(sx-dx,sy-dy))
X				pline("The %s bounces!", fltxt);
X			if(ZAP_POS(levl[sx][sy-dy].typ))
X				bounce = 1;
X			if(ZAP_POS(levl[sx-dx][sy].typ)) {
X				if(!bounce || rn2(2)) bounce = 2;
X			}
X			switch(bounce){
X			case 0:
X				dx = -dx;
X				dy = -dy;
X				continue;
X			case 1:
X				dy = -dy;
X				sx -= dx;
X				break;
X			case 2:
X				dx = -dx;
X				sy -= dy;
X				break;
X			}
X			Tmp_at2(-2,(int) dirlet(dx,dy));
X			continue;
X		}
X		if(is_pool(sx,sy) && abstype == 1 /* fire */) {
X#ifdef STRONGHOLD
X			if(lev->typ != POOL) {	/* MOAT or DRAWBRIDGE_UP */
X			    if(cansee(sx,sy))
X				pline("Some water evaporates.");
X			    else if(flags.soundok)
X				You("hear a hissing sound.");
X			} else {
X#endif
X			    register struct trap *ttmp;
X
X			    range -= 3;
X			    lev->typ = ROOM;
X			    mnewsym(sx,sy);
X			    if(cansee(sx,sy)) pline("The water evaporates.");
X			    else if(flags.soundok)
X				You("hear a hissing sound.");
X			    ttmp = maketrap(sx, sy, PIT);
X			    ttmp->tseen = 1;
X#ifdef STRONGHOLD
X			}
X#endif
X		}
X		if(is_pool(sx,sy) && abstype == 3 /* cold */) {
X			boolean moat = (lev->typ != POOL);
X
X			range -= 3;
X#ifdef STRONGHOLD
X			if(lev->typ == DRAWBRIDGE_UP)
X				lev->drawbridgemask |= DB_FLOOR;
X			else
X#endif
X				lev->typ = ROOM;
X			mnewsym(sx,sy);
X			if(cansee(sx,sy)) {
X				if(moat)
X					pline("The moat is bridged with ice!");
X				else 	pline("The water freezes.");
X			} else if(flags.soundok)
X				You("hear a crackling sound.");
X		}
X		if(IS_DOOR(lev->typ) && (lev->doormask & (D_LOCKED | D_CLOSED))) {
X			range = 0;
X			switch(abstype) {
X			case 1:
X			   lev->doormask = D_NODOOR;
X			   if(cansee(sx,sy))
X				pline("The door is consumed in flames!");
X			   else You("smell smoke.");
X			   if(type >= 0 && in_shop(sx, sy)) {
X				shopdoor = TRUE;
X				olx = sx;
X				oly = sy;
X			   }
X			   break;
X			case 3:
X			   lev->doormask = D_NODOOR;
X			   if(cansee(sx,sy))
X				pline("The door freezes and shatters!");
X			   else You("feel cold.");
X			   if(type >= 0 && in_shop(sx, sy)) {
X				shopdoor = TRUE;
X				olx = sx;
X				oly = sy;
X			   }
X			   break;
X			case 4:
X			   lev->doormask = D_NODOOR;
X			   if(cansee(sx,sy))
X				pline("The door disintegrates!");
X			   else if(flags.soundok)
X				You("hear a crashing sound.");
X			   if(type >= 0 && in_shop(sx, sy)) {
X				shopdoor = TRUE;
X				olx = sx;
X				oly = sy;
X			   }
X			   break;
X			case 5:
X			   lev->doormask = D_BROKEN;
X			   if(cansee(sx,sy))
X				pline("The door splinters!");
X			   else if(flags.soundok)
X				You("hear a crackling sound.");
X			   if(type >= 0 && in_shop(sx, sy)) {
X				shopdoor = TRUE;
X				olx = sx;
X				oly = sy;
X			   }
X			   break;
X			default:
X			   if(cansee(sx,sy)) {
X			       if (type >= 0 && type <= 9)
X				   pline("The door absorbs your bolt!");
X			       else if (type >= 10 && type <= 19)
X				   pline("The door absorbs your spell!");
X#ifdef POLYSELF
X			       else if (type >= 20 && type <= 29)
X				   pline("The door absorbs your blast!");
X#endif
X			       else if (type >= -19 && type <= -10)
X				   pline("The door absorbs the spell!");
X			       else
X				   pline("The door absorbs the blast!");
X			   } else You("feel vibrations.");
X			   break;
X			}
X		}
X		if(levl[sx][sy].omask && abstype == 1)
X			if(burn_floor_scrolls(sx,sy) && cansee(sx,sy))  {
X			    mnewsym(sx,sy);
X			    if(!Blind)
X				You("see a puff of smoke.");
X			}
X		if(levl[sx][sy].mmask){
X			mon = m_at(sx,sy);
X			/* Cannot use wakeup() which also angers the monster */
X			mon->msleep = 0;
X			if(mon->mimic) seemimic(mon);
X			if(type >= 0) {
X			    setmangry(mon);
X#if defined(ALTARS) && defined(THEOLOGY)
X			    if(mon->ispriest && in_temple(mon->mx, mon->my))
X				priesthit = TRUE;
X#endif
X			}
X			if(rnd(20) < 18 + mon->data->ac) {
X			    register int tmp = zhit(mon, type, nd);
X			    if(mon->mhp < 1) {
X				if(type < 0) {
X				    if(cansee(mon->mx,mon->my))
X				      pline("%s is killed by the %s!",
X					    Monnam(mon), fltxt);
X				    mondied(mon);
X				} else
X				    killed(mon);
X			     } else
X				hit(fltxt, mon, exclam(tmp));
X			    range -= 2;
X			} else
X				miss(fltxt,mon);
X		} else if(sx == u.ux && sy == u.uy) {
X			nomul(0);
X			if(rnd(20) < 18+u.uac) {
X				register int dam = 0;
X				range -= 2;
X				pline("The %s hits you!",fltxt);
X				if (Reflecting) {
X				    if (!Blind) {
X					if(Reflecting & WORN_AMUL)
X					    makeknown(AMULET_OF_REFLECTION);
X					else
X					    makeknown(SHIELD_OF_REFLECTION);
X			pline("But it reflects from your %s!",
X				(Reflecting & W_AMUL) ? "amulet" : "shield");
X				    } else
X			pline("For some reason you are not affected!");
X				    if (dx) dx = -dx;
X				    if (dy) dy = -dy;
X				    shieldeff(sx, sy);
X				}
X				else switch(abstype) {
X				case 0:		/* magic missile */
X				    if(Antimagic) {
X					shieldeff(sx, sy);
X					pline("The missiles bounce off!");
X				    } else dam = d(nd,6);
X				    break;
X				case 1:		/* fire */
X				    if(Fire_resistance) {
X					shieldeff(sx, sy);
X					You("don't feel hot!");
X#ifdef POLYSELF
X#ifdef GOLEMS
X					ugolemeffects(AD_FIRE, d(nd, 6));
X#endif /* GOLEMS */
X#endif
X				    } else dam = d(nd, 6);
X				    while (1) {
X					switch(rn2(5)) {
X					case 0:
X		if (!rust_dmg(uarmh, "leather helmet", 0, FALSE)) continue;
X					    break;
X					case 1:
X					    bodyhit = TRUE;
X					    if (uarmc) break;
X		(void)(rust_dmg(uarm, "leather armor", 0, FALSE));
X					    break;
X					case 2:
X		if (!rust_dmg(uarms, "wooden shield", 0, FALSE)) continue;
X					    break;
X					case 3:
X		if (!rust_dmg(uarmg, "gloves", 0, FALSE)) continue;
X					    break;
X					case 4:
X		if (!rust_dmg(uarmf, "boots", 0, FALSE)) continue;
X					    break;
X					}
X					break; /* Out of while loop */
X		    		    }
X				    if(!rn2(3) && bodyhit)
X					destroy_item(POTION_SYM, AD_FIRE);
X				    if(!rn2(3) && bodyhit)
X					destroy_item(SCROLL_SYM, AD_FIRE);
X#ifdef SPELLS
X				    if(!rn2(5) && bodyhit)
X					destroy_item(SPBOOK_SYM, AD_FIRE);
X#endif
X				    break;
X				case 2:		/* sleep */
X				    if(Sleep_resistance) {
X					shieldeff(u.ux, u.uy);
X					You("don't feel sleepy.");
X				    } else nomul(-d(nd,25)); /* sleep ray */
X				    break;
X				case 3:		/* cold */
X				    if(Cold_resistance) {
X					shieldeff(sx, sy);
X					You("don't feel cold.");
X#ifdef POLYSELF
X#ifdef GOLEMS
X					ugolemeffects(AD_COLD, d(nd, 6));
X#endif /* GOLEMS */
X#endif
X				    } else
X					dam = d(nd, 6);
X				    if(!rn2(3))
X					destroy_item(POTION_SYM, AD_COLD);
X				    break;
X				case 4:		/* death */
X				    if(type == -24) { /* disintegration */
X					if(uarms) {
X					    (void) destroy_arm(uarms);
X					} else if (uarm) {
X				if (Disint_resistance & WORN_ARMOR)
X					Your("armor absorbs the blast!");
X				else (void) destroy_arm(uarm);
X					}
X				    break;
X				    }
X#ifdef POLYSELF
X				    else if(is_undead(uasmon)) {
X					shieldeff(sx, sy);
X					You("seem unaffected.");
X					break;
X				    }
X#endif
X				    u.uhp = -1;
X				    break;
X				case 5:		/* lightning */
X				    if (Shock_resistance) {
X					shieldeff(sx, sy);
X					You("aren't affected.");
X#ifdef POLYSELF
X#ifdef GOLEMS
X					ugolemeffects(AD_ELEC, d(nd, 6));
X#endif /* GOLEMS */
X#endif
X				    } else
X					dam = d(nd, 6);
X				    break;
X				case 6:		/* poison */
X				    poisoned("blast", A_DEX, "poisoned blast");
X				    break;
X				case 7:		/* acid */
X				    pline("The acid burns!");
X				    dam = d(nd,6);
X				    if(!rn2(6)) corrode_weapon();
X				    if(!rn2(6)) corrode_armor();
X				    break;
X				}
X				losehp(dam,fltxt);
X			} else pline("The %s whizzes by you!",fltxt);
X			if (abstype == 5 && !Blind) { /* LIGHTNING */
X		    		You("are blinded by the flash!");
X				make_blinded((long)d(nd,50),FALSE);
X				seeoff(0);
X			}
X			stop_occupation();
X		}
X		if(!ZAP_POS(lev->typ)) {
X			int bounce = 0, rmn;
X			if(cansee(sx,sy)) pline("The %s bounces!", fltxt);
X			range--;
X			if(!dx || !dy || !rn2(20)){
X				dx = -dx;
X				dy = -dy;
X			} else {
X			  if(ZAP_POS(rmn = levl[sx][sy-dy].typ) &&
X			    (IS_ROOM(rmn) || ZAP_POS(levl[sx+dx][sy-dy].typ)))
X				bounce = 1;
X			  if(ZAP_POS(rmn = levl[sx-dx][sy].typ) &&
X			    (IS_ROOM(rmn) || ZAP_POS(levl[sx-dx][sy+dy].typ)))
X				if(!bounce || rn2(2))
X					bounce = 2;
X
X			  switch(bounce){
X			  case 0:
X				dy = -dy;
X				dx = -dx;
X				break;
X			  case 1:
X				dy = -dy;
X				break;
X			  case 2:
X				dx = -dx;
X				break;
X			  }
X			  Tmp_at2(-2, (int) dirlet(dx,dy));
X			}
X		}
X	}
X	Tmp_at2(-1,-1);
X	if(shopdoor && !in_shop(u.ux, u.uy))
X		pay_for_door(olx, oly, abstype == 1 ? "burn away" :
X				       abstype == 3 ? "shatter" :
X				       abstype == 4 ? "disintegrate" :
X				       "destroy");
X}
X
Xvoid
Xrloco(obj)
Xregister struct obj *obj;
X{
X	register int tx, ty, otx, oty;
X
X	otx = obj->ox;
X	oty = obj->oy;
X	do {
X		tx = rn1(COLNO-3,2);
X		ty = rn2(ROWNO);
X	} while(!goodpos(tx,ty));
X	obj->ox = tx;
X	obj->oy = ty;
X	set_omask(otx,oty);
X	if(cansee(otx,oty))
X		newsym(otx,oty);
X	levl[tx][ty].omask = 1;
X	if(cansee(tx,ty))
X		newsym(tx,ty);
X}
X
Xvoid
Xfracture_rock(obj)	/* fractured by pick-axe or wand of striking */
Xregister struct obj *obj;		   /* no texts here! */
X{
X	/* unpobj(obj); */
X	obj->otyp = ROCK;
X	obj->blessed = FALSE;
X	obj->quan = 7 + rn2(60);
X	obj->owt = weight(obj);
X	obj->olet = GEM_SYM;
X	obj->known = FALSE;
X	if(cansee(obj->ox,obj->oy))
X		prl(obj->ox,obj->oy);
X}
X
Xboolean
Xbreak_statue(obj)
Xregister struct obj *obj;
X{
X	struct trap *trap;
X
X	if(trap = t_at(obj->ox,obj->oy))
X	    if(obj->corpsenm == trap->pm)
X		if(makemon(&mons[trap->pm], obj->ox, obj->oy)) {
X		    pline("Instead of shattering, the statue suddenly comes alive!");
X		    delobj(obj);
X		    deltrap(trap);
X		    return FALSE;
X		}
X	if (obj->spe) {
X	    struct obj *magazine;
X#ifdef SPELLS
X	    magazine = mkobj_at(SPBOOK_SYM, obj->ox, obj->oy);
X#else
X	    magazine = mkobj_at(SCROLL_SYM, obj->ox, obj->oy);
X#endif
X	    magazine->blessed = obj->blessed;
X	    magazine->cursed = obj->cursed;
X	}
X	fracture_rock(obj);
X	return TRUE;
X}
X
Xconst char *destroy_strings[] = {
X	"freezes and shatters", "freeze and shatter", "shattered potion",
X	"boils and explodes", "boil and explode", "boiling potion",
X	"catches fire and burns", "catch fire and burn", "burning scroll",
X	"catches fire and burns", "catch fire and burn", "burning book",
X	"turns to dust and vanishes", "turn to dust and vanish", "",
X	"breaks apart and explodes", "break apart and explode", "exploding wand"
X};
X
Xvoid
Xdestroy_item(osym, dmgtyp)
Xregister int osym, dmgtyp;
X{
X	register struct obj *obj, *obj2;
X	register int quan, i, cnt, dmg, xresist, skip;
X	register int dindx;
X	char *mult;
X
X	for(obj = invent; obj; obj = obj2) {
X
X	    obj2 = obj->nobj;
X	    if(obj->olet != osym) continue; /* test only objs of type osym */
X	    xresist = skip = 0;
X
X	    switch(dmgtyp) {
X		case AD_COLD:
X		    if(osym == POTION_SYM) {
X			quan = obj->quan;
X			dindx = 0;
X			dmg = rnd(4);
X		    } else skip++;
X	    	    break;
X		case AD_FIRE:
X		    xresist = (Fire_resistance && obj->olet != POTION_SYM);
X
X		    /* Let's say scrolls of fire are fire resistant */
X
X		    if (obj->otyp == SCR_FIRE)
X		      skip++;
X		    quan = obj->quan;
X		    switch(osym) {
X			case POTION_SYM:
X			    dindx = 1;
X			    dmg = rnd(6);
X			    break;
X			case SCROLL_SYM:
X			    dindx = 2;
X			    dmg = 1;
X			    break;
X#ifdef SPELLS
X			case SPBOOK_SYM:
X			    dindx = 3;
X			    dmg = 1;
X			    break;
X#endif
X			default:
X			    skip++;
X			    break;
X		    }
X		    break;
X		case AD_ELEC:
X		    xresist = (Shock_resistance && obj->olet != RING_SYM);
X		    quan = obj->quan;
X		    switch(osym) {
X			case RING_SYM:
X			    if(obj->otyp == RIN_SHOCK_RESISTANCE)
X				    { skip++; break; }
X			    dindx = 4;
X			    dmg = 0;
X			    break;
X			case WAND_SYM:
X			    if(obj->otyp == WAN_LIGHTNING) { skip++; break; }
X			    dindx = 5;
X			    dmg = rnd(10);
X			    break;
X			default:
X			    skip++;
X			    break;
X		    }
X		    break;
X		default:
X		    skip++;
X		    break;
X	    }
X	    if(!skip) {
X		for(i = cnt = 0; i < quan; i++)
X		    if(!rn2(3)) cnt++;
X
X		if(!cnt) continue;
X		if(cnt == quan)	mult = "Your";
X		else	mult = (cnt == 1) ? "One of your" : "Some of your";
X		pline("%s %s %s!", mult, xname(obj),
X			(cnt > 1) ? destroy_strings[dindx*3 + 1]
X				  : destroy_strings[dindx*3]);
X		if(osym == POTION_SYM && dmgtyp != AD_COLD)
X		    potionbreathe(obj);
X		for(i = 0; i < cnt; i++) useup(obj);
X		if(dmg) {
X		    if(xresist)	You("aren't hurt!");
X		    else	losehp(dmg, destroy_strings[dindx*3 + 2]);
X		}
X	    }
X	}
X	return;
X}
X
Xint
Xdestroy_mitem(mtmp, osym, dmgtyp)
Xregister struct monst *mtmp;
Xregister int osym, dmgtyp;
X{
X	register struct obj *obj, *obj2;
X	register int quan, i, cnt, skip, tmp = 0;
X	register int dindx;
X
X	for(obj = mtmp->minvent; obj; obj = obj2) {
X
X	    obj2 = obj->nobj;
X	    if(obj->olet != osym) continue; /* test only objs of type osym */
X	    skip = 0;
X
X	    switch(dmgtyp) {
X		case AD_COLD:
X		    if(osym == POTION_SYM) {
X			quan = obj->quan;
X			dindx = 0;
X			tmp++;
X		    } else skip++;
X	    	    break;
X		case AD_FIRE:
X		    /* Let's say scrolls of fire are fire resistant */
X
X		    if (obj->otyp == SCR_FIRE)
X		      skip++;
X		    quan = obj->quan;
X		    switch(osym) {
X			case POTION_SYM:
X			    dindx = 1;
X			    tmp++;
X			    break;
X			case SCROLL_SYM:
X			    dindx = 2;
X			    tmp++;
X			    break;
X#ifdef SPELLS
X			case SPBOOK_SYM:
X			    dindx = 3;
X			    tmp++;
X			    break;
X#endif
X			default:
X			    skip++;
X			    break;
X		    }
X		    break;
X		case AD_ELEC:
X		    quan = obj->quan;
X		    switch(osym) {
X			case RING_SYM:
X			    if(obj->otyp == RIN_SHOCK_RESISTANCE)
X				    { skip++; break; }
X			    dindx = 4;
X			    break;
X			case WAND_SYM:
X			    if(obj->otyp == WAN_LIGHTNING) { skip++; break; }
X			    dindx = 5;
X			    tmp++;
X			    break;
X			default:
X			    skip++;
X			    break;
X		    }
X		    break;
X		default:
X		    skip++;
X		    break;
X	    }
X	    if(!skip) {
X		for(i = cnt = 0; i < quan; i++)
X		    if(!rn2(3)) cnt++;
X
X		if(!cnt) continue;
X		pline("%s's %s %s!", Monnam(mtmp), xname(obj),
X			(cnt > 1) ? destroy_strings[dindx*3 + 1]
X				  : destroy_strings[dindx*3]);
X		for(i = 0; i < cnt; i++) m_useup(mtmp, obj);
X	    }
X	}
X	return(tmp);
X}
X
X/*ARGSUSED*/
Xint
Xresist(mtmp, olet, damage, tell)
Xregister struct monst	*mtmp;
Xregister char	olet;
Xregister int	damage, tell;
X{
X	register int	resisted = 0;
X#ifdef HARD
X	register int	level;
X
X	switch(olet)  {
X
X	    case WAND_SYM:
X			level = 8;
X			break;
X
X	    case SCROLL_SYM:
X			level = 6;
X			break;
X
X	    case POTION_SYM:
X			level = 5;
X			break;
X
X	    default:	level = u.ulevel;
X			break;
X	}
X
X	resisted = (rn2(100) - mtmp->m_lev + level) < mtmp->data->mr;
X	if(resisted) {
X
X		if(tell) {
X		    shieldeff(mtmp->mx, mtmp->my);
X		    pline("%s resists!", canseemon(mtmp) ? Monnam(mtmp) : "It");
X		}
X		mtmp->mhp -= damage/2;
X	} else
X#endif
X		mtmp->mhp -= damage;
X
X	if(mtmp->mhp < 1) killed(mtmp);
X	return(resisted);
X}
X
Xvoid
Xmakewish()
X{
X	char buf[BUFSZ];
X	register struct obj *otmp;
X	int wishquan, mergquan;
X	register boolean dropit = (inv_cnt() >= 52);
X	int tries = 0;
X
Xretry:
X	You("may wish for an object.  What do you want? ");
X	getlin(buf);
X	if(buf[0] == '\033') buf[0] = 0;
X/* Note: if they wished for and got a non-object successfully, such as gold,
X * otmp = &zeroobj
X */
X	otmp = readobjnam(buf);
X	if (!otmp) {
X	    pline("Nothing fitting that description exists in the game.");
X	    if (++tries < 5) goto retry;
X	    pline(thats_enough_tries);
X	    if (!(otmp = readobjnam((char *)0)))
X		return; /* for safety; should never happen */
X	}
X	if (otmp != &zeroobj) {
X	    if(dropit) {
X		pline("Oops!  The %s drop%s to the floor!", xname(otmp),
X			otmp->quan > 1 ? "" : "s");
X		dropy(otmp);
X	    } else {
X	    	wishquan = otmp->quan;
X	    	otmp = addinv(otmp);
X	    	mergquan = otmp->quan;
X	    	otmp->quan = wishquan; /* to fool prinv() */
X	    	prinv(otmp);
X	    	otmp->quan = mergquan;
X	    }
X#ifdef WIZARD
X 	if (!wizard)
X#endif
X	    if(otmp->otyp == WAN_WISHING) otmp->recharged = 1;
X
X#ifdef THEOLOGY
X	    u.ublesscnt += rn1(100,50);  /* the gods take notice */
X#endif
X	}
X}
END_OF_FILE
if test 44087 -ne `wc -c <'src/zap.c'`; then
    echo shar: \"'src/zap.c'\" unpacked with wrong size!
fi
# end of 'src/zap.c'
fi
echo shar: End of archive 2 \(of 38\).
cp /dev/null ark2isdone
MISSING=""
for I in 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 ; do
    if test ! -f ark${I}isdone ; then
	MISSING="${MISSING} ${I}"
    fi
done
if test "${MISSING}" = "" ; then
    echo You have unpacked all 38 archives.
    rm -f ark[1-9]isdone ark[1-9][0-9]isdone
else
    echo You still need to unpack the following archives:
    echo "        " ${MISSING}
fi
##  End of shell archive.
exit 0