diff --git a/doc/fixes35.0 b/doc/fixes35.0 index 776ec1947..1f93ea782 100644 --- a/doc/fixes35.0 +++ b/doc/fixes35.0 @@ -343,6 +343,8 @@ when reading an unknown scroll and learning it, discovery of teleporation was using an unlocking tool on a closed door which was actually a mimic reported that there was no door to unlock instead of exposing the mimic purple worm could end up in wall or solid rock when swallowing ghost or xorn +enhance life-saving by preventing subsequent poison from being fatal upon + rescue from death due to spiked pit, dart trap, or poisoned missile Platform- and/or Interface-Specific Fixes diff --git a/src/attrib.c b/src/attrib.c index b39e2b3f5..e43ea5103 100644 --- a/src/attrib.c +++ b/src/attrib.c @@ -1,5 +1,4 @@ /* NetHack 3.5 attrib.c $Date$ $Revision$ */ -/* SCCS Id: @(#)attrib.c 3.5 2008/02/02 */ /* Copyright 1988, 1989, 1990, 1992, M. Stephenson */ /* NetHack may be freely redistributed. See license for details. */ @@ -225,10 +224,10 @@ void poisoned(reason, typ, pkiller, fatal, thrown_weapon) const char *reason, /* controls what messages we display */ *pkiller; /* for score+log file if fatal */ -int typ, fatal; +int typ, fatal; /* if fatal is 0, limit damage to adjattrib */ boolean thrown_weapon; /* thrown weapons are less deadly */ { - int i, kprefix = KILLED_BY_AN; + int i, loss, kprefix = KILLED_BY_AN; /* inform player about being poisoned unless that's already been done; "blast" has given a "blast of poison gas" message; "poison arrow", @@ -259,17 +258,22 @@ boolean thrown_weapon; /* thrown weapons are less deadly */ kprefix = KILLED_BY; } - i = rn2(fatal + (thrown_weapon ? 20 : 0)); + i = !fatal ? 1 : rn2(fatal + (thrown_weapon ? 20 : 0)); if (i == 0 && typ != A_CHA) { + /* instant kill */ u.uhp = -1; pline_The("poison was deadly..."); - } else if (i <= 5) { - /* check that a stat change was made */ - if (adjattrib(typ, thrown_weapon ? -1 : -rn1(3,3), 1)) - poisontell(typ, TRUE); + } else if (i > 5) { + /* HP damage; more likely--but less severe--with missiles */ + loss = thrown_weapon ? rnd(6) : rn1(10,6); + losehp(loss, pkiller, kprefix); /* poison damage */ } else { - i = thrown_weapon ? rnd(6) : rn1(10,6); - losehp(i, pkiller, kprefix); /* poison damage */ + /* attribute loss; if typ is A_STR, reduction in current and + maximum HP will occur once strength has dropped down to 3 */ + loss = (thrown_weapon || !fatal) ? 1 : d(2, 2); /* was rn1(3,3) */ + /* check that a stat change was made */ + if (adjattrib(typ, -loss, 1)) + poisontell(typ, TRUE); } if (u.uhp < 1) { diff --git a/src/mthrowu.c b/src/mthrowu.c index 193582639..8ae801ca1 100644 --- a/src/mthrowu.c +++ b/src/mthrowu.c @@ -1,5 +1,4 @@ /* NetHack 3.5 mthrowu.c $Date$ $Revision$ */ -/* SCCS Id: @(#)mthrowu.c 3.5 2009/02/17 */ /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */ /* NetHack may be freely redistributed. See license for details. */ @@ -245,7 +244,7 @@ struct obj *obj; /* missile (or stack providing it) */ struct monst *mtmp; struct obj *singleobj; char sym = obj->oclass; - int hitu, blindinc = 0; + int hitu, oldumort, blindinc = 0; bhitpos.x = x; bhitpos.y = y; @@ -346,6 +345,7 @@ struct obj *obj; /* missile (or stack providing it) */ potionhit(&youmonst, singleobj, FALSE); break; } + oldumort = u.umortality; switch(singleobj->otyp) { int dam, hitv; case EGG: @@ -383,7 +383,10 @@ struct obj *obj; /* missile (or stack providing it) */ Strcpy(onmbuf, xname(singleobj)); Strcpy(knmbuf, killer_xname(singleobj)); - poisoned(onmbuf, A_STR, knmbuf, 10, TRUE); + poisoned(onmbuf, A_STR, knmbuf, + /* if damage triggered life-saving, + poison is limited to attrib loss */ + (u.umortality > oldumort) ? 0 : 10, TRUE); } if(hitu && can_blnd((struct monst*)0, &youmonst, diff --git a/src/trap.c b/src/trap.c index 7f25e967d..51cf074d7 100644 --- a/src/trap.c +++ b/src/trap.c @@ -686,6 +686,7 @@ unsigned trflags; forcebungle = (trflags & FORCEBUNGLE) != 0, plunged = (trflags & TOOKPLUNGE) != 0, adj_pit = conjoined_pits(trap, t_at(u.ux0,u.uy0), TRUE); + int oldumort; #ifdef STEED int steed_article = ARTICLE_THE; #endif @@ -779,13 +780,17 @@ unsigned trflags; otmp->quan = 1L; otmp->owt = weight(otmp); if (!rn2(6)) otmp->opoisoned = 1; + oldumort = u.umortality; #ifdef STEED if (u.usteed && !rn2(2) && steedintrap(trap, otmp)) /* nothing */; else #endif if (thitu(7, dmgval(otmp, &youmonst), otmp, "little dart")) { if (otmp->opoisoned) - poisoned("dart", A_CON, "little dart", 10, TRUE); + poisoned("dart", A_CON, "little dart", + /* if damage triggered life-saving, + poison is limited to attrib loss */ + (u.umortality > oldumort) ? 0 : 10, TRUE); obfree(otmp, (struct obj *)0); } else { place_object(otmp, u.ux, u.uy); @@ -1041,6 +1046,7 @@ glovecheck: (void) rust_dmg(uarmg, "gauntlets", 1, TRUE, &youmonst); if (!steedintrap(trap, (struct obj *)0)) { #endif if (ttype == SPIKED_PIT) { + oldumort = u.umortality; losehp(Maybe_Half_Phys(rnd(adj_pit ? 6 : 10)), plunged ? "deliberately plunged into a pit of iron spikes" : adj_pit ? "stepped into a pit of iron spikes" : @@ -1048,9 +1054,11 @@ glovecheck: (void) rust_dmg(uarmg, "gauntlets", 1, TRUE, &youmonst); NO_KILLER_PREFIX); if (!rn2(6)) poisoned("spikes", A_STR, - adj_pit ? "stepping on poison spikes" : - "fall onto poison spikes", - 8, FALSE); + adj_pit ? "stepping on poison spikes" : + "fall onto poison spikes", + /* if damage triggered life-saving, + poison is limited to attrib loss */ + (u.umortality > oldumort) ? 0 : 8, FALSE); } else { if (!adj_pit) losehp(Maybe_Half_Phys(rnd(6)),