diff --git a/src/do.c b/src/do.c index c6267249f..f26ffe68d 100644 --- a/src/do.c +++ b/src/do.c @@ -1442,8 +1442,7 @@ goto_level( unplacebc(); reset_utrap(FALSE); /* needed in level_tele */ fill_pit(u.ux, u.uy); - set_ustuck((struct monst *) 0); /* idem */ - u.uswallow = u.uswldtim = 0; + set_ustuck((struct monst *) 0); /* clear u.ustuck and u.uswallow */ set_uinwater(0); /* u.uinwater = 0 */ u.uundetected = 0; /* not hidden, even if means are available */ keepdogs(FALSE); diff --git a/src/mon.c b/src/mon.c index cbcbadb06..ae3aa2801 100644 --- a/src/mon.c +++ b/src/mon.c @@ -2952,7 +2952,7 @@ monkilled( } void -set_ustuck(struct monst* mtmp) +set_ustuck(struct monst *mtmp) { if (iflags.sanity_check || iflags.debug_fuzzer) { if (mtmp && !next2u(mtmp->mx, mtmp->my)) @@ -2962,23 +2962,26 @@ set_ustuck(struct monst* mtmp) g.context.botl = 1; u.ustuck = mtmp; + if (!u.ustuck) { + u.uswallow = 0; + u.uswldtim = 0; + } } void -unstuck(struct monst* mtmp) +unstuck(struct monst *mtmp) { if (u.ustuck == mtmp) { struct permonst *ptr = mtmp->data; + unsigned swallowed = u.uswallow; /* do this first so that docrt()'s botl update is accurate; - safe to do as long as u.uswallow is also cleared before docrt() */ + clears u.uswallow as well as setting u.ustuck to Null */ set_ustuck((struct monst *) 0); - if (u.uswallow) { + if (swallowed) { u.ux = mtmp->mx; u.uy = mtmp->my; - u.uswallow = 0; - u.uswldtim = 0; if (Punished && uchain->where != OBJ_FLOOR) placebc(); g.vision_full_recalc = 1; diff --git a/src/save.c b/src/save.c index 2466969d1..a953e5c7c 100644 --- a/src/save.c +++ b/src/save.c @@ -183,7 +183,7 @@ dosave0(void) /* these pointers are no longer valid, and at least u.usteed * may mislead place_monster() on other levels */ - set_ustuck((struct monst *) 0); + set_ustuck((struct monst *) 0); /* also clears u.uswallow */ u.usteed = (struct monst *) 0; for (ltmp = (xint8) 1; ltmp <= maxledgerno(); ltmp++) { diff --git a/src/teleport.c b/src/teleport.c index fe0fc94e5..08dda0baf 100644 --- a/src/teleport.c +++ b/src/teleport.c @@ -354,6 +354,7 @@ teleok(coordxy x, coordxy y, boolean trapok) void teleds(coordxy nux, coordxy nuy, int teleds_flags) { + unsigned was_swallowed; boolean ball_active, ball_still_in_range = FALSE, allow_drag = (teleds_flags & TELEDS_ALLOW_DRAG) != 0, is_teleport = (teleds_flags & TELEDS_TELEPORT) != 0; @@ -391,6 +392,7 @@ teleds(coordxy nux, coordxy nuy, int teleds_flags) unplacebc(); /* have to move the ball */ } reset_utrap(FALSE); + was_swallowed = u.uswallow; /* set_ustuck(Null) clears uswallow */ set_ustuck((struct monst *) 0); u.ux0 = u.ux; u.uy0 = u.uy; @@ -400,9 +402,7 @@ teleds(coordxy nux, coordxy nuy, int teleds_flags) g.youmonst.m_ap_type = M_AP_NOTHING; } - if (u.uswallow) { - /* subset of unstuck() */ - u.uswldtim = u.uswallow = 0; + if (was_swallowed) { if (Punished) { /* ball&chain are off map while swallowed */ ball_active = TRUE; /* to put chain and non-carried ball on map */ ball_still_in_range = allow_drag = FALSE; /* (redundant) */