From 40716b7b0abb3bbdb4f21b8849f1f2882e244e80 Mon Sep 17 00:00:00 2001 From: PatR Date: Sat, 6 Jul 2024 17:00:30 -0700 Subject: [PATCH] fix #K4199 - dereference of null firstmatch pointer Bumping into something (by fuzzer) with mention_walls On crashed when trying to display output generated by do_screen_description(). I wasn't able to reproduce this but didn't spend much time trying. Without a test case I'm only guessing that this fix solves the problem. If there was a monster phazing at the 'wall' location or an object embedded there, the screen description wouldn't be appropriate for trying to describe the terrain. (I don't think that the pass-walls monster csse would reach the affected code but the embedded object case might.) Use the background glyph calculated for the map, which yields the intended "stone" instead of "wall" when outside a not-yet-mapped wall, rather than the displayed glyph. --- src/hack.c | 27 +++++++++++++-------------- 1 file changed, 13 insertions(+), 14 deletions(-) diff --git a/src/hack.c b/src/hack.c index 2836500e8..886215770 100644 --- a/src/hack.c +++ b/src/hack.c @@ -959,25 +959,24 @@ test_move( return FALSE; } else { if (mode == DO_MOVE) { - if (is_db_wall(x, y)) + if (is_db_wall(x, y)) { pline("That drawbridge is up!"); - /* sokoban restriction stays even after puzzle is solved */ - else if (Passes_walls && !may_passwall(x, y) - && In_sokoban(&u.uz)) + } else if (Passes_walls && !may_passwall(x, y) + && In_sokoban(&u.uz)) { + /* soko restriction stays even after puzzle is solved */ pline_The("Sokoban walls resist your ability."); - else if (flags.mention_walls) { + } else if (flags.mention_walls) { char buf[BUFSZ]; - coord cc; - int sym = 0; - const char *firstmatch = 0; + int glyph = back_to_glyph(x, y), + sym = glyph_is_cmap(glyph) ? glyph_to_cmap(glyph) : -1; - cc.x = x, cc.y = y; - do_screen_description(cc, TRUE, sym, buf, &firstmatch, - NULL); - if (!strcmp(firstmatch, "stone")) - Sprintf(buf, "solid stone"); + if (sym == S_stone) + Strcpy(buf, "solid stone"); + else if (sym >= 0) + Strcpy(buf, an(defsyms[sym].explanation)); else - Sprintf(buf, "%s", an(firstmatch)); + Sprintf(buf, "impossible [background glyph=%d]", + glyph); pline_dir(xytod(dx, dy), "It's %s.", buf); } }