From: nethack.rankin Date: Sat, 3 Dec 2005 03:16:25 +0000 (+0000) Subject: fix #Q241 - swallowing Medusa (trunk only) X-Git-Tag: MOVE2GIT~1196 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=6955f1ab63b6ee1f934559bc735ca4231de7efd7;p=nethack fix #Q241 - swallowing Medusa (trunk only) From a bug report, eating Medusa's corpse is fatal but devouring her whole (purple worm or poly'd hero) was not. Now it will be. Also, being killed by swallowing a cockatrice or a Rider could have disclosed "you went without food" if you hadn't eaten anything else prior. This fixes that too, although it might be a little silly if it happens to a monk since he'll feel guilty (for non-vegetarian diet) right as he dies. --- diff --git a/doc/fixes35.0 b/doc/fixes35.0 index 015d8a6a6..4716ff969 100644 --- a/doc/fixes35.0 +++ b/doc/fixes35.0 @@ -100,6 +100,8 @@ adjust feedback for gas spore explosion when hallucinating traps detected by scroll or crystal ball overlooked carried or buried chests can't wish for a trapped box/chest/tin by specifying "poisoned" grammar bit if killed by stealing a cockatrice corpse from a monster +being petrified by swallowing a cockatrice violates foodless conduct +devouring Medusa whole is fatal Platform- and/or Interface-Specific Fixes diff --git a/src/mhitm.c b/src/mhitm.c index 997587e32..e70325a49 100644 --- a/src/mhitm.c +++ b/src/mhitm.c @@ -1,4 +1,4 @@ -/* SCCS Id: @(#)mhitm.c 3.5 2005/09/27 */ +/* SCCS Id: @(#)mhitm.c 3.5 2005/12/02 */ /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */ /* NetHack may be freely redistributed. See license for details. */ @@ -698,7 +698,9 @@ mdamagem(magr, mdef, mattk) res = MM_MISS; boolean cancelled; - if (touch_petrifies(pd) && !resists_ston(magr)) { + if ((touch_petrifies(pd) || /* or flesh_petrifies() */ + (mattk->adtyp == AD_DGST && pd == &mons[PM_MEDUSA])) && + !resists_ston(magr)) { long protector = attk_protection((int)mattk->aatyp), wornitems = magr->misc_worn_check; @@ -1509,4 +1511,3 @@ int aatyp; } /*mhitm.c*/ - diff --git a/src/uhitm.c b/src/uhitm.c index 5c716a19d..7767f8114 100644 --- a/src/uhitm.c +++ b/src/uhitm.c @@ -1774,9 +1774,17 @@ gulpum(mdef,mattk) register struct monst *mdef; register struct attack *mattk; { +#ifdef LINT /* static char msgbuf[BUFSZ]; */ + char msgbuf[BUFSZ]; +#else + static char msgbuf[BUFSZ]; /* for nomovemsg */ +#endif register int tmp; register int dam = d((int)mattk->damn, (int)mattk->damd); + boolean fatal_gulp; struct obj *otmp; + struct permonst *pd = mdef->data; + /* Not totally the same as for real monsters. Specifically, these * don't take multiple moves. (It's just too hard, for too little * result, to program monsters which attack from inside you, which @@ -1785,27 +1793,44 @@ register struct attack *mattk; * after exactly 1 round of attack otherwise. -KAA */ - if(mdef->data->msize >= MZ_HUGE) return 0; + if (pd->msize >= MZ_HUGE) return 0; if(u.uhunger < 1500 && !u.uswallow) { for (otmp = mdef->minvent; otmp; otmp = otmp->nobj) (void) snuff_lit(otmp); - if(!touch_petrifies(mdef->data) || Stone_resistance) { -#ifdef LINT /* static char msgbuf[BUFSZ]; */ - char msgbuf[BUFSZ]; -#else - static char msgbuf[BUFSZ]; -#endif + /* engulfing a cockatrice or digesting a Rider or Medusa */ + fatal_gulp = (touch_petrifies(pd) && !Stone_resistance) || + (mattk->adtyp == AD_DGST && (is_rider(pd) || + (pd == &mons[PM_MEDUSA]) && !Stone_resistance)); + + if ((mattk->adtyp == AD_DGST && !Slow_digestion) || fatal_gulp) { + /* KMH, conduct */ + u.uconduct.food++; + if (!vegan(pd)) + u.uconduct.unvegan++; + if (!vegetarian(pd)) + violated_vegetarian(); + } + + if (fatal_gulp && !is_rider(pd)) { /* petrification */ + char kbuf[BUFSZ]; + const char *mname = pd->mname; + + if (!type_is_pname(pd)) mname = an(mname); + You("bite into %s.", mon_nam(mdef)); + Sprintf(kbuf, "swallowing %s whole", mname); + instapetrify(kbuf); + } else { start_engulf(mdef); switch(mattk->adtyp) { case AD_DGST: /* eating a Rider or its corpse is fatal */ - if (is_rider(mdef->data)) { + if (is_rider(pd)) { pline("Unfortunately, digesting any of it is fatal."); end_engulf(); Sprintf(killer.name, "unwisely tried to eat %s", - mdef->data->mname); + pd->mname); killer.format = NO_KILLER_PREFIX; done(DIED); return 0; /* lifesaved */ @@ -1816,13 +1841,6 @@ register struct attack *mattk; break; } - /* KMH, conduct */ - u.uconduct.food++; - if (!vegan(mdef->data)) - u.uconduct.unvegan++; - if (!vegetarian(mdef->data)) - violated_vegetarian(); - /* Use up amulet of life saving */ if (!!(otmp = mlifesaver(mdef))) m_useup(mdef, otmp); @@ -1832,12 +1850,11 @@ register struct attack *mattk; You("hurriedly regurgitate the sizzling in your %s.", body_part(STOMACH)); } else { - tmp = 1 + (mdef->data->cwt >> 8); + tmp = 1 + (pd->cwt >> 8); if (corpse_chance(mdef, &youmonst, TRUE) && - !(mvitals[monsndx(mdef->data)].mvflags & - G_NOCORPSE)) { + !(mvitals[monsndx(pd)].mvflags & G_NOCORPSE)) { /* nutrition only if there can be a corpse */ - u.uhunger += (mdef->data->cnutrit+1) / 2; + u.uhunger += (pd->cnutrit + 1) / 2; } else tmp = 0; Sprintf(msgbuf, "You totally digest %s.", mon_nam(mdef)); @@ -1852,9 +1869,9 @@ register struct attack *mattk; nomul(-tmp); nomovemsg = msgbuf; } else pline("%s", msgbuf); - if (mdef->data == &mons[PM_GREEN_SLIME]) { + if (pd == &mons[PM_GREEN_SLIME]) { Sprintf(msgbuf, "%s isn't sitting well with you.", - The(mdef->data->mname)); + The(pd->mname)); if (!Unchanging) { make_slimed(5L, (char*) 0); } @@ -1867,8 +1884,7 @@ register struct attack *mattk; if (youmonst.data == &mons[PM_FOG_CLOUD]) { pline("%s is laden with your moisture.", Monnam(mdef)); - if (amphibious(mdef->data) && - !flaming(mdef->data)) { + if (amphibious(pd) && !flaming(pd)) { dam = 0; pline("%s seems unharmed.", Monnam(mdef)); } @@ -1937,12 +1953,6 @@ register struct attack *mattk; pline("Obviously, you didn't like %s taste.", s_suffix(mon_nam(mdef))); } - } else { - char kbuf[BUFSZ]; - - You("bite into %s.", mon_nam(mdef)); - Sprintf(kbuf, "swallowing %s whole", an(mdef->data->mname)); - instapetrify(kbuf); } } return(0);