Commit Graph

336 Commits

Author SHA1 Message Date
nhmall
0792e5fe9e expand implicit fallthrough detection to non-gcc compilers
gcc has recognized various "magic comments" for white-listing
occurrences of implicit fallthrough in switch statements for
a long time:

    The range and shape of "falls through" comments accepted are
    contingent upon the level of the warning. (The default level is =3.)

    -Wimplicit-fallthrough=0 disables the warning altogether.
    -Wimplicit-fallthrough=1 treats any kind of comment as a "falls through" comment.
    -Wimplicit-fallthrough=2 essentially accepts any comment that contains something
     that matches (case insensitively) "falls?[ \t-]*thr(ough|u)" regular expression.
    -Wimplicit-fallthrough=3 case sensitively matches a wide range of regular
     expressions, listed in the GCC manual. E.g., all of these are accepted:
        /* Falls through. */
        /* fall-thru */
        /* Else falls through. */
        /* FALLTHRU */
        /* ... falls through ... */
       etc.
    -Wimplicit-fallthrough=4 also, case sensitively matches a range of regular
     expressions but is much more strict than level =3.
    -Wimplicit-fallthrough=5 doesn't recognize any comments.

Plenty of other compilers did not recognize the gcc comment convention,
and up until now the compiler warning for detecting unintended
fallthrough had to be suppressed on other compilers. That's because the code
in NetHack has been relying on the gcc approach, and only the gcc approach.

The C23 standard introduces an attribute [[fallthrough]] for the
functionality, when implicit fallthrough warnings have been enabled.

Several popular compilers already support that, or a very similar attribute
style approach, today, even ahead of their C23 support:

       C compiler                       whitelist approach
       ---------------------------   -------------------------------------
       C23 conforming compilers         [[fallthrough]]

       clang versions supporting
       standards prior to
       C23                              __attribute__((__fallthrough__))

       Microsoft Visual Studio
       since VS 2022 17.4.
       The warning C5262 controls
       whether the implict
       fallthrough is detected and
       warned about with
       /std:clatest.                    [[fallthrough]]

This adds support to NetHack for the attribute approach by inserting a
macro FALLTHROUGH to the existing cases that require white-listing, so
other compilers can analyze things too.

The definition of the FALLTHROUGH macro is controlled in include/tradstdc.h.

The gcc comment approach has also been left in place at this time.
2024-11-30 14:16:27 -05:00
PatR
1c888b3b07 noit_mon_nam()
Change noit_mon_nam() to work as if it was noit_y_monnam() (without
renaming it or adding yet another monster naming routine) to use
"your <mon>" rather than "the <mon>" when <mon> is a pet that can
be seen (so not the case where "it" gets replaced by "someone" or
"something").
2024-11-26 21:51:00 -08:00
PatR
5adabc07a3 missing comment: YMonnam() variant of x_monnam()
YMonnam() was added three weeks ago but the comment preceding
x_monnam() didn't get updated to list it.
2024-07-26 14:53:33 -07:00
nhmall
0eb7f109e0 follow-up, program_state 2024-07-13 16:31:35 -04:00
PatR
72d2b0414c fix github issue #1257 - nymph theft while blind
Issue reported by Meklon2007:  some theft feedback during nymph
attacks refers to the attacker as "she" and others as "it" if hero
is blind.

The "she" references are intentional.  However, mixing them with
"it" references when a series of messages occurs is jarring.  This
changes "it" to "someone", which is still different from "she" but
hopefully enough less so to be tolerable.

That resulted in monkeys also being referred to as "someone" because
they're classified as humanoid.  Change x_monnam()'s AUGMENT_IT
handling, which chooses between "someone" and "something" when the
monster is not seen, to override humanoid for animals (affects 'Y'
class) and for mindless (affects zombies, mummies, and golems).
So an unseen monkey will be "it" again.

The final message for current item was relying on a cached monster
name value.  If an unseen nymph or monkey stole a worn blindfold
so that hero's vision was restored:  "It <stole> item" before the
changes and "Someone|Something <stole> item" after.  So update the
cached name if sight gets regained, to give "<Mon> stole <item>."
(If the item is worn armor and the thief is a nymph, it was and
still is "She stole <item>".)

The message for having any worn item be stolen, which got split
into two parts within the past year, was giving "<Mon> takes off
<alt weapon>".  When not dual-wielded, the alternate weapon isn't
really worn.  Rather than suppress it outright, change the message
for uwep/uswapwep/uquiver to say "disarms" instead of "takes off".
For accessories, change "takes off" to "removes".  Those are more
or less interchangeable these days but "removes" matches R instead
of T.

While testing, my pet evidently killed a nymph (I was blinded and
couldn't see it happen) while she stole my gloves and the next
message I got was "You finish taking off your suit."  The gloves
weren't worn anymore so equipname() defaulted to suit.  Get rid of
equipname() altogether and switch to armor_simple_name() which
doesn't rely on the worn-armor pointers.

Fixes #1257
2024-07-13 12:30:59 -07:00
nhmall
6c0ae092c6 distinguish global variables that get written to savefile
The g? structs had a mix of variables that were written to
the savefile, and those that were not.

For better clarity and to distinguish those that end up in
the savefile, relocate some g? variables that get written
directly to the savefile into different structs.

This updates EDITLEVEL, although technically it probably
didn't need to, since savefile contents are not changing.

Details:

    gb.bases            -> svb.bases
    gb.bbubbles         -> svb.bbubbles
    gb.branches         -> svb.branches
    gc.context          -> svc.context
    gd.disco            -> svd.disco
    gd.dndest           -> svd.dndest
    gd.doors            -> svd.doors
    gd.doors_alloc      -> svd.doors_alloc
    gd.dungeon_topology -> svd.dungeon_topology
    gd.dungeons         -> svd.dungeons
    ge.exclusion_zones  -> sve.exclusion_zones
    gh.hackpid          -> svh.hackpid
    gi.inv_pos          -> svi.inv_pos
    gk.killer           -> svk.killer
    gl.lastseentyp      -> svl.lastseentyp
    gl.level            -> svl.level
    gl.level_info       -> svl.level_info
    gm.mapseenchn       -> svm.mapseenchn
    gm.moves            -> svm.moves
    gm.mvitals          -> svm.mvitals
    gn.n_dgns           -> svn.n_dgns
    gn.n_regions        -> svn.n_regions
    gn.nroom            -> svn.nroom
    go.oracle_cnt       -> svo.oracle_cnt
    gp.pl_character     -> svp.pl_character
    gp.pl_fruit         -> svp.pl_fruit
    gp.plname           -> svp.plname
    gp.program_state    -> svp.program_state
    gq.quest_status     -> svq.quest_status
    gr.rooms            -> svr.rooms
    gs.sp_levchn        -> svs.sp_levchn
    gs.spl_book         -> svs.spl_book
    gt.timer_id         -> svt.timer_id
    gt.tune             -> svt.tune
    gu.updest           -> svu.updest
    gx.xmax             -> svx.xmax
    gx.xmin             -> svx.xmin
    gy.ymax             -> svy.ymax
    gy.ymin             -> svy.ymin

Related note:
There are some pointer variables that are heads of chains that were not
moved from 'g?' to 'sv?', because they are not actually written to the
savefile directly, but the objects/monst/trap/lightsource/timer in the
chains they point to are. That can be changed, if desired.
Examples: gi.invent, gm.migrating_objs, gb.billobjs, gm.migrating_mons,
          gf.ftrap, gl.light_base, gt.timer_base
2024-07-13 14:57:50 -04:00
PatR
a33f1edd24 YMonnam(monst)
Replace several upstart(y_monnam(mon)) with new YMonnam(mon) to
produce "Your little dog" and such.

Also change one or two Monnam(mon) to YMonnam(mon) and one pline(...)
to pline_mon(mon, ...).
2024-07-04 14:27:28 -07:00
PatR
aaea81c6ac fix analyzer complaint
about testing whether an unsigned value is >= 0.  Since there's no
chance that it might have a value of NON_PM (-1), just comment out
the assertion that was intended to ward off a potential complaint
about that.
2024-04-18 23:14:35 -07:00
PatR
ea8ebea2d3 simplify a couple of monster naming bits 2024-04-18 12:34:03 -07:00
PatR
064523e162 mon name of monster appearing as another monster
When a monster mimicks another monster (traditionally Double Trouble
Wizard, since 3.6.x also pet that eats a mimic corpse), using farlook
or getpos+autodescribe revealed the monster's real identity.  Hard to
believe that nobody ever noticed, but it was obvious when a pet dog
quick-mimicked a cat or vice versa.

Add an extra x_monnam() flag to ignore monst->m_ap_type==M_AP_MONSTER
plus monst->mappearance.  Only the m_monnam() variation of x_monnam()
includes it (via EXACT_NAME); monnam() and the rest will now describe
an M_AP_MONSTER by its appearance rather than as its true self.
2024-04-17 14:40:20 -07:00
nhkeni
54c3dd35ac Merge branch 'keni-staticfn' into NetHack-3.7 2024-03-16 09:38:21 -04:00
nhmall
79648c6ce2 some variables not referenced in another translation unit made static
Also adds some cross-refence comments for some variables that are
referenced in another translation unit.
2024-03-15 16:00:14 -04:00
nhkeni
9c0ed8ae63 NOSTATICFN for src/* 2024-03-14 17:41:51 -04:00
nhmall
50811037f3 split some code into separate files
new .h files: hacklib.h selvar.h stairs.h

new .c files: calendar.c, getpos.c, report.c, selvar.c, stairs.c,
              strutil.c, wizcmds.c

cleanup of hacklib.c and mdlib.c

hacklib contains functions that do not have to link with the core

relocate wiz commands from cmd.c to wizcmds.c

relocate CRASHREPORT stuff to report.c

relocate getpos stuff from do_name.c to getpos.c

remove temporary struct definition from extern.h

cross-compile PRE-section split into cross-pre1.370 and cross-pre2.370

Windows sys/windows/Makefile.nmake and sys/windows/Makefile.mingw32 and
visual studio project file updates

Unix sys/unix/Makefile.src, sys/unix/Makefile.utl

populate selvar.c and selvar.h

build on MS-DOS (not cross-compile) Makefile updates
for sys/msdos/Makefile.GCC (untested)

vms updates for above (untested)
2024-03-07 11:01:04 -05:00
RainRat
a3658f85ac fix typos 2024-02-28 20:15:56 -08:00
Pasi Kallinen
25fa293c81 Accessibility: lookaround command, mention_map option
Adds a new extended command #lookaround, which will describe
the map around the hero they can see or remember.

Adds a new boolean option mention_map, which will give a message
when an interesting map location in sight changes.
2024-02-28 20:53:52 +02:00
PatR
5acb82640d update a getpos() comment
Not a typo this time; the highlight-valid-position callback interface
was simplified.
2024-02-25 12:36:19 -08:00
PatR
cba7e6eb43 umpteenth comment typo fix
plus bonus fix:  change a recent fixes entry to past tense.
2024-02-22 11:01:53 -08:00
nhmall
688ac6ffbe remove register from variable declarations 2024-02-19 16:30:07 -05:00
PatR
d253e947da more getpos() highlighting plus jumping in place
Simplify the valid-position highlighting via '$' by combining the
tmp_at(start) and tmp_at(populate) steps.

Add highlighting for a couple of targetting operations that would
give valid/invalid feedback via autodescribe but weren't displaying
highlight markers for $.

I made several jumping changes, most of them dealing with picking
hero's own spot.
2024-02-16 15:36:17 -08:00
PatR
1d5f45aa78 getpos() highlighting of valid positions
Redo getpos() highlighting.  If bgcolors is Off, '$' toggles between
no highlighting and showing dollar signs at valid spots.  ^R removes
those if they're present.  When bgcolors is On, '$' cycles among
three settings:  highlighting via background color, no highlighting,
and highlighting by drawing dollar sign characters.  ^R switches to
background color mode.

This doesn't directly solve the problem of background color causing
conflict with the foreground color of some objects or monsters, but
being able to get rid of the background with a keystroke should be an
improvement.

'bgcolors' defaults to On, which was a problem for tty when 'color'
was Off.  Turn it Off (in the core) for text map if color is Off and
bgcolors hasn't been explicitly set.  Conversely, Qt was leaving
color Off and then using color with abandon.  Turn in On (in the core)
for tiled map if it hasn't been given an explicit value.  Those two
changes should cope with most situations and still let the player
override.
2024-02-16 14:56:20 -08:00
Pasi Kallinen
baeb1d925f Change some ints to coordxy 2024-01-22 17:02:40 +02:00
Pasi Kallinen
57747535af Add m_next2u, analogous to m_next2m and next2u 2024-01-19 21:53:25 +02:00
nhmall
25a8c258e6 replace x >= LOW_PM with ismnum(x) shorthand macro 2024-01-11 14:01:10 -05:00
nhmall
80afc96def comment follow-up 2023-12-27 10:44:50 -05:00
nhmall
6d8c37b754 static analyzer bit for do_name.c
src/do_name.c(1494): warning C28183: 'aname' could be '0'
2023-12-27 10:40:02 -05:00
PatR
97272d3627 fix unnaming types of objects
docall() would access freed memory if the player used space(s) as
a fake object type name in order to remove an existing name without
giving any new one.

3.4.3 had this bug too; I didn't go farther back.
2023-12-27 04:59:44 -08:00
nhmall
e9e05db113 add a pair of shorthand macros to validate an index into an array
Two variations:

IndexOk(idx, array)       validate that idx is a valid index into the array

IndexOkT(idx, array)      validate that idx is a valid index into the
                          array, excluding the final Terminator element
2023-12-23 13:46:54 -05:00
nhmall
c5a5b55c15 nonnull for some static functions during recent analysis 2023-12-16 10:51:59 -05:00
Pasi Kallinen
5dc94f3d83 Macro for picking random entry from array 2023-12-05 10:06:27 +02:00
Pasi Kallinen
dd5ca5b058 Change menu_headings to accept color and attribute
Instead of just accepting an attribute, it's now possible to
use a color, or both color and attribute, for example:

OPTIONS=menu_headings:inverse
OPTIONS=menu_headings:red
OPTIONS=menu_headings:red&underline

Default is still just inverse.
This lets the player change the menu heading color without
needing to use menu colors for them.

Also makes it so the core uses NO_COLOR instead of 0, for all
the menu lines which don't have any prefedefined color.

Tested for tty, curses, x11, qt, and win32
2023-11-13 07:33:56 +02:00
nhmall
ee0247ac5f follow-up u.uswallow 2023-11-10 19:01:16 -05:00
nhmall
088c15b3cd improve x_monnam results when swallowed
This addresses one of the scenarios that had previously been discussed
in the comments under pull request #979.
2023-11-10 17:01:46 -05:00
nhmall
f360cb24b1 allow monster that has swallowed hero to be named 2023-11-10 16:35:43 -05:00
nhmall
6cbefc7c2d Revert "granular verbose message suppression mechanics"
This reverts commit be76727265.
2023-10-29 20:39:07 -04:00
PatR
284452796c redo tty resizing
Rest of 'not PR #1102'.  Resizing the terminal while getpos was in
operation recalculated the map from scratch instead of redrawing what
the core considers to already be shown.  And it was always operating
while an asynchronous signal was excuting which could potentially
clobber whatever was running at the time the signal arrived.

This uses same redrawing as the prior '^R during getpos()' fix.  It
also only performs the resize while tty_nhgetch() is waiting for
input.  If that is the situation at the time that the signal arrives
then it will resize immediately (while in the asynchronous signal
handler); if not, it will set a flag and tty_nhgetch() will do the
resize the next time it gets called.

This builds with TTY_PERM_INVENT enabled and doesn't seem to be any
worse than before, but there are bugs with that.  The only way I could
get perminv to appear was to save and restore, then perm_invent was
honored for both RC file and mO command.  And once I managed to get it
to display, moving an item from a lower case slot to slot 'A', made
that item vanish; nothing appeared in the invent's right hand panel.

Both of those misbehaviors already happen prior to this commit.  I
also saw an abort+panictrace if I resized while at the "Dump core?"
prompt when running the pre-commit code and didn't see that with the
post-commit code (although the prompt wasn't shown so I couldn't tell
that it was waiting for an answer).  The abort probably sounds scarier
than it warrants; I suspect that the pre-commit code just treated the
resize as answering 'y' for some reason, possibly a stale value in the
variable it uses.
2023-10-12 18:45:14 -07:00
PatR
f70f84aee7 not PR #1102 - map refresh during #terrain
This fixes the part of pull request #1102 by entrez dealing with the
map refresh side of things.  It was pulled out of a much larger patch
that also deals with terminal window resize for tty.

Using ^R when getpos() is in operation, whether actually picking a
position for something or browsing the map during #terrain or post
detection magic, it was reconstructing the known map and positioning
the cursor on the hero instead redrawing the selected terrain subset
or detected objects/monsters/whatever.  There's already a routine to
redraw the current view of the map without recalculating it, but it
wasn't being used for ^R during getpos operation.
2023-10-12 01:18:55 -07:00
PatR
05a99064b6 fix #K3997 - livelog feedback for high priests
If you killed a second high priest (either two on Astral or first in
the Sanctum and another on Astral) the livelog/#chronicle message
would report "killed high priest of Foo (2nd time)" even though the
first was the high priest of Bar, or even just "killed high priest
(2nd time)" if second kill happened when not adjacent.

High priests pass the 'unique monster' test (even though they aren't
actually unique--there will be four of them) so get logged for killing
such.  Always report "killed high priest of Foo" and only do so if the
specific high priest[ess] monster hasn't been revived and re-killed.

Logging deaths of unique monsters normally reports the 1st, 2nd, 3rd,
5th, 10th, and various later instances.  If you were to kill Moloch's
high priest and all three on Astral, the last one wouldn't be logged
because 4th instance gets skipped.  This forces each one to be treated
as the 1st (provided that the mrevived flag is clear), so for logging
purposes it will now behave as if there are 4 distinct high priests.
2023-08-29 00:02:19 -07:00
PatR
0d31bb8c88 change program_state.getting_a_command
to program_state.input_state

Rename program_state.getting_a_command and give it an int value
instead of treating it as boolean.  Start using to it for Qt to
suppress commands initiated from the drop down menus in the title bar
if nethack isn't expecting to get a command from the user.  Those menu
choices inject extended command text into the input stream and should
be avoided when entering text or waiting for a menu to be dismissed.

These menus would be better if they grayed out unavailable choices
when pulled down instead of accepting any choice and then treating
that no good.  I'm not going to try to figure out to do that with Qt.
And this workaround for the menus doesn't have any affect on the
toolbar buttons below the title bar.  Those execute core commands
directly and when I tried to use jacket routines instead, the tool bar
stopped showing up so I've given up.

This won't fix the reported problem of getting stuck in a loop.
2023-04-06 01:56:08 -07:00
Pasi Kallinen
62476fe101 Stop blinking cursor on hero when farlooking
I happened to notice when looking at a ttyrec that farlooking
with automatic description would blink the cursor on hero for
one frame, and then back on the farlooked map location.
2023-03-10 14:11:56 +02:00
nhmall
ecf74d5308 some pline()-like function usage 2023-03-08 19:12:52 -05:00
PatR
b3d5158e64 git issue #994 - killed by a touch of death
Issue reported by vultur-cadens:  cause of death reason for touch
of death and death due to loss of strength only showed the cause,
not the monster spellcaster who was responsible.

This changes
|Killed by a touch of death.
to
|Killed by the touch of death inflicted by the Wizard of Yendor.
and
|Killed by terminal fraility.
to
|Killed by strength loss inflicted by a chameleon imitating an arch-lich.
(The 'imitating' part doesn't fit on the tombstone but will be present
in logfile/xlogfile.)

Noticed while implemented this:  touch of death was modifying u.uhpmax
and basing death vs damage on that even when hero was polymorphed.
It now rehumanizes the hero in that situation.

Closes #994
2023-03-05 15:11:25 -08:00
Pasi Kallinen
5d659cf1f6 Tips and option to disable them
Adds a more general way to handle gameplay tips, and adds
a boolean option "tips", which can be used to disable all
tips.  Adds a helpful longer message when the game goes
into the "farlook" mode.

Also adds a lua binding to easily show multi-line text
in a menu window.

Breaks save compat.
2023-02-19 15:56:18 +02:00
PatR
04ef7cba46 Address github issue #983 - getpos valid locations
Issue reported by entrez:  when getpos() is being used to have the
player pick a map location, if player types '$' (for some operations
like jumping or applying a polearm) then valid spots are highlighted
but the highlighting obscures what was shown on the map.  I'm not
sure whether this 'fixes' the issue but it's probably good enough.
Allow typing another '$' to toggle the highlighting back off,
redisplaying the map in the process, without needing to move the
cursor or type ^R to accomplish that.  Toggling seems more intuitive.

This is a lot more complicated than it needs to be because I assumed
that the background aspect of highlighting stayed visible when the
glyphs were reverted.  It doesn't work that way but I haven't thrown
out the effort to make toggling the highlights work sanely.  Prior
to this, typing '$' again just redrew the highlighting again, with
no visible effect.

Closes #983
2023-02-17 12:21:54 -08:00
nhmall
288cc01f3a Merge branch 'naming-overflow-fix2' into NetHack-3.7 2023-02-16 18:52:47 -05:00
nhmall
fbd9a7bae8 another update to the soundlib interface
sound_verbal(char *text, int32_t gender, int32_t tone, int32_t vol,
             int32_t moreinfo);
    -- NetHack will call this function when it wants to pass text of
       spoken language by a character or creature within the game.
    -- text is a transcript of what has been spoken.
    -- gender indicates MALE or FEMALE sounding voice.
    -- tone indicates the tone of the voice.
    -- vol is the volume (1% - 100%) for the sound.
    -- moreinfo is used to provide additional information to the soundlib.
    -- there may be some accessibility uses for this function.

It may be useful for accessibility purposes too.

A preliminary implementation has been attempted for macsound to test
the interface on macOS. No tinkering of the voices has been done.

Use of the test implementation requires the following at build time with make.
    WANT_SPEECH=1
That needs to be included on the make command line to enable the test code,
otherwise just the interface update is compiled in.

I don't know for certain when AVSpeechSynthesizer went into macOS, but older versions
likely don't support it, and would just leave off the WANT_SPEECH=1.

If built with WANT_SPEECH=1, the 'voices' NetHack option needs to be enabled.

It was a bit strange, when I first started up the test, to hear Asidonhopo,
the shopkeeper, talking to me as I entered his shop and interacted with him.
2023-02-07 00:44:36 -05:00
PatR
b9bbf0205b Pending 3.7 edition of the naming overflow patch.
Like the 3.6.7 one, the original pieces have been combined into one
commit.  But it is separate from the one added to that version.
2023-01-28 13:02:46 -08:00
nhmall
2fc0d25d45 introduce support for coloring the frame behind a map location
Also includes support by paxed for polearm targeting using the
frame color.

Also renames USE_TILES to TILES_IN_GLYPHMAP which is a more
accurate description.

Not all window interfaces have full support for the color framing
of the background square yet.

MS-DOS needs further work (to bring it to both VESA and VGA, with
and without tiles.

Windows GUI is missing support.

X11 and Qt have been started, but may require further refinement.
2023-01-01 19:55:02 -05:00
PatR
e4145f7dc1 calling objects
An earlier attempted fix was not working as intended.  This
accomplishes what I was trying to do.  I haven't reverted
interesting_to_discover() to static within o_init.c.
2022-12-14 14:07:22 -08:00
PatR
daeec9291c refine PR #946 - named armor
Move the new stuff from PR #946 out of xname() into new routine
armor_simple_name().

Noticed while testing:  tweak 'call object type' so that it doesn't
list instances of pre-discovered armor as likely candidates since
assigning a name to such wasn't showing up in the discoveries list.

Add "silver shield" as wishing synonym for "polished silver shield".
2022-12-14 07:37:04 -08:00