Skip to content

Commit

Permalink
Fix: impossible "trying to break non-equipped glass obj?" when attack…
Browse files Browse the repository at this point in the history
…ing with certain objects.

Discovered this whilst fuzzing. The hero was attacking monsters with a
wielded paper object (scroll, spellbook). One particular monster it
attacked was a flaming sphere, which blows up once killed, and will
cause fire damage to random objects in inventory. Things like spellbooks
and scrolls will burn up instantly - when that happened while said
scroll or spellbook was being wielded, it caused an impossible in
break_glass_obj().

The fix - guard against materials that don't technically break.
  • Loading branch information
k21971 committed Mar 6, 2025
1 parent 5ab35b5 commit e00795a
Show file tree
Hide file tree
Showing 2 changed files with 14 additions and 3 deletions.
2 changes: 2 additions & 0 deletions doc/evilhack-changelog.md
Original file line number Diff line number Diff line change
Expand Up @@ -4357,4 +4357,6 @@ The following changes to date are:
- Fix: the Riders/Wizard of Yendor should not be able to open any locked
container
- Fix: wizkill command vs dmonsfree
- Fix: impossible "trying to break non-equipped glass obj?" when
attacking with certain objects

15 changes: 12 additions & 3 deletions src/dothrow.c
Original file line number Diff line number Diff line change
Expand Up @@ -2670,9 +2670,9 @@ boolean in_view;

/* Possibly destroy a glass object by its use in melee or thrown combat.
* Return TRUE if destroyed.
* Separate logic from breakobj because we are not unconditionally breaking the
* object, and we also need to make sure it's removed from the inventory
* properly. */
* Separate logic from breakobj because we are not unconditionally
* breaking the object, and we also need to make sure it's removed from
* the inventory properly. */
boolean
break_glass_obj(obj)
struct obj* obj;
Expand All @@ -2685,6 +2685,15 @@ struct obj* obj;
if (!obj)
return FALSE;

/* guard against objects that can never break
or go 'splat!' */
if (!(obj->material == GLASS
|| obj->material == FLESH
|| obj->material == VEGGY
|| obj->material == ADAMANTINE
|| obj->forged_qual == FQ_INFERIOR))
return FALSE;

ucarried = carried(obj);

if (ucarried) {
Expand Down

0 comments on commit e00795a

Please sign in to comment.