diff --git a/doc/fixes36.3 b/doc/fixes36.3 index 05ed99bd2..7f7371c8a 100644 --- a/doc/fixes36.3 +++ b/doc/fixes36.3 @@ -1,4 +1,4 @@ -$NHDT-Branch: NetHack-3.6 $:$NHDT-Revision: 1.25 $ $NHDT-Date: 1559035655 2019/05/28 09:27:35 $ +$NHDT-Branch: NetHack-3.6 $:$NHDT-Revision: 1.26 $ $NHDT-Date: 1559088523 2019/05/29 00:08:43 $ This fixes36.3 file is here to capture information about updates in the 3.6.x lineage following the release of 3.6.2 in May 2019. Please note, however, @@ -30,6 +30,8 @@ free ball and chain if Punished hero dies while descending stairs or dies or quits while swallowed; put ball and chain in bones for the stairs case if hero dies while a thrown or kicked object is in transit, put that object on the map in case bones data gets saved +fix a memory leak that occurred if player used wizard mode to leave and return + to the Plane of Air or Plane of Water (not possible in normal play) Fixes to Post-3.6.2 Problems that Were Exposed Via git Repository diff --git a/src/do.c b/src/do.c index 20aadf751..9c887c037 100644 --- a/src/do.c +++ b/src/do.c @@ -1,4 +1,4 @@ -/* NetHack 3.6 do.c $NHDT-Date: 1548978604 2019/01/31 23:50:04 $ $NHDT-Branch: NetHack-3.6.2-beta01 $:$NHDT-Revision: 1.189 $ */ +/* NetHack 3.6 do.c $NHDT-Date: 1559088523 2019/05/29 00:08:43 $ $NHDT-Branch: NetHack-3.6 $:$NHDT-Revision: 1.190 $ */ /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */ /*-Copyright (c) Derek S. Ray, 2015. */ /* NetHack may be freely redistributed. See license for details. */ @@ -1365,6 +1365,16 @@ boolean at_stairs, falling, portal; } savelev(fd, ledger_no(&u.uz), cant_go_back ? FREE_SAVE : (WRITE_SAVE | FREE_SAVE)); + /* air bubbles and clouds are saved in game-state rather than with the + level they're used on; in normal play, you can't leave and return + to any endgame level--bubbles aren't needed once you move to the + next level so used to be discarded when the next special level was + loaded; but in wizard mode you can leave and return, and since they + aren't saved with the level and restored upon return (new ones are + created instead), we need to discard them to avoid a memory leak; + so bubbles are now discarded as we leave the level they're used on */ + if (Is_waterlevel(&u.uz) || Is_airlevel(&u.uz)) + save_waterlevel(fd, FREE_SAVE); /* note: doesn't use 'fd' */ bclose(fd); if (cant_go_back) { /* discard unreachable levels; keep #0 */ @@ -1428,6 +1438,7 @@ boolean at_stairs, falling, portal; oinit(); /* reassign level dependent obj probabilities */ } reglyph_darkroom(); + u.uinwater = 0; /* do this prior to level-change pline messages */ vision_reset(); /* clear old level's line-of-sight */ vision_full_recalc = 0; /* don't let that reenable vision yet */ diff --git a/src/mkmaze.c b/src/mkmaze.c index 2a8dc226c..7bea6485e 100644 --- a/src/mkmaze.c +++ b/src/mkmaze.c @@ -1,4 +1,4 @@ -/* NetHack 3.6 mkmaze.c $NHDT-Date: 1558562368 2019/05/22 21:59:28 $ $NHDT-Branch: NetHack-3.6 $:$NHDT-Revision: 1.70 $ */ +/* NetHack 3.6 mkmaze.c $NHDT-Date: 1559088524 2019/05/29 00:08:44 $ $NHDT-Branch: NetHack-3.6 $:$NHDT-Revision: 1.71 $ */ /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */ /*-Copyright (c) Pasi Kallinen, 2018. */ /* NetHack may be freely redistributed. See license for details. */ @@ -460,8 +460,6 @@ baalz_fixup() bughack.inarea.y2 = bughack.delarea.y2 = 0; } -static boolean was_waterlevel; /* ugh... this shouldn't be needed */ - /* this is special stuff that the level compiler cannot (yet) handle */ void fixup_special() @@ -472,14 +470,8 @@ fixup_special() struct mkroom *croom; boolean added_branch = FALSE; - if (was_waterlevel) { - was_waterlevel = FALSE; - u.uinwater = 0; - unsetup_waterlevel(); - } if (Is_waterlevel(&u.uz) || Is_airlevel(&u.uz)) { level.flags.hero_memory = 0; - was_waterlevel = TRUE; /* water level is an odd beast - it has to be set up before calling place_lregions etc. */ setup_waterlevel(); @@ -497,6 +489,7 @@ fixup_special() lev.dlevel = atoi(r->rname.str); } else { s_level *sp = find_level(r->rname.str); + lev = sp->dlevel; } /*FALLTHRU*/ @@ -1574,13 +1567,13 @@ int fd, mode; int n = 0; for (b = bbubbles; b; b = b->next) ++n; - bwrite(fd, (genericptr_t) &n, sizeof(int)); - bwrite(fd, (genericptr_t) &xmin, sizeof(int)); - bwrite(fd, (genericptr_t) &ymin, sizeof(int)); - bwrite(fd, (genericptr_t) &xmax, sizeof(int)); - bwrite(fd, (genericptr_t) &ymax, sizeof(int)); + bwrite(fd, (genericptr_t) &n, sizeof n); + bwrite(fd, (genericptr_t) &xmin, sizeof xmin); + bwrite(fd, (genericptr_t) &ymin, sizeof ymin); + bwrite(fd, (genericptr_t) &xmax, sizeof xmax); + bwrite(fd, (genericptr_t) &ymax, sizeof ymax); for (b = bbubbles; b; b = b->next) - bwrite(fd, (genericptr_t) b, sizeof(struct bubble)); + bwrite(fd, (genericptr_t) b, sizeof *b); } if (release_data(mode)) unsetup_waterlevel(); @@ -1597,15 +1590,15 @@ int fd; return; set_wportal(); - mread(fd, (genericptr_t) &n, sizeof(int)); - mread(fd, (genericptr_t) &xmin, sizeof(int)); - mread(fd, (genericptr_t) &ymin, sizeof(int)); - mread(fd, (genericptr_t) &xmax, sizeof(int)); - mread(fd, (genericptr_t) &ymax, sizeof(int)); + mread(fd, (genericptr_t) &n, sizeof n); + mread(fd, (genericptr_t) &xmin, sizeof xmin); + mread(fd, (genericptr_t) &ymin, sizeof ymin); + mread(fd, (genericptr_t) &xmax, sizeof xmax); + mread(fd, (genericptr_t) &ymax, sizeof ymax); for (i = 0; i < n; i++) { btmp = b; - b = (struct bubble *) alloc(sizeof(struct bubble)); - mread(fd, (genericptr_t) b, sizeof(struct bubble)); + b = (struct bubble *) alloc(sizeof *b); + mread(fd, (genericptr_t) b, sizeof *b); if (bbubbles) { btmp->next = b; b->prev = btmp; @@ -1617,7 +1610,6 @@ int fd; } ebubbles = b; b->next = (struct bubble *) 0; - was_waterlevel = TRUE; } const char * @@ -1740,7 +1732,7 @@ int x, y, n; if (bmask[n][1] > MAX_BMASK) { panic("bmask size is larger than MAX_BMASK"); } - b = (struct bubble *) alloc(sizeof(struct bubble)); + b = (struct bubble *) alloc(sizeof *b); if ((x + (int) bmask[n][0] - 1) > bxmax) x = bxmax - bmask[n][0] + 1; if ((y + (int) bmask[n][1] - 1) > bymax) @@ -1751,7 +1743,7 @@ int x, y, n; b->dy = 1 - rn2(3); /* y dimension is the length of bitmap data - see bmask above */ (void) memcpy((genericptr_t) b->bm, (genericptr_t) bmask[n], - (bmask[n][1] + 2) * sizeof(b->bm[0])); + (bmask[n][1] + 2) * sizeof (b->bm[0])); b->cons = 0; if (!bbubbles) bbubbles = b;