[comp.sources.games] v07i025: omega3 - rogue like dungeon exploration

billr@saab.CNA.TEK.COM (Bill Randle) (07/13/89)

Submitted-by: "Laurence R. Brothers"   <brothers@paul.rutgers.edu>
Posting-number: Volume 7, Issue 25
Archive-name: omega3/Part06
Supersedes: omega2: Volume 5, Issue 11-29,38-40



#! /bin/sh
# This is a shell archive.  Remove anything before this line, then unpack
# it by saving it into a file and typing "sh file".  To overwrite existing
# files, type "sh file -c".  You can also feed this as standard input via
# unshar, or by typing "sh <file", e.g..  If this archive is complete, you
# will see the following message at the end:
#		"End of archive 6 (of 20)."
# Contents:  oaux3.c odate.h osave.c
# Wrapped by billr@saab on Thu Jun 29 08:14:01 1989
PATH=/bin:/usr/bin:/usr/ucb ; export PATH
if test -f 'oaux3.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'oaux3.c'\"
else
echo shar: Extracting \"'oaux3.c'\" \(30108 characters\)
sed "s/^X//" >'oaux3.c' <<'END_OF_FILE'
X/* omega copyright (C) by Laurence Raphael Brothers, 1987,1988,1989 */
X
X/* oaux3.c */
X
X/* some functions called by ocom.c, also see oaux1.c, oaux2.c */ 
X/* This is a real grab bag file. It contains functions used by
X   oaux1 and o.c, as well as elsewhere. It is mainly here so oaux1.c
X   and oaux2 are not huge */
X  
X#include "oglob.h"
X
X/* check every ten minutes */
Xvoid tenminute_check()
X{
X  if (Time % 60 == 0) hourly_check();
X  else {
X    if (Current_Environment == Current_Dungeon)  wandercheck();
X    minute_status_check();
X    tenminute_status_check();
X    if ((Player.status[DISEASED] < 1) && (Player.hp < Player.maxhp))
X      Player.hp = min(Player.maxhp,Player.hp+Player.level+1);
X    if (Current_Environment != E_COUNTRYSIDE)
X      indoors_random_event();
X  }
X}
X
X
X
X/* hourly check is same as ten_minutely check except food is also
X   checked, and since time moves in hours out of doors, also
X   outdoors_random_event is possible */
X
Xvoid hourly_check()
X{
X  Player.food--;
X  foodcheck();
X  if (hour()==0) { /* midnight, a new day */
X    moon_check();
X    Date++;
X  }
X  torch_check();
X  if (Current_Environment == Current_Dungeon)  wandercheck();
X  minute_status_check();
X  tenminute_status_check();
X  if ((Player.status[DISEASED] == 0) && (Player.hp < Player.maxhp))
X    Player.hp = min(Player.maxhp,Player.hp+Player.level+1);
X  if (Current_Environment != E_COUNTRYSIDE)
X    indoors_random_event();
X}
X
X
X
X
Xvoid indoors_random_event()
X{
X  pml ml;
X  pol ol;
X  switch(random_range(1000)) {
X    case 0: 
X      print3("You feel an unexplainable elation.");
X      morewait();
X      break;
X    case 1:
X      print3("You hear a distant rumbling.");
X      morewait();
X      break;
X    case 2:
X      print3("You realize your fly is open.");
X      morewait();
X      break;
X    case 3:
X      print3("You have a sudden craving for a pecan twirl.");
X      morewait();
X      break;
X    case 4:
X      print3("A mysterious healing flux settles over the level.");
X      morewait();
X      for (ml=Level->mlist;ml!=NULL;ml=ml->next)
X	if (ml->m->hp > 0) ml->m->hp = Monsters[ml->m->id].hp;
X      Player.hp = max(Player.hp,Player.maxhp);
X      break;
X    case 5:
X      print3("You discover an itch just where you can't scratch it.");
X      morewait();
X      break;
X    case 6:
X      print3("A cosmic ray strikes!");
X      p_damage(10,UNSTOPPABLE,"a cosmic ray");
X      morewait();
X      break;
X    case 7:
X      print3("You catch your second wind....");
X      Player.hp = ++Player.maxhp;
X      Player.mana = max(Player.mana, calcmana());
X      morewait();
X      break;
X    case 8:
X      print3("You find some spare change in a hidden pocket.");
X      Player.cash += Player.level*Player.level+1;
X      morewait();
X      break;
X    case 9:
X      print3("You feel strangely lucky.");
X      morewait();
X      break;
X    case 10:
X      print3("You trip over something hidden in a shadow...");
X      morewait();
X      ol = ((pol) malloc(sizeof(oltype)));
X      ol->thing = create_object(difficulty());
X      ol->next = Level->site[Player.x][Player.y].things;
X      Level->site[Player.x][Player.y].things = ol;
X      pickup();
X      break;
X    case 11: 
X      print3("A mysterious voice echoes all around you....");
X      hint();
X      morewait();
X      break;
X    case 12:
X      if (Balance > 0) {
X	print3("You get word of the failure of your bank!");
X	Balance = 0;
X      }
X      else print3("You feel lucky.");
X      break;
X    case 13:
X      if (Balance > 0) {
X	print3("You get word of a bank error in your favor!");
X	Balance += 5000;
X      }
X      else print3("You feel unlucky.");
X      break;
X    }
X  showflags();
X}
X
X
X
Xvoid outdoors_random_event()
X{
X  int num,i,j;
X  pob ob;
X
X  switch(random_range(300)) {
X  case 0:
X    switch(Country[Player.x][Player.y].current_terrain_type) {
X    case TUNDRA: 
X      mprint("It begins to snow. Heavily.");
X      break;
X    case DESERT:
X      mprint("A sandstorm swirls around you.");
X      break;
X    default:
X      if ((Date > 75) && (Date < 330))
X	mprint("You are drenched by a sudden downpour!");
X      else mprint("It begins to snow. Heavily.");
X    }
X    mprint("Due to the inclement weather conditions, you have become lost.");
X    Precipitation+=random_range(12)+1;
X    setgamestatus(LOST);
X    break;
X  case 1:
X    mprint("You enter a field of brightly colored flowers...");
X    mprint("Wow, man! These are some pretty poppies...");
X    morewait();
X    mprint("poppies...");
X    morewait();
X    mprint("poppies...");
X    morewait();
X    print3("You become somewhat disoriented...");
X    setgamestatus(LOST);
X    break;
X  case 2:
X    mprint("You discover a sprig of athelas growing lonely in the wild.");
X    mprint("Using your herbalist lore you cook a cake of lembas....");
X    ob = ((pob) malloc(sizeof(objtype)));
X    *ob = Objects[FOODID+1];
X    gain_item(ob);
X    break;
X  case 3:
X    if (Precipitation > 0) {
X      mprint("You are struck by a bolt of lightning!");
X      p_damage(random_range(25),ELECTRICITY,"a lightning strike");
X    }
X    else mprint("You feel static cling");
X    break;
X  case 4:
X    mprint("You find a fast-food establishment.");
X    l_commandant();
X    break;
X  case 5:
X    mprint("A weird howling tornado hits from out of the West!");
X    mprint("You've been caught in a chaos storm!");
X    num = random_range(300);
X    if (num <10) {
X      mprint("Your cell-structure was disrupted!");
X      p_damage(random_range(100),UNSTOPPABLE,"a chaos storm");
X    }
X    else if (num < 20) {
X      mprint("The chaos storm warps your frame!");
X      mprint("Your statistical entropy has been maximized.");
X      mprint("You feel average...");
X      Player.str = Player.maxstr = Player.con = Player.maxcon =
X	Player.dex = Player.maxdex = Player.agi = Player.maxagi =
X	  Player.iq = Player.maxiq = Player.pow = Player.maxpow =
X	    ((Player.maxstr+Player.maxcon+Player.maxdex+Player.maxagi+
X	      Player.maxiq+Player.maxpow+12)/6);
X    }
X    else if (num < 30) {
X      mprint("Your entire body glows with an eerie flickering light.");
X      for(i=1;i<MAXITEMS;i++)
X	if (Player.possessions[i] != NULL) {
X	  Player.possessions[i]->plus++;
X	  if (Player.possessions[i]->objchar == STICK)
X	    Player.possessions[i]->charge+=10;
X	  Player.possessions[i]->blessing+=10;
X	}
X      cleanse(1);
X      mprint("You feel filled with energy!");
X      Player.maxpow += 5;
X      Player.pow += 5;
X      Player.mana = Player.maxmana = calcmana() * 5;
X      mprint("You also feel weaker. Paradoxical, no?");
X      Player.con -= 5;
X      Player.maxcon -= 5;
X      if (Player.con < 3)
X	p_death("congestive heart failure");
X    }
X    else if (num < 40) {
X      mprint("Your entire body glows black.");
X      dispel(-1);
X      dispel(-1);
X      Player.pow-=10;
X      Player.mana=0;
X    }
X    else if (num < 60) {
X      mprint("The storm deposits you in a strange place....");
X      Player.x = random_range(WIDTH);
X      Player.y = random_range(LENGTH);
X      screencheck(Player.y);
X    }
X    else if (num < 70) {
X      mprint("A tendril of the storm condenses and falls into your hands.");
X      ob = ((pob) malloc(sizeof(objtype)));
X      make_artifact(ob,-1);
X      gain_item(ob);
X    }
X    else if (num < 80) {
X      if (gamestatusp(MOUNTED)) {
X	mprint("Your horse screams as he is transformed into an");
X	mprint("imaginary unseen dead tortoise.");
X	mprint("You are on foot.");
X	resetgamestatus(MOUNTED);
X      }
X      else {
X	mprint("You notice you are riding a horse. Odd. Very odd....");
X	mprint("Now that's a horse of a different color!");
X	setgamestatus(MOUNTED);
X      }
X    }
X    else if (num < 90) {
X      mprint("You feel imbued with godlike power....");
X      wish(1);
X    }
X    else if (num < 100) {
X      mprint("The chaos storm has wiped your memory!");
X      mprint("You feel extraordinarily naive....");
X      mprint("You can't remember a thing! Not even your name.");
X      Player.xp = 0;
X      Player.level = 0;
X      for (i=0;i<NUMRANKS;i++) Player.rank[i] = 0;
X      for (i=0;i<NUMSPELLS;i++) Spells[i].known = FALSE;
X      rename_player();
X    }
X    else {
X      mprint("You survive the chaos storm relatively unscathed.");
X      mprint("It was a learning experience.");
X      gain_experience(1000);
X    }
X    break;
X  case 6: case 7: case 8: case 9: case 10:
X    mprint("An encounter!");
X    change_environment(E_TACTICAL_MAP);
X    break;
X  case 11:
X    mprint("You find a Traveller's Aid station with maps of the local area.");
X    if (gamestatusp(LOST)) {
X      resetgamestatus(LOST);
X      mprint("You know where you are now.");
X    }
X    for(i=Player.x-5;i<Player.x+6;i++)
X      for(j=Player.y-5;j<Player.y+6;j++)
X	if (inbounds(i,j)) {
X	  Country[i][j].explored = TRUE;
X	  Country[i][j].current_terrain_type = 
X	    Country[i][j].base_terrain_type;
X	}
X    show_screen();
X    break;
X  case 12:
X    if (! gamestatusp(MOUNTED)) {
X      mprint("You develop blisters....");
X      p_damage(1,UNSTOPPABLE,"blisters");
X    }
X    break;
X  case 13:
X    mprint("You discover an itch just where you can't scratch it.");
X    break;
X  case 14:
X    mprint("A cosmic ray strikes!");
X    p_damage(10,UNSTOPPABLE,"a cosmic ray");
X    break;
X  case 15:
X    mprint("You feel strangely lucky.");
X    break;
X  case 16:
X    mprint("The west wind carries with it a weird echoing voice....");
X    hint();
X    break;
X  }
X  dataprint();
X  showflags();
X}
X
X
Xchar getlocation()
X{
X  char response;
X  menuprint(" (enter location [HCL])");
X  do response = mcigetc();
X  while ((response != 'h') &&
X	 (response != 'c') &&
X	 (response != 'l'));
X  switch(response){
X  case 'h':menuprint(" High."); return ('H'); break;
X  case 'c':menuprint(" Center."); return('C'); break;
X  case 'l':menuprint(" Low."); return('L'); break;
X  }
X}
X
X
X
X
X
X
X/* chance for player to resist magic somehow */
X/* hostile_magic ranges in power from 0 (weak) to 10 (strong) */
Xint magic_resist(hostile_magic)
Xint hostile_magic;
X{
X  if ((Player.rank[COLLEGE]+Player.rank[CIRCLE] > 0) &&
X      (Player.level/2 + random_range(20) >
X       hostile_magic + random_range(20))) {
X    if (Player.mana > hostile_magic * hostile_magic) {
X      mprint("Thinking fast, you defend youself with a counterspell!");
X      Player.mana -= hostile_magic * hostile_magic;
X      dataprint();
X      return(TRUE);
X    }
X  }
X  if (Player.level/4 + Player.status[PROTECTION] + random_range(20) > 
X      hostile_magic + random_range(30)) {
X    mprint("You make your saving throw!");
X    return(TRUE);
X  }
X  else return(FALSE);
X}
X
X
X
X
X
Xvoid terrain_check(takestime)
Xint takestime;
X{
X  if (! takestime)
X    switch(random_range(32)) {
X    case 0:print2("Boingg!"); break;
X    case 1:print2("Whooosh!"); break;
X    case 2:print2("Over hill, over dale...."); break;
X    case 3:print2("...able to leap over 7 leagues in a single bound....");
X      break;
X    }
X  else if (gamestatusp(MOUNTED))
X    switch(random_range(32)) {
X    case 0:
X    case 1:print2("Clippity Clop.");break;
X    case 2:print2("....my spurs go jingle jangle jingle....");break;
X    case 3:print2("....as I go riding merrily along....");break;
X    }
X  else switch(random_range(32)) {
X  case 0:print2("Trudge. Trudge."); break;
X  case 1:print2("The road goes ever onward...."); break;
X  }
X  switch(Country[Player.x][Player.y].current_terrain_type) {
X  case RIVER:
X    if ((Player.y < 6) && (Player.x > 20)) locprint("Star Lake.");
X    else if (Player.y < 41) {
X      if (Player.x < 10) locprint("Aerie River.");
X      else locprint("The Great Flood.");
X    }
X    else if (Player.x < 42) locprint("The Swamp Runs.");
X    else locprint("River Greenshriek.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X    }
X    break;
X  case ROAD:
X    locprint("A well-maintained road.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X    }
X    break;
X  case PLAINS:
X    locprint("A rippling sea of grass.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X      if (! gamestatusp(MOUNTED)) {
X	Time += 60;
X	hourly_check();
X      }
X    }
X    break;
X  case TUNDRA:
X    locprint("The Great Northern Wastes.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X      if (! gamestatusp(MOUNTED)) {
X	Time += 60;
X	hourly_check();
X      }
X    }
X    break;
X  case FOREST:
X    if (Player.y < 10) locprint("The Deepwood.");
X    else if (Player.y < 18) locprint("The Forest of Erelon.");
X    else if (Player.y < 46) locprint("The Great Forest.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      if (! gamestatusp(MOUNTED)) {
X	Time += 60;
X	hourly_check();
X      }
X    }
X    break;
X  case JUNGLE:
X    locprint("Greenshriek Jungle.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      if (! gamestatusp(MOUNTED)) {
X	Time += 60;
X	hourly_check();
X	Time += 60;
X	hourly_check();
X      }
X    }
X    break;
X  case DESERT:
X    locprint("The Waste of Time.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      if (! gamestatusp(MOUNTED)) {
X	Time += 60;
X	hourly_check();
X	Time += 60;
X	hourly_check();
X      }
X    }
X    break;
X  case MOUNTAINS:
X    if ((Player.y < 9) && (Player.x < 12))
X      locprint("The Magic Mountains");
X    else if ((Player.y < 9) && (Player.y > 2) && (Player.x < 40))
X      locprint("The Peaks of the Fist.");
X    else if (Player.x < 52)
X      locprint("The Rift Mountains.");
X    else locprint("Borderland Mountains.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      if (! gamestatusp(MOUNTED)) {
X	Time += 60;
X	hourly_check();
X	Time += 60;
X	hourly_check();
X	Time += 60;
X	hourly_check();
X      }
X    }
X    break;
X  case PASS:
X    locprint("A hidden pass.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X    }
X    break;
X  case CHAOS_SEA:
X    locprint("The Sea of Chaos.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X    }
X    l_chaos();
X    mprint("You have entered the sea of chaos...");
X    break;
X  case SWAMP:
X    locprint("The Loathly Swamp.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      Time += 60;
X      hourly_check();
X      if (! gamestatusp(MOUNTED)) {
X	Time += 60;
X	hourly_check();
X	Time += 60;
X	hourly_check();
X      }
X    }
X    break;
X  case CITY:
X    if (gamestatusp(LOST)) {
X      resetgamestatus(LOST); 
X      mprint("Well, I guess you know where you are now....");
X    }
X    locprint("Outside Rampart, the city.");
X    break;
X  case VILLAGE:
X    if (gamestatusp(LOST)) {
X      resetgamestatus(LOST); 
X      mprint("The village guards let you know where you are....");
X    }
X    locprint("Outside a small village.");
X    break;
X  case CAVES:
X    locprint("A deserted hillside.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X    }
X    mprint("You notice a concealed entrance into the hill.");
X    break;
X  case CASTLE:
X    locprint("Near a fortified castle.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X    }
X    mprint("The castle is hewn from solid granite. The drawbridge is down.");
X    break;
X  case TEMPLE:
X    switch(Country[Player.x][Player.y].aux) {
X    case ODIN: locprint("A rough-hewn granite temple."); break;
X    case SET: locprint("A black pyramidal temple made of sandstone."); break;
X    case ATHENA: locprint("A classical marble-columned temple."); break;
X    case HECATE: locprint("A temple of ebony adorned with ivory."); break;
X    case DRUID: locprint("A temple formed of living trees."); break;
X    case DESTINY: locprint("A temple of some mysterious blue crystal."); break;
X    }
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X    }
X    mprint("You notice an entrance conveniently at hand.");
X    break;
X  case MAGIC_ISLE:
X    locprint("A strange island in the midst of the Sea of Chaos.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X    }
X    mprint("There is a narrow causeway to the island from here.");
X    break;
X  case STARPEAK:
X    locprint("Star Peak.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X    }
X    mprint("The top of the mountain seems to glow with a allochroous aura.");
X    break;
X  case DRAGONLAIR:
X    locprint("A rocky chasm.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X    }
X    mprint("You are at a cave entrance from which you see the glint of gold.");
X    break;
X  case VOLCANO:
X    locprint("HellWell Volcano.");
X    if (takestime) {
X      Time += 60;
X      hourly_check();
X    }
X    mprint("A shimmer of heat lightning plays about the crater rim.");
X    break;
X  default:
X    locprint("I haven't any idea where you are!!!");
X    break;
X   }
X  outdoors_random_event();
X}
X
X
X
Xvoid countrysearch()
X{
X  int x,y;
X  Time+=60;
X  hourly_check();
X  for (x=Player.x-1;x<Player.x+2;x++)
X    for (y=Player.y-1;y<Player.y+2;y++)
X      if (inbounds(x,y)) {
X	if (Country[x][y].current_terrain_type !=
X	    Country[x][y].base_terrain_type) {
X	  mprint("Your search was fruitful!");
X	  Country[x][y].current_terrain_type=Country[x][y].base_terrain_type;
X	  mprint("You discovered:");
X	  mprint(countryid(Country[x][y].base_terrain_type));
X	}
X      }
X}
X
Xchar *countryid(terrain)
Xchar terrain;
X{
X  switch(terrain) {
X  case MOUNTAINS:
X    strcpy(Str1,"Almost impassable mountains");
X    break;
X  case PLAINS:
X    strcpy(Str1,"Seemingly endless plains");
X    break;
X  case TUNDRA:
X    strcpy(Str1,"A frosty stretch of tundra");
X    break;
X  case ROAD:
X    strcpy(Str1,"A paved highway");
X    break;
X  case PASS:
X    strcpy(Str1,"A secret mountain pass");
X    break;
X  case RIVER:
X    strcpy(Str1,"A rolling river");
X    break;
X  case CITY:
X    strcpy(Str1,"The city of Rampart");
X    break;
X  case VILLAGE:
X    strcpy(Str1,"A rural village");
X    break;
X  case FOREST:
X    strcpy(Str1,"A verdant forest");
X    break;
X  case JUNGLE:
X    strcpy(Str1,"A densely overgrown jungle");
X    break;
X  case SWAMP:
X    strcpy(Str1,"A swampy fen");
X    break;
X  case VOLCANO:
X    strcpy(Str1,"A huge active volcano");
X    break;
X  case CASTLE:
X    strcpy(Str1,"An imposing castle");
X    break;
X  case STARPEAK:
X    strcpy(Str1,"A mysterious mountain.");
X    break;
X  case DRAGONLAIR:
X    strcpy(Str1,"A cavern filled with treasure.");
X    break;
X  case MAGIC_ISLE:
X    strcpy(Str1,"An island emanating magic.");
X    break;
X  case CAVES:
X    strcpy(Str1,"A hidden cave entrance");
X    break;
X  case TEMPLE:
X    strcpy(Str1,"A neoclassical temple");
X    break;
X  case DESERT:
X    strcpy(Str1,"A sere desert");
X    break;
X  case CHAOS_SEA:
X    strcpy(Str1,"The Sea of Chaos");
X    break;
X  default:
X    strcpy(Str1,"I have no idea.");
X    break;
X  }
X  return(Str1);
X}
X
X/* i is the offset from CITYSITEBASE, not the actual constant */
Xchar *citysiteid(i)
Xint i;
X{
X  switch(i+CITYSITEBASE) {
X  case L_CHARITY:strcpy(Str4,"hospice"); break;
X  case L_ORDER:strcpy(Str4,"order of paladins"); break;
X  case L_ARMORER:strcpy(Str4,"armorer"); break;
X  case L_CLUB:strcpy(Str4,"explorers' club"); break;
X  case L_GYM:strcpy(Str4,"gymnasium"); break;
X  case L_THIEVES_GUILD:strcpy(Str4,"thieves' guild"); break;
X  case L_COLLEGE:strcpy(Str4,"collegium magii"); break;
X  case L_HEALER:strcpy(Str4,"healer"); break;
X  case L_CASINO:strcpy(Str4,"casino"); break;
X  case L_TAVERN:strcpy(Str4,"tavern"); break;
X  case L_MERC_GUILD:strcpy(Str4,"mercenary guild"); break;
X  case L_ALCHEMIST:strcpy(Str4,"alchemist"); break;
X  case L_SORCERORS:strcpy(Str4,"sorcerors' guild "); break;
X  case L_CASTLE:strcpy(Str4,"castle"); break;
X  case L_ARENA:strcpy(Str4,"arena"); break;
X  case L_DPW:strcpy(Str4,"department of public works"); break;
X  case L_LIBRARY:strcpy(Str4,"library"); break;
X  case L_PAWN_SHOP:strcpy(Str4,"pawn shop"); break;
X  case L_BANK:strcpy(Str4,"bank"); break;
X  case L_CONDO:strcpy(Str4,"condo"); break;
X  case L_ORACLE:strcpy(Str4,"oracle"); break;
X  case L_BROTHEL:strcpy(Str4,"brothel"); break;
X  case L_DINER:strcpy(Str4,"diner"); break;
X  case L_COMMANDANT:strcpy(Str4,"fast food"); break;
X  case L_CRAP:strcpy(Str4,"les crapuleux"); break;
X  case L_TEMPLE:strcpy(Str4,"temple"); break;
X  case L_COUNTRYSIDE:strcpy(Str4,"city gates"); break;
X  default:strcpy(Str4,"???"); break;
X  }
X  return(Str4);
X}
X
X
X
Xvoid expandsiteabbrevs(prefix)
Xchar prefix[80];
X{
X  int i,printed=FALSE;
X  
X  menuclear();
X  menuprint("\nPossible Sites:\n");
X  for (i=0;i<NUMCITYSITES;i++)
X    if (CitySiteList[i][0] && strprefix(prefix,citysiteid(i))) {
X      menuprint(citysiteid(i));
X      menuprint("\n");
X      printed = TRUE;
X    }
X  if (! printed)
X    menuprint("\nNo known sites match that prefix!");
X}
X
X
Xint expandsite(prefix)
Xchar prefix[80];
X{
X  int i,site,matched=0;
X  
X  for (i=0;i<NUMCITYSITES;i++)
X    if (CitySiteList[i][0] && strprefix(prefix,citysiteid(i))) {
X      site = i;
X      matched++;
X    }
X  if (matched==0) {
X    print3("No known locations match that prefix!");
X    return(ABORT);
X  }
X  else if (matched > 1) {
X    print3("That is an ambiguous abbreviation!");
X    return(ABORT);
X  }
X  else return(site);
X}
X
X
X
Xint parsecitysite()
X{
X  int site= -3,place=0;
X  char byte,prefix[80];
X
X  prefix[0]=0;
X
X  do {
X    byte = mgetc();
X    if ((byte >= 'A') && (byte <= 'Z')) {
X      maddch(byte+'a'-'A');
X      prefix[place] = byte+'a'-'A';
X      prefix[place+1] = 0;
X      place++;
X    }
X    else if ((byte == ' ') || ((byte >= 'a') && (byte <= 'z'))) {
X      maddch(byte);
X      prefix[place] = byte;
X      prefix[place+1] = 0;
X      place++;
X    }
X    else if ((byte == 8) || (byte == 127)) { /* ^h or delete */ 
X      prefix[place]=0;
X      if (place > 0) {
X	place--;
X	dobackspace();
X      }
X    }
X    else if (byte == '?') {
X      maddch(byte);
X      expandsiteabbrevs(prefix);
X      dobackspace();
X    }
X    else if (byte == '\n')
X      site = expandsite(prefix);
X    else if (byte == ESCAPE)
X      site = ABORT;
X  } while (site == -3);
X  xredraw();
X  return(site);
X}
X
X/* are there hostile monsters within 2 moves? */
Xint hostilemonstersnear()
X{
X  int i,j,hostile = FALSE;
X
X  for (i=Player.x-2;((i<Player.x+3)&&(! hostile));i++)
X    for (j=Player.y-2;((j<Player.y+3)&&(! hostile));j++)
X      if (inbounds(i,j))
X	if (Level->site[i][j].creature != NULL)
X	  hostile = m_statusp(Level->site[i][j].creature,HOSTILE);
X  
X  return(hostile);
X}
X
X/* random effects from some of stones in villages */  
X/* if alignment of stone is alignment of player, gets done sooner */
Xint stonecheck(alignment)
X{
X  int *stone,match=FALSE,cycle=FALSE,i;
X
X  if (alignment == 1) {
X    stone = &Lawstone;
X    match = Player.alignment > 0;
X  }
X  else if (alignment == -1) {
X    stone = &Chaostone;
X    match = Player.alignment < 0;
X  }
X  else {
X    stone = &Mindstone;
X    match = FALSE;
X  }
X  *stone += random_range(4) + (match ? random_range(4) : 0);
X  switch((*stone)++) {
X  case 0:case 2:case 4:case 6:case 8:case 10:case 12:case 14:case 16:case 18:
X  case 20:case 22:case 24:case 26:case 28:case 30:case 32:case 34:case 36:
X  case 38:case 40: print1("The stone glows grey.");
X    print2("Not much seems to happen this time."); 
X    (*stone)--;
X    break;
X  case 1: print1("The stone glows black"); 
X    print2("A burden has been removed from your shoulders.....");
X    print3("Your pack has disintegrated!");
X    for(i=0;i<MAXPACK;i++) 
X      if (Player.pack[i] != NULL) {
X	free((char *) Player.pack[i]);
X	Player.pack[i] = NULL;
X      }
X    Player.packptr = 0;
X    break;
X  case 3: print1("The stone glows microwave");
X    print2("A vortex of antimana spins about you!");
X    dispel(-1);
X    break;
X  case 5: print1("The stone glows infrared");
X    print2("A portal opens nearby and an obviously confused monster appears!");
X    summon(-1,-1);
X    break;
X  case 7: print1("The stone glows brick red");
X    print2("A gold piece falls from the heavens into your money pouch!");
X    Player.cash++;
X    break;
X  case 9: print1("The stone glows cherry red");
X    print2("A flush of warmth spreads through your body.");
X    augment(1);
X    break;
X  case 11: print1("The stone glows orange");
X    print2("A flux of energy blasts you!"); 
X    manastorm(Player.x,Player.y,random_range(Player.maxhp)+1);
X    break;
X  case 13: print1("The stone glows lemon yellow");
X    print2("You're surrounded by enemies! You begin to foam at the mouth.");
X    Player.status[BERSERK] += 10;
X    break;
X  case 15: print1("The stone glows yellow");
X    print2("Oh no! The DREADED AQUAE MORTIS!");
X    morewait();
X    print2("No, wait, it's just your imagination.");
X    break;
X  case 17: print1("The stone glows chartreuse");
X    print2("Your joints stiffen up.");
X    Player.agi -= 3;
X    break;
X  case 19: print1("The stone glows green");
X    print2("You come down with an acute case of Advanced Leprosy.");
X    Player.status[DISEASED] = 1100;
X    Player.hp = 1;
X    Player.dex -= 5;
X    break;
X  case 21: print1("The stone glows forest green");
X    print2("You feel wonderful!");
X    Player.status[HERO]+=10;
X    break;
X  case 23: print1("The stone glows cyan");
X    print2("You feel a strange twisting sensation....");
X    strategic_teleport(-1);
X    break;
X  case 25: print1("The stone glows blue");
X    morewait();
X    print1("You feel a tingle of an unearthly intuition:");
X    hint();
X    break;
X  case 27: print1("The stone glows navy blue");
X    print2("A sudden shock of knowledge overcomes you.");
X    morewait();
X    clearmsg();
X    identify(1);
X    knowledge(1);
X    break;
X  case 29: print1("The stone glows blue-violet");
X    print2("You feel forgetful.");
X    for(i=0;i<NUMSPELLS;i++) 
X      if (Spells[i].known) {
X	Spells[i].known = FALSE;
X	break;
X      }
X    break;
X  case 31: print1("The stone glows violet");
X    acquire(0);
X    break;
X  case 33: print1("The stone glows deep purple");
X    print2("You vanish.");
X    Player.status[INVISIBLE]+=10;
X    break;
X  case 35: print1("The stone glows ultraviolet");
X    print2("All your hair rises up on end.... A bolt of lightning hits you!");
X    p_damage(random_range(Player.maxhp),ELECTRICITY,"mystic lightning");
X    break;
X  case 37: print1("The stone glows roentgen");
X    print2("You feel more experienced.");
X    gain_experience((Player.level+1)*250);
X    break;
X  case 39: print1("The stone glows gamma"); 
X    print2("Your left hand shines silvery, and your right emits a golden aura."); 
X    enchant(1);
X    bless(1);
X    print3("Your hands stop glowing.");
X    break;
X  case 41:case 42:case 43:case 44:case 45:case 46:case 47:case 48:case 49:
X    print1("The stone glows cosmic!");
X    print2("The stone's energy field quiets for a moment...");
X    *stone = 50;
X    cycle = TRUE;
X    break;  
X  default: print1("The stone glows polka-dot (?!?!?!?)");
X    print2("You feel a strange twisting sensation....");
X    *stone = 0;
X    strategic_teleport(-1);
X    break;
X  }
X  calc_melee();
X  return(cycle);
X}
X
Xvoid alert_guards()
X{
X  int foundguard=FALSE;
X  pml ml;
X  for(ml=Level->mlist;ml!=NULL;ml=ml->next)
X    if (((ml->m->id == ML0+3) ||  /*guard*/
X	 ((ml->m->id == ML0+8) && (ml->m->aux2 == 15))) && /*justiciar*/
X	(ml->m->hp > 0)) {
X      foundguard=TRUE;
X      m_status_set(ml->m,AWAKE);
X      m_status_set(ml->m,HOSTILE);
X    }
X  if (foundguard) print2("You hear a whistle and the sound of running feet!");
X  if ((! foundguard) && (Current_Environment == E_CITY)) {
X    print2("The last member of the Order of Paladins dies....");
X    gain_experience(1000);
X    Player.alignment -= 250;
X    if (! gamestatusp(KILLED_LAWBRINGER)) {
X      morewait();
X      print1("A chime sounds from far away.... The sound grows stronger....");
X      print2("Suddenly the great shadowy form of the LawBringer appears over");
X      print3("the city. He points his finger at you....");
X      morewait();
X      print1("Cursed art thou, minion of chaos! May thy strength fail thee");
X      print2("in thy hour of need! You feel an unearthly shiver as the");
X      print3("LawBringer waves his palm across the city skies....");
X      Player.str /= 2;
X      morewait();
X      print1("You hear a bell tolling, and eerie moans all around you....");
X      print2("Suddenly, the image of the LawBringer is gone.");
X      print3("You hear a guardsman's whistle in the distance!");
X      morewait();
X      resurrect_guards();
X    }
X    else {
X      print1("The Order's magical defenses have dropped, and the");
X      print2("Legions of Chaos strike....");
X      morewait();
X      print1("The city shakes! An earthquake has struck!");
X      print2("Cracks open in the street, and a chasm engulfs the Order HQ!");
X      print3("Flames lick across the sky and you hear wild laughter....");
X      gain_experience(5000);
X      destroy_order();
X    }
X  }
X}
X
X
X/* can only occur when player is in city, so OK to use Level */
Xvoid destroy_order()
X{
X  int i,j;
X  setgamestatus(DESTROYED_ORDER);
X  if (Level != City) print1("Zounds! A Serious Mistake!");
X  else 
X    for(i=35;i<46;i++)
X      for(j=61;j<64;j++) {
X	Level->site[i][j].locchar = RUBBLE;
X	Level->site[i][j].p_locf = L_RUBBLE;
X	if (Level->site[i][j].creature != NULL)
X	  free((char *) Level->site[i][j].creature);
X	make_site_monster(i,j,ML2+6);
X	Level->site[i][j].creature->monstring = 
X	  salloc("ghost of a Paladin");
X	m_status_set(Level->site[i][j].creature,HOSTILE);
X      }
X}
X
X
X
Xint maneuvers()
X{
X  int m;
X  float times;
X  times = (Player.status[HASTED] ? 2.0 : 1.0);
X  times *= (Player.status[SLOWED] ? 0.5 : 1.0);
X
X  m = 2 + Player.level/7;
X  if (Player.rank[ARENA]) m++;
X  m = ((int) (m*times));
X  m = min(8,max(1,m));
X  
X  return(m);
X}
X
X/* for when haste runs out, etc. */
Xvoid default_maneuvers()
X{
X  int i;
X  morewait();
X  clearmsg();
X  print1("Warning, resetting your combat options to the default.");
X  print2("Use the 'F' command to select which options you prefer.");
X  morewait();
X  for(i=0;i<maneuvers();i+=2) {
X    Player.meleestr[i*2]='A';
X    Player.meleestr[(i+1)*2]='B';
X    Player.meleestr[((i+1)*2)+1]='C';
X    Player.meleestr[(i*2)+1]='C';
X  }
X  Player.meleestr[maneuvers()*2]=0;
X}
END_OF_FILE
if test 30108 -ne `wc -c <'oaux3.c'`; then
    echo shar: \"'oaux3.c'\" unpacked with wrong size!
fi
# end of 'oaux3.c'
fi
if test -f 'odate.h' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'odate.h'\"
else
echo shar: Extracting \"'odate.h'\" \(148 characters\)
sed "s/^X//" >'odate.h' <<'END_OF_FILE'
X/* omega copyright (C) by Laurence Raphael Brothers, 1987,1988,1989 */
X/* odate.h */
X
X#define LAST_OMEGA_EDIT_DATE "Thu May  4 14:38:33 EST 1989"
X
X
END_OF_FILE
if test 148 -ne `wc -c <'odate.h'`; then
    echo shar: \"'odate.h'\" unpacked with wrong size!
fi
# end of 'odate.h'
fi
if test -f 'osave.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'osave.c'\"
else
echo shar: Extracting \"'osave.c'\" \(20936 characters\)
sed "s/^X//" >'osave.c' <<'END_OF_FILE'
X/* omega copyright (c) 1987,1988,1989 by Laurence Raphael Brothers */
X/* osave.c */
X
X#include "oglob.h"
X
X/*Various functions for doing game saves and restores */
X/*The game remembers various player information, the city level,
Xthe country level, and the last or current dungeon level */
X
X/**************** SAVE FUNCTIONS */
X
X/* Checks to see if save file already exists.
X   Checks to see if save file can be opened for write.
X   The player, the city level, and the current dungeon level are saved.
X*/
X    
Xint save_game(compress,savestr)
Xint compress;
Xchar *savestr;
X{
X#ifdef MSDOS
X  int tmpdepth;
X#endif
X  int i,writeok=TRUE;
X  char cmd[80];
X#ifndef MSDOS
X  FILE *fd =fopen(savestr,"r");
X#else
X  FILE *fd =fopen(savestr,"rb");
X#endif
X  if (fd != NULL) {
X    mprint(" Overwrite old file?");
X    writeok = (ynq() == 'y');
X    fclose(fd);
X  }
X  if (writeok) {
X#ifndef MSDOS
X    fd=fopen(savestr,"w");
X#else
X    fd=fopen(savestr,"wb");
X#endif
X    if (fd == NULL) {
X      writeok = FALSE;
X      mprint(" Error opening file.");
X    }
X  }
X  if (! writeok)
X    print2("Save aborted.");
X  else {
X
X    print1("Saving Game....");
X
X    /* write the version number */
X    i = VERSION;
X    fwrite((char *)&i,sizeof(int),1,fd);
X    /* write game id to save file */
X
X    save_player(fd);
X    save_country(fd);
X#ifdef MSDOS
X    tmpdepth = Level->depth;
X    City = msdos_changelevel(Level,E_CITY,0);
X#endif
X    save_level(fd,City);
X    
X    if ((Current_Environment != E_CITY) &&
X	(Current_Environment != E_COUNTRYSIDE)) {
X      i = TRUE;
X      fwrite((char *)&i,sizeof(int),1,fd);
X#ifdef MSDOS
X      Level = msdos_changelevel(NULL,Current_Environment,tmpdepth);
X#endif
X      save_level(fd,Level);
X    }
X    else {
X      i = FALSE;
X      fwrite((char *)&i,sizeof(int),1,fd);
X    }
X    fclose(fd);
X    print1("Game Saved.");
X
X#ifdef COMPRESS_SAVE_FILES
X    if (compress) {
X      print2("Compressing Save File....");
X      strcpy(cmd,"compress ");
X      strcat(cmd,savestr);
X      system(cmd);
X      if (strlen(savestr) < 13) {
X	strcpy(cmd,"mv ");
X	strcat(cmd,savestr);
X	strcat(cmd,".Z ");
X	strcat(cmd,savestr);
X	system(cmd);
X      }
X    }
X#endif
X
X    morewait();
X    clearmsg();
X  }
X  return(writeok);
X}
X
X
X
X
X/* saves game on SIGHUP */
X/* no longer tries to compress, which hangs */
Xint signalsave()
X{
X  int i;
X#ifndef MSDOS
X  FILE *fd=fopen("Omega.Sav","w");
X#else
X  FILE *fd=fopen("Omega.Sav","wb");
X#endif
X  if (fd != NULL) {
X    /* write the version number */
X    i = VERSION;
X    fwrite((char *)&i,sizeof(int),1,fd);
X    /* write game id to save file */
X
X    save_player(fd);
X    save_country(fd);
X    save_level(fd,City);
X    
X    if ((Current_Environment != E_CITY) &&
X	(Current_Environment != E_COUNTRYSIDE)) {
X      i = TRUE;
X      fwrite((char *)&i,sizeof(int),1,fd);
X      save_level(fd,Level);
X    }
X    else {
X      i = FALSE;
X      fwrite((char *)&i,sizeof(int),1,fd);
X    }
X    fclose(fd);
X  }
X  exit(0);
X}
X
X
X    
X
X	
X
X
X
X
X
X/* also saves some globals like Level->depth... */
X
Xvoid save_player(fd)
XFILE *fd;
X{
X  int i,twohand;
X
X  twohand =
X    ((Player.possessions[O_READY_HAND] == Player.possessions[O_WEAPON_HAND])
X     && (Player.possessions[O_READY_HAND] != NULL));
X
X  /* Save random global state information */
X
X  fwrite((char *)&Player,sizeof(Player),1,fd);
X  fprintf(fd,"%s\n",Password);
X  fprintf(fd,"%s\n",Player.name);
X  fwrite((char *)CitySiteList,sizeof(CitySiteList),1,fd);
X  fwrite((char *)&GameStatus,sizeof(long),1,fd);
X  fwrite((char *)&Current_Environment,sizeof(int),1,fd);
X  fwrite((char *)&Last_Environment,sizeof(int),1,fd);
X  fwrite((char *)&Current_Dungeon,sizeof(int),1,fd);
X  fwrite((char *)&Villagenum,sizeof(int),1,fd);
X  fwrite((char *)&Verbosity,sizeof(char),1,fd);
X#ifndef MSDOS
X  fwrite((char *)&Time,sizeof(int),1,fd);
X#else
X  fwrite((char *)&Time,sizeof(long),1,fd);
X#endif
X  fwrite((char *)&Tick,sizeof(int),1,fd);
X  fwrite((char *)&Searchnum,sizeof(int),1,fd);
X  fwrite((char *)&Phase,sizeof(int),1,fd);
X  fwrite((char *)&Date,sizeof(int),1,fd);
X  fwrite((char *)&Spellsleft,sizeof(int),1,fd);
X  fwrite((char *)&SymbolUseHour,sizeof(int),1,fd);
X  fwrite((char *)&ViewHour,sizeof(int),1,fd);
X  fwrite((char *)&HelmHour,sizeof(int),1,fd);
X  fwrite((char *)&Constriction,sizeof(int),1,fd);
X  fwrite((char *)&Blessing,sizeof(int),1,fd);
X  fwrite((char *)&LastDay,sizeof(int),1,fd);
X  fwrite((char *)&RitualHour,sizeof(int),1,fd);
X  fwrite((char *)&Lawstone,sizeof(int),1,fd);
X  fwrite((char *)&Chaostone,sizeof(int),1,fd);
X  fwrite((char *)&Mindstone,sizeof(int),1,fd);
X  fwrite((char *)&Arena_Opponent,sizeof(int),1,fd);
X  fwrite((char *)&Imprisonment,sizeof(int),1,fd);
X#ifndef MSDOS
X  fwrite((char *)&Gymcredit,sizeof(int),1,fd);
X#else
X  fwrite((char *)&Gymcredit,sizeof(long),1,fd);
X#endif
X#ifndef MSDOS
X  fwrite((char *)&Balance,sizeof(int),1,fd);
X#else
X  fwrite((char *)&Balance,sizeof(long),1,fd);
X#endif
X  fwrite((char *)&StarGemUse,sizeof(int),1,fd);
X  fwrite((char *)&HiMagicUse,sizeof(int),1,fd);
X  fwrite((char *)&HiMagic,sizeof(int),1,fd);
X#ifndef MSDOS
X  fwrite((char *)&FixedPoints,sizeof(int),1,fd);
X#else
X  fwrite((char *)&FixedPoints,sizeof(long),1,fd);
X#endif
X  fwrite((char *)&LastCountryLocX,sizeof(int),1,fd);
X  fwrite((char *)&LastCountryLocY,sizeof(int),1,fd);
X  fwrite((char *)&LastTownLocX,sizeof(int),1,fd);
X  fwrite((char *)&LastTownLocY,sizeof(int),1,fd);
X  fwrite((char *)&Pawndate,sizeof(int),1,fd);
X
X  fwrite((char *)&twohand,sizeof(int),1,fd);
X
X  fwrite((char *)Spells,sizeof(Spells),1,fd);
X
X  fwrite((char *)&Command_Duration,sizeof(Command_Duration),1,fd);
X  fwrite((char *)&Precipitation,sizeof(Precipitation),1,fd);
X  fwrite((char *)&Lunarity,sizeof(Lunarity),1,fd);
X  fwrite((char *)&ZapHour,sizeof(ZapHour),1,fd);
X  fwrite((char *)&RitualRoom,sizeof(RitualRoom),1,fd);
X
X  /* High score stuff */
X  fwrite((char *)&Shadowlordbehavior,sizeof(Shadowlordbehavior),1,fd);
X  fwrite((char *)&Archmagebehavior,sizeof(Archmagebehavior),1,fd);
X  fwrite((char *)&Primebehavior,sizeof(Primebehavior),1,fd);
X  fwrite((char *)&Justiciarbehavior,sizeof(Justiciarbehavior),1,fd);
X  fwrite((char *)&Commandantbehavior,sizeof(Commandantbehavior),1,fd);
X  fwrite((char *)&Chaoslordbehavior,sizeof(Chaoslordbehavior),1,fd);
X  fwrite((char *)&Lawlordbehavior,sizeof(Lawlordbehavior),1,fd);
X  fwrite((char *)&Championbehavior,sizeof(Championbehavior),1,fd);
X  fwrite((char *)Priestbehavior,sizeof(Priestbehavior),1,fd);
X  fwrite((char *)&Hibehavior,sizeof(Hibehavior),1,fd);
X  fwrite((char *)&Dukebehavior,sizeof(Dukebehavior),1,fd);
X  fwrite((char *)Shadowlord,sizeof(Shadowlord),1,fd);
X  fwrite((char *)Archmage,sizeof(Archmage),1,fd);
X  fwrite((char *)Prime,sizeof(Prime),1,fd);
X  fwrite((char *)Commandant,sizeof(Commandant),1,fd);
X  fwrite((char *)Duke,sizeof(Duke),1,fd);
X  fwrite((char *)Champion,sizeof(Champion),1,fd);
X  fwrite((char *)Priest,sizeof(Priest),1,fd);
X  fwrite((char *)Hiscorer,sizeof(Hiscorer),1,fd);
X  fwrite((char *)Hidescrip,sizeof(Hidescrip),1,fd);
X  fwrite((char *)Chaoslord,sizeof(Chaoslord),1,fd);
X  fwrite((char *)Lawlord,sizeof(Lawlord),1,fd);
X  fwrite((char *)Justiciar,sizeof(Justiciar),1,fd);
X  fwrite((char *)&Shadowlordlevel,sizeof(Shadowlordlevel),1,fd);
X  fwrite((char *)&Archmagelevel,sizeof(Archmagelevel),1,fd);
X  fwrite((char *)&Primelevel,sizeof(Primelevel),1,fd);
X  fwrite((char *)&Commandantlevel,sizeof(Commandantlevel),1,fd);
X  fwrite((char *)&Dukelevel,sizeof(Dukelevel),1,fd);
X  fwrite((char *)&Championlevel,sizeof(Championlevel),1,fd);
X  fwrite((char *)Priestlevel,sizeof(Priestlevel),1,fd);
X  fwrite((char *)&Hiscore,sizeof(Hiscore),1,fd);
X  fwrite((char *)&Hilevel,sizeof(Hilevel),1,fd);
X  fwrite((char *)&Justiciarlevel,sizeof(Justiciarlevel),1,fd);
X  fwrite((char *)&Chaoslordlevel,sizeof(Chaoslordlevel),1,fd);
X  fwrite((char *)&Lawlordlevel,sizeof(Lawlordlevel),1,fd);
X  fwrite((char *)&Chaos,sizeof(Chaos),1,fd);
X  fwrite((char *)&Law,sizeof(Law),1,fd);
X
X  /* stuff which used to be statics */
X  fwrite((char *)&twiddle,sizeof(twiddle),1,fd);
X  fwrite((char *)&saved,sizeof(saved),1,fd);
X  fwrite((char *)&onewithchaos,sizeof(onewithchaos),1,fd);
X  fwrite((char *)&club_hinthour,sizeof(club_hinthour),1,fd);
X  fwrite((char *)&winnings,sizeof(winnings),1,fd);
X  fwrite((char *)&tavern_hinthour,sizeof(tavern_hinthour),1,fd);
X  fwrite((char *)scroll_ids,sizeof(scroll_ids),1,fd);
X  fwrite((char *)potion_ids,sizeof(potion_ids),1,fd);
X  fwrite((char *)stick_ids,sizeof(stick_ids),1,fd);
X  fwrite((char *)ring_ids,sizeof(ring_ids),1,fd);
X  fwrite((char *)cloak_ids,sizeof(cloak_ids),1,fd);
X  fwrite((char *)boot_ids,sizeof(boot_ids),1,fd);
X  fwrite((char *)deepest,sizeof(deepest),1,fd);
X
X  /* Save player possessions */
X
X  for(i=0;i<MAXITEMS;i++) save_item(fd,Player.possessions[i]);
X  for(i=0;i<MAXPACK;i++) save_item(fd,Player.pack[i]);
X  for(i=0;i<PAWNITEMS;i++) save_item(fd,Pawnitems[i]);
X
X  /* Save items in condo vault */
X  save_itemlist(fd,Condoitems);
X
X  /* Save player item knowledge */
X  for (i=0;i<TOTALITEMS;i++)
X    fwrite((char *)&(Objects[i].known),sizeof(Objects[i].known),1,fd);
X}
X
X
X/* Save whatever is pointed to by level */
Xvoid save_level(fd,level)
XFILE *fd;
Xplv level;
X{
X  int i,j;
X
X  fwrite((char *)level,sizeof(levtype),1,fd);
X#ifdef MSDOS
X  for (i = 0; i < MAXWIDTH; i++)
X      fwrite((char *)level->site[i],MAXLENGTH * sizeof(loctype),1,fd);
X#endif
X  save_monsters(fd,level->mlist);
X  for(i=0;i<MAXWIDTH;i++)
X    for(j=0;j<MAXLENGTH;j++)
X      save_itemlist(fd,level->site[i][j].things);
X}
X
X
Xvoid save_monsters(fd,ml)
XFILE *fd;
Xpml ml;
X{
X  pml tml;
X  int nummonsters=0;
X
X  /* First count monsters */
X  for(tml=ml;tml!=NULL;tml=tml->next) 
X    if (tml->m->hp > 0) nummonsters++;
X
X  fwrite((char *)&nummonsters,sizeof(int),1,fd);
X
X  /* Now save monsters */
X  for(tml=ml;tml!=NULL;tml=tml->next) {
X    if (tml->m->hp > 0) {
X      fwrite((char *)tml->m,sizeof(montype),1,fd);
X      fprintf(fd,"%s\n",tml->m->monstring);
X      save_itemlist(fd,tml->m->possessions);
X    }
X  }
X}
X
X
X/* Save o unless it's null, then save a null item instead */
Xvoid save_item(fd,o)
XFILE *fd;
Xpob o;
X{
X  objtype nullobject;
X  nullobject.id = -1;
X  if (o == NULL) {
X    fwrite((char *)&nullobject,sizeof(objtype),1,fd);
X    fprintf(fd,"Null Object. Report if you see this!\n");
X  }
X  else {
X    fwrite((char *)o,sizeof(objtype),1,fd);
X    fprintf(fd,"%s\n",o->truename);
X  }
X}
X
Xvoid save_itemlist(fd,ol)
XFILE *fd;
Xpol ol;
X{
X  int numitems = 0;
X  pol tol;
X  for(tol=ol;tol!=NULL;tol=tol->next) numitems++;
X  fwrite((char *)&numitems,sizeof(int),1,fd);
X  for(tol=ol;tol!=NULL;tol=tol->next) 
X    save_item(fd,tol->thing);
X}
X
X
Xvoid save_country(fd)
XFILE *fd;
X{
X  fwrite((char *)Country,sizeof(Country),1,fd);
X}
X
X
X
X
X/* read player data, city level, dungeon level,
X   check on validity of save file, etc.
X   return TRUE if game restored, FALSE otherwise */
X
Xint restore_game(savestr)
Xchar *savestr;
X{
X  int i,version; 
X  char cmd[80];
X  FILE *fd;
X
X
X#ifdef COMPRESS_SAVE_FILES
X  print1("Uncompressing Save File....");
X  if (strlen(savestr) < 13) {
X    strcpy(cmd,"mv ");
X    strcat(cmd,savestr);
X    strcat(cmd," ");
X    strcat(savestr,".Z");
X    strcat(cmd,savestr);
X    system(cmd);
X  }
X  strcpy(cmd,"uncompress ");
X  strcat(cmd,savestr);
X  system(cmd);
X  print2("Save file uncompressed.");
X  morewait();
X  if ((savestr[strlen(savestr)-1] == 'Z') &&
X      (savestr[strlen(savestr)-2] == '.'))
X    savestr[strlen(savestr)-2] = 0;
X#endif
X  
X#ifndef MSDOS
X  fd = fopen(savestr,"r");
X#else
X  fd = fopen(savestr,"rb");
X#endif
X
X  if (fd == NULL) {
X    print1("Error restoring game -- aborted.");
X    print2("File name was: ");
X    nprint2(savestr);
X    morewait();
X    return(FALSE);
X  }
X  else {
X    print1("Restoring...");
X
X    fread((char *)&version,sizeof(int),1,fd);
X
X    if (VERSION != version) {
X      print2(" Sorry, I can't restore an outdated save file!");
X      morewait();
X      return(FALSE);
X    }
X    restore_player(fd);
X    restore_country(fd);
X    restore_level(fd); /* the city level */
X    fread((char *)&i,sizeof(int),1,fd);
X    if (i == TRUE)
X#ifndef MSDOS
X      restore_level(fd);
X#else
X    {
X      msdos_changelevel(Level,0,-1);
X      restore_level(fd);
X    }
X#endif
X    print3("Restoration complete.");
X    ScreenOffset = -1000;
X    screencheck(Player.y);
X    drawvision(Player.x,Player.y);
X    setgamestatus(SKIP_MONSTERS);
X    dataprint();
X    showflags();
X    fclose(fd);
X    return(TRUE);
X  }
X}
X
X
X
Xvoid restore_player(fd)
XFILE *fd;
X{
X  int i,twohand;
X  fread((char *)&Player,sizeof(Player),1,fd);
X  filescanstring(fd,Password);
X  filescanstring(fd,Player.name);
X  fread((char *)CitySiteList,sizeof(CitySiteList),1,fd);
X  fread((char *)&GameStatus,sizeof(long),1,fd);
X  fread((char *)&Current_Environment,sizeof(int),1,fd);
X  fread((char *)&Last_Environment,sizeof(int),1,fd);
X  fread((char *)&Current_Dungeon,sizeof(int),1,fd);
X  fread((char *)&Villagenum,sizeof(int),1,fd);
X  switch(Current_Dungeon) {
X  case E_ASTRAL: MaxDungeonLevels = ASTRALLEVELS; break;
X  case E_SEWERS: MaxDungeonLevels = SEWERLEVELS; break;
X  case E_CASTLE: MaxDungeonLevels = CASTLELEVELS; break;
X  case E_CAVES: MaxDungeonLevels = CAVELEVELS; break;
X  case E_VOLCANO: MaxDungeonLevels = VOLCANOLEVELS; break;
X  }
X  fread((char *)&Verbosity,sizeof(char),1,fd);
X#ifndef MSDOS
X  fread((char *)&Time,sizeof(int),1,fd);
X#else
X  fread((char *)&Time,sizeof(long),1,fd);
X#endif
X  fread((char *)&Tick,sizeof(int),1,fd);
X  fread((char *)&Searchnum,sizeof(int),1,fd);
X  fread((char *)&Phase,sizeof(int),1,fd);
X  fread((char *)&Date,sizeof(int),1,fd);
X  fread((char *)&Spellsleft,sizeof(int),1,fd);
X  fread((char *)&SymbolUseHour,sizeof(int),1,fd);
X  fread((char *)&ViewHour,sizeof(int),1,fd);
X  fread((char *)&HelmHour,sizeof(int),1,fd);
X  fread((char *)&Constriction,sizeof(int),1,fd);
X  fread((char *)&Blessing,sizeof(int),1,fd);
X  fread((char *)&LastDay,sizeof(int),1,fd);
X  fread((char *)&RitualHour,sizeof(int),1,fd);
X  fread((char *)&Lawstone,sizeof(int),1,fd);
X  fread((char *)&Chaostone,sizeof(int),1,fd);
X  fread((char *)&Mindstone,sizeof(int),1,fd);
X  fread((char *)&Arena_Opponent,sizeof(int),1,fd);
X  fread((char *)&Imprisonment,sizeof(int),1,fd);
X#ifndef MSDOS
X  fread((char *)&Gymcredit,sizeof(int),1,fd);
X#else
X  fread((char *)&Gymcredit,sizeof(long),1,fd);
X#endif
X#ifndef MSDOS
X  fread((char *)&Balance,sizeof(int),1,fd);
X#else
X  fread((char *)&Balance,sizeof(long),1,fd);
X#endif
X  fread((char *)&StarGemUse,sizeof(int),1,fd);
X  fread((char *)&HiMagicUse,sizeof(int),1,fd);
X  fread((char *)&HiMagic,sizeof(int),1,fd);
X#ifndef MSDOS
X  fread((char *)&FixedPoints,sizeof(int),1,fd);
X#else
X  fread((char *)&FixedPoints,sizeof(long),1,fd);
X#endif
X  fread((char *)&LastCountryLocX,sizeof(int),1,fd);
X  fread((char *)&LastCountryLocY,sizeof(int),1,fd);
X  fread((char *)&LastTownLocX,sizeof(int),1,fd);
X  fread((char *)&LastTownLocY,sizeof(int),1,fd);
X  fread((char *)&Pawndate,sizeof(int),1,fd);
X
X  fread((char *)&twohand,sizeof(int),1,fd);
X
X  fread((char *)Spells,sizeof(Spells),1,fd);
X
X  fread((char *)&Command_Duration,sizeof(Command_Duration),1,fd);
X  fread((char *)&Precipitation,sizeof(Precipitation),1,fd);
X  fread((char *)&Lunarity,sizeof(Lunarity),1,fd);
X  fread((char *)&ZapHour,sizeof(ZapHour),1,fd);
X  fread((char *)&RitualRoom,sizeof(RitualRoom),1,fd);
X
X  /* High score stuff */
X  fread((char *)&Shadowlordbehavior,sizeof(Shadowlordbehavior),1,fd);
X  fread((char *)&Archmagebehavior,sizeof(Archmagebehavior),1,fd);
X  fread((char *)&Primebehavior,sizeof(Primebehavior),1,fd);
X  fread((char *)&Justiciarbehavior,sizeof(Justiciarbehavior),1,fd);
X  fread((char *)&Commandantbehavior,sizeof(Commandantbehavior),1,fd);
X  fread((char *)&Chaoslordbehavior,sizeof(Chaoslordbehavior),1,fd);
X  fread((char *)&Lawlordbehavior,sizeof(Lawlordbehavior),1,fd);
X  fread((char *)&Championbehavior,sizeof(Championbehavior),1,fd);
X  fread((char *)Priestbehavior,sizeof(Priestbehavior),1,fd);
X  fread((char *)&Hibehavior,sizeof(Hibehavior),1,fd);
X  fread((char *)&Dukebehavior,sizeof(Dukebehavior),1,fd);
X  fread((char *)Shadowlord,sizeof(Shadowlord),1,fd);
X  fread((char *)Archmage,sizeof(Archmage),1,fd);
X  fread((char *)Prime,sizeof(Prime),1,fd);
X  fread((char *)Commandant,sizeof(Commandant),1,fd);
X  fread((char *)Duke,sizeof(Duke),1,fd);
X  fread((char *)Champion,sizeof(Champion),1,fd);
X  fread((char *)Priest,sizeof(Priest),1,fd);
X  fread((char *)Hiscorer,sizeof(Hiscorer),1,fd);
X  fread((char *)Hidescrip,sizeof(Hidescrip),1,fd);
X  fread((char *)Chaoslord,sizeof(Chaoslord),1,fd);
X  fread((char *)Lawlord,sizeof(Lawlord),1,fd);
X  fread((char *)Justiciar,sizeof(Justiciar),1,fd);
X  fread((char *)&Shadowlordlevel,sizeof(Shadowlordlevel),1,fd);
X  fread((char *)&Archmagelevel,sizeof(Archmagelevel),1,fd);
X  fread((char *)&Primelevel,sizeof(Primelevel),1,fd);
X  fread((char *)&Commandantlevel,sizeof(Commandantlevel),1,fd);
X  fread((char *)&Dukelevel,sizeof(Dukelevel),1,fd);
X  fread((char *)&Championlevel,sizeof(Championlevel),1,fd);
X  fread((char *)Priestlevel,sizeof(Priestlevel),1,fd);
X  fread((char *)&Hiscore,sizeof(Hiscore),1,fd);
X  fread((char *)&Hilevel,sizeof(Hilevel),1,fd);
X  fread((char *)&Justiciarlevel,sizeof(Justiciarlevel),1,fd);
X  fread((char *)&Chaoslordlevel,sizeof(Chaoslordlevel),1,fd);
X  fread((char *)&Lawlordlevel,sizeof(Lawlordlevel),1,fd);
X  fread((char *)&Chaos,sizeof(Chaos),1,fd);
X  fread((char *)&Law,sizeof(Law),1,fd);
X
X  /* stuff which used to be statics */
X  fread((char *)&twiddle,sizeof(twiddle),1,fd);
X  fread((char *)&saved,sizeof(saved),1,fd);
X  fread((char *)&onewithchaos,sizeof(onewithchaos),1,fd);
X  fread((char *)&club_hinthour,sizeof(club_hinthour),1,fd);
X  fread((char *)&winnings,sizeof(winnings),1,fd);
X  fread((char *)&tavern_hinthour,sizeof(tavern_hinthour),1,fd);
X  fread((char *)scroll_ids,sizeof(scroll_ids),1,fd);
X  fread((char *)potion_ids,sizeof(potion_ids),1,fd);
X  fread((char *)stick_ids,sizeof(stick_ids),1,fd);
X  fread((char *)ring_ids,sizeof(ring_ids),1,fd);
X  fread((char *)cloak_ids,sizeof(cloak_ids),1,fd);
X  fread((char *)boot_ids,sizeof(boot_ids),1,fd);
X  fread((char *)deepest,sizeof(deepest),1,fd);
X
X  /* Set up the strings for the id's */
X  inititem(0);
X
X  for(i=0;i<MAXITEMS;i++) 
X    Player.possessions[i] = restore_item(fd);
X  if (twohand) {
X    free((char *)Player.possessions[O_READY_HAND]);
X    Player.possessions[O_READY_HAND] = 
X      Player.possessions[O_WEAPON_HAND];
X  }
X  for(i=0;i<MAXPACK;i++) 
X    Player.pack[i] = restore_item(fd);
X  for(i=0;i<PAWNITEMS;i++) 
X    Pawnitems[i] = restore_item(fd);
X  Condoitems = restore_itemlist(fd);
X  for (i=0;i<TOTALITEMS;i++) 
X    fread((char *)&(Objects[i].known),sizeof(Objects[i].known),1,fd);
X  calc_melee();
X}
X
X
X
Xpob restore_item(fd)
XFILE *fd;
X{
X  char tempstr[80];
X  pob obj = ((pob) malloc(sizeof(objtype)));
X  fread((char *)obj,sizeof(objtype),1,fd);
X  filescanstring(fd,tempstr);
X  obj->truename = salloc(tempstr);
X  if (obj->id < 0) {
X    free((char *) obj);
X    return(NULL);
X  }
X  else {
X    obj->objstr = Objects[obj->id].objstr;
X    obj->cursestr = Objects[obj->id].cursestr;
X    return(obj);
X  }
X}
X
Xpol restore_itemlist(fd)
XFILE *fd;
X{
X  pol ol=NULL,cur=NULL,new=NULL;
X  int i,numitems,firsttime=TRUE;
X  fread((char *)&numitems,sizeof(int),1,fd);
X  for(i=0;i<numitems;i++) {
X    new = ((pol) malloc(sizeof(oltype)));
X    new->thing = restore_item(fd);
X    new->next = NULL;
X    if (firsttime==TRUE) {
X      ol = cur = new;
X      firsttime = FALSE;
X    }
X    else {
X      cur->next = new;
X      cur = new;
X    }
X  }
X  return(ol);
X}
X
X
X
X
X
X
X
X
Xvoid restore_level(fd)
XFILE *fd;
X{
X  int i,j;
X
X#ifndef MSDOS
X  Level = ((plv) malloc(sizeof(levtype)));
X  
X  fread((char *)Level,sizeof(levtype),1,fd);
X#else
X  plc *tmp = (plc *)malloc(MAXWIDTH * sizeof(plc));
X
X  Level = &TheLevel;
X  for (i = 0; i < MAXWIDTH; i++)
X    tmp[i] = Level->site[i];
X  fread((char *)Level,sizeof(levtype),1,fd);
X  for (i = 0; i < MAXWIDTH; i++)
X    fread((char *)(Level->site[i] = tmp[i]),MAXLENGTH * sizeof(loctype),1,fd);
X  free(tmp);
X#endif
X
X  Level->next = NULL;
X
X  restore_monsters(fd,Level);
X  for(i=0;i<MAXWIDTH;i++)
X    for(j=0;j<MAXLENGTH;j++)
X      Level->site[i][j].things = restore_itemlist(fd);
X  if (Level->environment == E_CITY) City = Level;
X  else if (Level->environment == Current_Dungeon) Dungeon = Level;
X}
X
X
X
X
Xvoid restore_monsters(fd,level)
XFILE *fd;
Xplv level;
X{
X  pml ml=NULL;
X  int i,nummonsters;
X  char tempstr[80];
X
X  level->mlist = NULL;
X
X  fread((char *)&nummonsters,sizeof(int),1,fd);
X  
X  for(i=0;i<nummonsters;i++) {
X    ml = ((pml) malloc(sizeof(mltype)));
X    ml->m = ((pmt) malloc(sizeof(montype)));
X    ml->next = NULL;
X    fread((char *)ml->m,sizeof(montype),1,fd);
X    filescanstring(fd,tempstr);
X    ml->m->monstring = salloc(tempstr);
X    ml->m->corpsestr = salloc(Monsters[ml->m->id].corpsestr);
X    ml->m->meleestr = salloc(Monsters[ml->m->id].meleestr);
X    level->site[ml->m->x][ml->m->y].creature = ml->m;
X    ml->m->possessions = restore_itemlist(fd);
X    ml->next = level->mlist;
X    level->mlist = ml;
X  }
X}
X
X
X
Xvoid restore_country(fd)
XFILE *fd;
X{
X  fread((char *)Country,sizeof(Country),1,fd);
X}
END_OF_FILE
if test 20936 -ne `wc -c <'osave.c'`; then
    echo shar: \"'osave.c'\" unpacked with wrong size!
fi
# end of 'osave.c'
fi
echo shar: End of archive 6 \(of 20\).
cp /dev/null ark6isdone
MISSING=""
for I in 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 ; do
    if test ! -f ark${I}isdone ; then
	MISSING="${MISSING} ${I}"
    fi
done
if test "${MISSING}" = "" ; then
    echo You have unpacked all 20 archives.
    rm -f ark[1-9]isdone ark[1-9][0-9]isdone
else
    echo You still need to unpack the following archives:
    echo "        " ${MISSING}
fi
##  End of shell archive.
exit 0