From 48a82fea8ce138577fafa35f4fdd968ac41225b3 Mon Sep 17 00:00:00 2001 From: PatR Date: Sun, 22 Dec 2019 13:30:25 -0800 Subject: [PATCH] fix github issue #266 - timed clairvoyance When the hero has random clairvoyance, the code used | (moves % 15) == 0 && rn2(2) != 0 (where 'moves' is actually the turn number) to decide when it would kick in and show a portion of the map. If the hero was fast enough to get an extra move when the turn value met the (moves % 15) == 0 condition then clairvoyance could happen twice (or more if poly'd) on the same turn. The changes (one new field, reordering a few others) in 'struct context' invalidate existing 3.7.0-x save files. Fixes #266 --- doc/fixes37.0 | 5 +++-- include/context.h | 15 ++++++++------- include/patchlevel.h | 4 ++-- src/allmain.c | 24 ++++++++++++++++++++---- 4 files changed, 33 insertions(+), 15 deletions(-) diff --git a/doc/fixes37.0 b/doc/fixes37.0 index 41f7347a7..63c0f879d 100644 --- a/doc/fixes37.0 +++ b/doc/fixes37.0 @@ -1,4 +1,4 @@ -$NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.22 $ $NHDT-Date: 1576288434 2019/12/14 01:53:54 $ +$NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.26 $ $NHDT-Date: 1577050214 2019/12/22 21:30:14 $ General Fixes and Modified Features ----------------------------------- @@ -13,6 +13,7 @@ improvements to pronoun usage when hallucinating function calls made from mapglyph based on dungeon level are now called once per level fix accessing mons[-1] when trying to gate in a non-valid demon +fast hero could have random clairvoyance happen more than once on same turn Fixes to Pre-3.7.0 Problems that Were Exposed Via git Repository @@ -56,7 +57,7 @@ Code Cleanup and Reorganization move majority of global variables into instance_globals struct g move zeroobj, zeromonst, zeroany into const_globals struct cg remove STATIC_DCL, STATIC_OVL, STATIC_VAR, STATIC_PTR -old Qt moved from win/Qt to win/Qt3 +old Qt moved from win/Qt to win/Qt3 and files renamed to use qt3_ prefix more current Qt for Qt version 4 and 5 moved from win/Qt4 to win/Qt; qt4 moniker changed to qt_ diff --git a/include/context.h b/include/context.h index 4e20f3bdc..10034a4fb 100644 --- a/include/context.h +++ b/include/context.h @@ -1,4 +1,4 @@ -/* NetHack 3.6 context.h $NHDT-Date: 1575775592 2019/12/08 03:26:32 $ $NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.35 $ */ +/* NetHack 3.6 context.h $NHDT-Date: 1577050216 2019/12/22 21:30:16 $ $NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.36 $ */ /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */ /*-Copyright (c) Michael Allison, 2006. */ /* NetHack may be freely redistributed. See license for details. */ @@ -111,14 +111,15 @@ struct context_info { unsigned run; /* 0: h (etc), 1: H (etc), 2: fh (etc) */ /* 3: FH, 4: ff+, 5: ff-, 6: FF+, 7: FF- */ /* 8: travel */ - unsigned startingpet_mid; - int current_fruit; /* fruit->fid corresponding to g.pl_fruit[] */ - int warnlevel; + unsigned startingpet_mid; /* monster id number for initial pet */ + int current_fruit; /* fruit->fid corresponding to g.pl_fruit[] */ + int mysteryforce; /* adjusts how often "mysterious force" kicks in */ int rndencode; /* randomized escape sequence introducer */ - int mysteryforce; + int warnlevel; /* threshold (digit) to warn about unseen mons */ long next_attrib_check; /* next attribute check */ - long stethoscope_move; - short stethoscope_movement; + long seer_turn; /* when random clairvoyance will next kick in */ + long stethoscope_move; /* when a stethoscope was last used */ + short stethoscope_movement; /* to track multiple moves on same turn */ boolean travel; /* find way automatically to u.tx,u.ty */ boolean travel1; /* first travel step */ boolean forcefight; diff --git a/include/patchlevel.h b/include/patchlevel.h index 3d272ed14..4f90efd41 100644 --- a/include/patchlevel.h +++ b/include/patchlevel.h @@ -1,4 +1,4 @@ -/* NetHack 3.7 patchlevel.h $NHDT-Date: 1575775596 2019/12/08 03:26:36 $ $NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.136 $ */ +/* NetHack 3.7 patchlevel.h $NHDT-Date: 1577050214 2019/12/22 21:30:14 $ $NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.141 $ */ /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */ /*-Copyright (c) Michael Allison, 2012. */ /* NetHack may be freely redistributed. See license for details. */ @@ -14,7 +14,7 @@ * Incrementing EDITLEVEL can be used to force invalidation of old bones * and save files. */ -#define EDITLEVEL 3 +#define EDITLEVEL 4 #define COPYRIGHT_BANNER_A "NetHack, Copyright 1985-2019" #define COPYRIGHT_BANNER_B \ diff --git a/src/allmain.c b/src/allmain.c index 5808503e8..678ff117d 100644 --- a/src/allmain.c +++ b/src/allmain.c @@ -1,4 +1,4 @@ -/* NetHack 3.6 allmain.c $NHDT-Date: 1555552624 2019/04/18 01:57:04 $ $NHDT-Branch: NetHack-3.6.2-beta01 $:$NHDT-Revision: 1.100 $ */ +/* NetHack 3.6 allmain.c $NHDT-Date: 1577050218 2019/12/22 21:30:18 $ $NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.136 $ */ /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */ /*-Copyright (c) Robert Patrick Rankin, 2012. */ /* NetHack may be freely redistributed. See license for details. */ @@ -66,6 +66,10 @@ boolean resuming; g.context.rndencode = rnd(9000); set_wear((struct obj *) 0); /* for side-effects of starting gear */ (void) pickup(1); /* autopickup at initial location */ + /* only matters if someday a character is able to start with + clairvoyance (wizard with cornuthaum perhaps?); without this, + first "random" occurrence would always kick in on turn 1 */ + g.context.seer_turn = (long) rnd(30); } g.context.botlx = TRUE; /* for STATUS_HILITES */ update_inventory(); /* for perm_invent */ @@ -336,9 +340,21 @@ boolean resuming; #endif if (g.context.bypasses) clear_bypasses(); - if ((u.uhave.amulet || Clairvoyant) && !In_endgame(&u.uz) - && !BClairvoyant && !(g.moves % 15) && !rn2(2)) - do_vicinity_map((struct obj *) 0); + if (g.moves >= g.context.seer_turn) { + if ((u.uhave.amulet || Clairvoyant) && !In_endgame(&u.uz) + && !BClairvoyant) + do_vicinity_map((struct obj *) 0); + /* we maintain this counter even when clairvoyance isn't + taking place; on average, go again 30 turns from now */ + g.context.seer_turn = g.moves + (long) rn1(31, 15); /*15..45*/ + /* [it used to be that on every 15th turn, there was a 50% + chance of farsight, so it could happen as often as every + 15 turns or theoretically never happen at all; but when + a fast hero got multiple moves on that 15th turn, it + could actually happen more than once on the same turn!] */ + } + /* [fast hero who gets multiple moves per turn ends up sinking + multiple times per turn; is that what we really want?] */ if (u.utrap && u.utraptype == TT_LAVA) sink_into_lava(); /* when/if hero escapes from lava, he can't just stay there */