- /* Herewith are all the variables whose values can change during a game,
- * omitting a few (such as I, J) whose values between turns are
- * irrelevant and some whose values when a game is
- * suspended or resumed are guaranteed to match. If unsure whether a value
- * needs to be saved, include it. Overkill can't hurt. Pad the last savwds
- * with junk variables to bring it up to 7 values. */
- SAVWDS(game.abbnum,game.blklin,game.bonus,game.clock1,game.clock2,game.closed,game.closng);
- SAVWDS(game.detail,game.dflag,game.dkill,game.dtotal,game.foobar,game.holdng,game.iwest);
- SAVWDS(game.knfloc,game.limit,K,game.lmwarn,game.loc,game.newloc,game.numdie);
- SAVWDS(K,game.oldlc2,game.oldloc,game.oldobj,game.panic,game.saved,game.setup);
- SAVWDS(SPK,game.tally,game.thresh,game.trndex,game.trnluz,game.turns,OBJTXT[OYSTER]);
- SAVWDS(K,WD1,WD1X,WD2,game.wzdark,game.zzword,OBJSND[BIRD]);
- SAVWDS(OBJTXT[SIGN],game.clshnt,game.novice,K,K,K,K);
- SAVARR(game.abbrev,LOCSIZ);
- SAVARR(game.atloc,LOCSIZ);
- SAVARR(game.dloc,NDWARVES);
- SAVARR(game.dseen,NDWARVES);
- SAVARR(game.fixed,NOBJECTS);
- SAVARR(game.hinted,HNTSIZ);
- SAVARR(game.hintlc,HNTSIZ);
- SAVARR(game.link,NOBJECTS*2);
- SAVARR(game.odloc,NDWARVES);
- SAVARR(game.place,NOBJECTS);
- SAVARR(game.prop,NOBJECTS);
- SAVWRD(kk,K);
- if (K != 0) {
- RSPEAK(270);
- exit(0);
+
+ /* Recalculate tally, throw the towel if in disagreement */
+ long temp_tally = 0;
+ for (int treasure = 1; treasure <= NOBJECTS; treasure++) {
+ if (objects[treasure].is_treasure) {
+ if (valgame.prop[treasure] == STATE_NOTFOUND) {
+ ++temp_tally;
+ }
+ }
+ }
+ if (temp_tally != valgame.tally) {
+ return false;
+ }
+
+ /* Check that properties of objects aren't beyond expected */
+ for (int obj = 0; obj <= NOBJECTS; obj++) {
+ if (game.prop[obj] < STATE_NOTFOUND || game.prop[obj] > 1) {
+ switch (obj) {
+ case RUG:
+ case DRAGON:
+ case BIRD:
+ case BOTTLE:
+ case PLANT:
+ case PLANT2:
+ case TROLL:
+ case URN:
+ case EGGS:
+ case VASE:
+ case CHAIN:
+ if (game.prop[obj] == 2) // There are multiple different states, but it's convenient to clump them together
+ continue;
+ case BEAR:
+ if (game.prop[BEAR] == CONTENTED_BEAR || game.prop[BEAR] == BEAR_DEAD)
+ continue;
+ default:
+ printf("%i", obj);
+ return false;
+ }
+ }