Last few && or || followed by end-of-line comments, plus tab replacement
and 'return' parentheses. Not as many of those; some of these files had
already had that done.
Also, tweaked non-cursed scroll of charging read while confused to be a
tiny bit more effective.
To do: find and fix block comments that immediately follow a line with
an end-of-line comment and got misindented to line up with that comment.
Add macros W_WEAPON and W_ACCESSORY, similar to existing W_ARMOR, bitmask
of all the relevant worn bits. Just for code readability; there should
be no change in behavior.
Also, reformat the "ugly checks" portion of getobj(). Slightly better
readability and fewer continuation lines, but only a modest improvement.
Allow one item to be taken out of a pile, and leave framework in place
for partial splits so that all monsters will take up to their capacity,
rather than leaving the whole pile if it's too big to take all at once.
Most of the time, rloc() is used for teleporting monsters and it's not a
big deal if they can't find somewhere to go. In a few cases, it is. I
went through all the callsites and made calls to rloc() not cause
impossible()s if they don't need to.
Fixes a bug/suite of bugs reported by ais523.
I'll push a formatting guide at some point. There may still be
outstanding changes, but please feel free to resolve those as you arrive
a them.
To the best of my knowledge, there is no changes to the actual code
content, but the formatter does have the occasional bug. If you run into
an issue, please fix it!
When gold is stolen by a leprechaun or lost when being "overwhelmed
by an urge to take a bath" while dipping in a fountain, if you had
99 gold pieces or less, you'd lose all of it (in the bath case, only
if it was at least 10 to start with), but if you had 100 or more,
you would lose a random amount which could be as little as 1. And
in the bath case, if the random amount was less than 10, you would
lose nothing but be told that "you lost some of your money in the
fountain". After this change, it is still possible to lose less
when starting with more, but not as likely and not as extreme a case
as maybe losing only 1 when starting with thousands.
The fountain-dip bath case has code to handle mutiple denominations
of coins, possibly the only place in the program where that exists.
I've left that alone although it should probably be taken out....
Instead of just "while helpless", the death reason will tell
more explicitly why the player was helpless. For example:
"while frozen by a monster's gaze"
Move debugging output into couple preprocessor defines, which
are no-op without DEBUG. To show debugging output from a
certain source files, use sysconf:
DEBUGFILES=dungeon.c questpgr.c
Also fix couple debug lines which did not compile.
This also includes fixes due to Derek Ray to depugpline to work better
on other platforms.
The message "you stop taking off <that armor>" when interrupted by a
nymph's or monkey's theft attack would only be given if you were using 'A'
to take off the armor. If you used 'T', you'd get "you stop putting on
<that armor>" instead. The fix for that also makes it easy to vary the
nymph message "<the nymph persuades> you to start taking off" to be "<the
nymph persuades you to continue taking off" when taking that same piece
of armor off was interrupted by the theft.
From a bug report, having some
armor stolen while in the midst of putting on armor--when both items have
a multiple turn completion delay--could result in side-effects for the
latter item being reversed even though they hadn't been applied yet. So
you'd lose points of Int and Wis when attempting to put on a positively
enchanted helm of brilliance, or gain such with a negatively enchanted one.
steal() was assigning to afternmv before it had been used to finish the
action of putting on or taking off armor. Fix by interrupting the attempt
to put on or take off armor when being victimized by theft (or being hit by
succubus or incubus seduction). The existing stop_occupation() call wasn't
sufficient because afternmv is different from occupation.
From the newsgroup: after killing a vault guard on a level where
every object had been removed or was held by the hero, object detection
gave feedback about finding something but was unable to show anything.
It was finding the dead guard's inventory at <0,0>, a part of the map
which never gets shown. A dying guard is sent to that location instead
of being killed and deleted, because the data for his temporary corridor
to/from the vault is kept in the egd structure attached to him. That's
somewhat obscure but works; dying guards just need to drop inventory
before being transfered there rather than after.
Depending upon how they're killed, it's possible that the umpteen
places in the code that loop over fmon might have been processing them
as if still in play. This sets their mhp to 0 so such loops will ignore
them, and teaches dmonsfree() not to release them. Once the temporary
corridor has been removed, their isgd flag is cleared and they become
ordinary dead monsters and get deleted from the fmon list the next time
it's purged.
This also lets you throw gold to/at the guard when he tells you to
drop it. He already would catch it, but now he won't treat the throw as
an attack. Any gold he carries will eventually disappear when he does,
so dropping it remains a better option for the player.
From a bug report, you could obtain
a saddle for free if it was dropped (while worn) by a dying pet inside a
shop. That's intentional, but it was happening even when the hero was
not in the shop, which doesn't seem right. Change things to only set it
no_charge if hero is within the same shop (including standing in the
doorway or a temporary wall breach, not just when all the way inside) at
the time of the drop.
Suggested by <email deleted> a month ago when he
reported that attempting to unlock a door which was actually a mimic
simply told the player that the door was not locked or that there was
no door. He thought that mimic should take the key/pick/card away from
the hero. This gives a 50% chance for the unlocking tool to be stolen
and become part of the mimic's inventory; it will be dropped when mimic
is killed.
The theft routine has groundwork to be able to be used to take the
hero's wielded or thrown weapon when hitting, but the attack code doesn't
call it so that won't happen (and the theft code hasn't been tested under
that circumstance). I'm not sure whether mimics should be able to grab
weapons, but g.cubes perhaps should, and if puddings could then "pudding
farming" [using a low damage iron weapon to split puddings, yielding tons
of experience, death drops, and #offer fodder when they're killed and
repeatable for as long as at least one pudding is kept healthy enough to
be split again] would become tougher to accomplish. [The item drop and
corpse aspects have been toned down quite a bit since 3.4.3, but with
sufficient patience it is still possible to abuse.]
Noticed while looking through steal.c: theft that takes multiple
turns uses stealarm() callback which removes stolen armor from hero's
shopping bill, but theft that happened without delay did not. So theft
of an unpaid non-armor or non-worn item while in a shop left it on the
bill where it wouldn't show up for either ``I u'' or ``I x'', hiding the
charge from the player ('$' did disclose the total amount that the shk
was owed though), and the shopkeeper would persist in blocking the door.
This makes immediate theft behave the same as delayed theft; the stolen
item is removed from shop's bill when the thieving monster takes it away
from the hero.
Dropped items that a shopkeeper doesn't want have their no_charge
bit set; that's only supposed to be used for floor items inside shops.
But no_charge would stick when an object was picked up by a monster, so
the object would stay free for player if that monster was subsequently
killed in another shop which stocked that kind of item. Probably never
noticed because most monsters won't pick up items off of shop floors,
also most levels don't have other shops dealing with alternate types of
stuff. This clears no_charge, except when the monster picking up the
item is tame (so that a pet picking up and then dropping a no_change
object in the same shop won't cause the shk to silently take possession,
which would certainly lead to reports of a bug...).
Mentioned by <email deleted> in his report about
sound anomalies, it was possible for a sleeping hero to "gladly start
removing armor" when attacked by a nymph or succubus. The code
explicitly wakes up the hero if he has fainted from lack of food because
"can't charm without waking you" (according to the existing comment),
but it didn't handle other forms of sleep and paralysis. You could get
|You fall asleep.
|The wood nymph charms you. You gladly start removing your armor.
|The combat awakens you.
Now in the same situation you'll get
|You fall asleep.
|You wake up.
|The wood nymph charms you. You gladly start removing your armor.
For GOLDOBJ configuration, relax the 52 object limit for inventory
when gold uses the special $ slot instead of a letter. Takes care of an
old buglist entry from the beta testers. [It will need to be revisited
if we ever implement multiple coin types that can't all fit in one slot.]
Also for GOLDOBJ, prevents nymphs and monkeys from stealing coins,
since allowing that made their steal-item attack be a complete superset
of leprechaun's steal-gold attack.
From a bug report: nymphs could steal
boulders even though they aren't allowed to pick those up. It happened
becuase can_carry() is only called for monkeys (consequently, they don't
have this problem), not for nymphs.
Noticed while looking at something else: zapping a wand of opening
or spell of knock downwards while riding causes your steed's saddle to
fall off, which in turn causes the hero to fall and take some damage.
If that damage was fatal, the saddle would be left worn in bones data.
This reorganizes mdrop_obj() to defer until last the part that ultimately
makes the hero fall off, and changes bhitm() to call that instead of
handling saddle removal inline, also gives new saddle-off feedback there.
The latest Micrsoft compilers complain when a function is
assigned to a function pointer, and the function's argument
list does not match the prototype precisely.
It was evem complaining about the difference between this:
int x()
{
[...]
}
and a prototype of
int x(void);
when assigning that function's address to a function pointer.
This quiets those warnings, without suppressing the mismatch
check altogether for more serious mismatches.
From a bug report, "The leprechuan quickly snatches some
gold from between your feet!" doesn't make much sense when you're riding.
Fix started out simple, but "between" isn't right if you're above the floor,
and "rear hooves" for horse or "rear claws" for dragon didn't sound right
for steed (or poly'd hero), so it got a little more complex. Complicated
even more due to requiring two copies; ick.
A minor side-effect of this change is that somewhat naughty sounding
"The leprechaun quickly snatches some gold from between your rear regions!"
won't occur anymore. :-}
Let monsters use lock picks and credit cards in addition to keys for
opening doors. And the earlier code to have pets hang on to a key didn't
work as intended. It worked fine if the key was the only object carried,
but the monsters' item dropping code didn't give any special handling to
keys so they'd be dropped too if the pet carried another droppable item.
This eliminates second set of checks for handling some items specially--
dropping now uses the same routine as is used when pet movement decides
whether there's anything to drop.
Also, a couple more door message tweaks. "You see a door open" seems
strange when you watch your pet do the opening. Previously fixed for the
"unlock and open" case, this does the same for opening already unlocked
doors and for giants smashing down doors--it now gives a more specific
message when you see a monster perform the action.
Possible change in play balance: pets capable of picking up the
rogue's Master Key of Thievery or tourist's Platinum Yendorian Express
Card will keep one of them. So a player might accidentally lose one by
leaving it on the floor in a pet's path, or more significantly, the Card
will yield a means of giving magic resistance to a monster who can't wear
a cloak or dragon scales. It's neutral and the most interesting high-end
pets are lawful (hence won't pick it up), so that probably won't have much
impact.
When lit due to being wielded by a monster, Sunsword continued to emit
light after that monster was killed. This was fixed by <Someone> in 3.4.1 but a
change I made for 3.4.3 broke that fix. When mdrop_obj() was split out of
relobj(), relevant unwielding code ended up only being executed for monsters
who were still alive.
Finally apply the patch sent by <Someone> in 11/2003 for slashem-Bugs-799278,
updated to match the current code and handle additional cases. The fix
is brute force: always ensure nomovemsg is set when nomul is called with
a negative value. I also scanned the code for places manually setting
multi negative, they all set nomovemsg. It would be nice to have a function
that did the right thing, but there are several special cases and I was
not feeling creative.
Neither nymphs nor monkeys can steal a ring worn underneath gloves
since they can't see them. If such rings are randomly targetted, try to
take gloves instead.
Succubi trying to take worn ring of adornment will attempt to take
off worn gloves first. (Presumeably they can sense magic rings hidden
beneath gloves better than nymphs can; they're about to try to take all
worn armor off anyway....) If the glove removal fails, ring theft will
too. Likewise for incubi, remove gloves before trying to force the hero
to put on ring of adornment.
At the moment succubi and incubi can't remove gloves which are
blocked by a welded weapon, but they can manipulate rings then if there
aren't any gloves involved. I don't think that's right. The latter is
nymph-like and could be attributed to magic, but if that's the case why
aren't they able to remove gloves from under cursed weapons too?
Prevent monkeys from stealing any ring which the hero can't remove due
to it being stuck inside the grip of a cursed weapon. Nymphs can still do
so though. From a bug report.
Something from <Someone>'s list: some messages have hardcoded references
to "helmet" which sound strange when the character is wearing a hat or cap.
helm_simple_name() is comparable to the existing cloak_simple_name(). It
returns "helm" or "hat" depending upon whether the helmet provides the
same protection that yields the assorted repetitions of "fortunately,
you are wearing a hard helmet". This choice ends up categorizing elven
leather helm as a hat (which I think is ok given that its undiscovered
description is "leather hat"), contrary to <Someone>'s suggestion that the
distinction be made based on whether the helmet was made of cloth.
I started on this a year and a half ago but didn't commit it.
Unfortunately I don't remember why and haven't done any significant
additional work now--just recovered from some intervening bit rot and
confirmed that the patch as is seems to be working ok (in the trunk; the
branch side has not been tested). I suspect that I meant to look for
additional helmet messages which could benefit from conditional headgear
description. (Those "hard helmet" ones don't need it, although they
should perhaps be moved into a common routine instead of being replicated.)
It was possible to get a shopkeeper to carry the Amulet from the
bottom of the dungeon up to the location of his shop, thereby bypassing
the usual labor of lugging it up yourself. [Drop the Amulet somewhere;
rob a shop so that the Kops are summoned and the shk comes after you;
when shk is next you, level teleport to the Amulet (probably two hops,
one to the Valley and another deeper into Gehennom); walk to the vicinity
of the Amulet; shk will eventually pick it up (shopkeepers like to pick
up magic items); now, pay him for the stolen goods--he'll be pacified
and migrate back to his shop, taking his inventory with him; lastly,
return to his shop and relieve him of his burder.] This patch makes
shopkeepers drop the Amulet or invocation tools if/when they set set to
migrate to their normal location.
Also fix another long standing risk that a monster that is sent
away (nurse when healing, Kops when you pacify a shopkeeper) might be
carrying the Amulet or one of the invocation tools and make the game
unwinnable. I doubt that that's ever actually happened but I think it'd
be possible if a monster that likes magic items ever got polymorphed
into a Kop. Such dismissed monsters will now drop the same stuff as
the shk above prior to leaving the game.
[ Caveat: compiles ok on branch code but only play tested on trunk code;
the do_wear.c diff is a lot different between the two variants and the
trunk one includes some whitespace cleanup. ]
<email deleted> reported that having a spellcasting monster
destroy some armor while you're in the midst of using 'A' to take that
armor off would result in a crash. The problem was actually more
widespread than that: having a nymph steal worn items (accessories as
well as armor), or a succubus remove them, or being interrupted by monster
activity and then reading a scroll of destroy armor prior to resuming 'A'
could all produce a similar crash. 'A' relied on stale context and could
attempt to manipulate an equipment slot which had become empty, ultimately
leading to an attempt to dereference a null pointer.
The 'R' command didn't have this problem since any accessory gets
removed immediately. The 'T' command already had handling for this:
there's only one item to deal with and multi-turn take off only applies
to some of the slots; the donning() check followed by cancel_don() took
care of those. Only 'A' was vulnerable to the problem and it wouldn't
necessarily need to be interrupted and resumed; loss of the current
multi-turn item or any pending item would be enough--but I'm not sure
whether such item loss could occur without also interrupting the current
activity, so resumption of previous 'A' was probably a requirement for
triggering the crash.
This makes shield and shirt handling be similar to other types of
armor instead of relying on the fact that none of them need to have any
attribute adjustments when put on or taken off. However, there are
still assumptions (the `cancelled_don' stuff) that some slots don't have
any eligible items requiring more than a single turn to use; that should
probably be changed.
Pat Rankin wrote:
> collect them all into some new struct and
> save that separately rather than jamming more non-option stuff
> into struct flags.
This patch:
- collects all context/tracking related fields from flags
into a new structure called "context."
It also adds the following to the new structure:
- stethoscope turn support
- victual support
- tin support
This patch introduces a change to yname() and Yname2() that avoids the
possessive "your" for the hero's normal, fully identified artifacts.
Quest artifacts still get the possessive, as do all other objects and all
objects not in the hero's possession. shk_your()/Shk_Your() are used in
many places with a specific, generalized name for the object, so I didn't
introduce the artifact behavior there, although I did change them to append
a space, which simplified some other code. Through added use of yname(),
there may be some places that used to just say "corpse" that will now be more
descriptive via yname()'s use of cxname(). I'm sure <Someone> will point
out any such places that are too onerous, although nothing obviously is.
I took the opportunity to inspect many uses of "your" and even Your(). Two
new functions are also introduced, yobjnam() and Yobjnam2(), which work
like aobjnam() and yname() combined, because I found that many uses of
aobjnam() were preceeded by "your" and I couldn't generally provide the
desired behavior for artifacts (or future artifacts) without a combined
function. In some cases, this change allowed better sharing of code.
rust_dmg() still takes a string as input which is sometimes initialized
from xname() and often prepends "your" to it. Currently, this isn't a
problem since there currently are no normal, armor artifacts. If/when any
are introduced, rust_dmg() will need to be addressed.
The patch is for the trunk only. A lot of research was required and I
didn't feel the upside was there for repeating it in the 3.4.3 branch.
<email deleted> wrote:
> If more monsters fall through a trap door than can fit on the
> level below, when you go down the stairs, you get the following
> message:
> "Program in disorder - perhaps you'd better #quit.
> rloc(): couldn't relocate monster"
> This message seems to appear once for every monster-too-many that
> fell through the hole. I originally found this while
> intentionally completely filling a level with black puddings
> (there was a trap door I didn't know about). I also confirmed it
> in a wiz-mode test using gremlins and water.
[confirmed: moveloop -> deferred_goto -> goto_level ->
losedogs -> mon_arrive -> rloc -> impossible]
This patch:
- causes rloc() to return TRUE if successful,
or FALSE if it wasn't.
- adds code to mon_arrive() in dog.c to deal with
the failed rloc()
- allows the x,y parameters to mkcorpstat() to
be 0,0 in order to trigger random placement of the
corpse on the level
- if you define DEBUG_MIGRATING_MONS when you build cmd.c
then you'll have a debug-mode command #migratemons to
store the number of random monsters that you specify
on the migrating monsters chain.
<Someone> reported the messages "It seduces you and you take off your
robe. She stole a burnt +0 robe." I noticed the 2 cases here only dealt
with blindness, not seeing the nymph in general. Also, one case forced
"She", the other "It". Now they both say "She", which is consistent with
the preposition in the 2nd message. We'll continue to the assume the
gender of the seducer is obvious, even when unseen.
Provide more control over message handling for monsters' use
of equipment. This fixes the statue revival problem (inappropriate
feedback when monster puts on speed boots) mentioned in the earlier
"intrinsics of dead monsters" patch.
Monster traits that are used to revive some corpses or statues
with their old attributes were retaining intrinsics conferred by worn
items. To prevent that, strip such attributes at time of a monster's
death before the traits are recorded. Statue handling needs to some
more work; now that extra speed is lost, there's an out of place
message if/when a revived statue gets to put on its old speed boots.
<Someone> wrote:
> Linux, Redhat 7.1 nethack 3.4.0
>
>Please see attached patch file.
>
>I'm attempting to move more stuff into the "read-only" area, in
>preparation for a port to another OS.