[comp.sources.games] v07i088: NetHack3 - display oriented dungeons & dragons

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

Submitted-by: Izchak Miller <izchak@linc.cis.upenn.edu>
Posting-number: Volume 7, Issue 88
Archive-name: NetHack3/Part33



#! /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 33 (of 38)."
# Contents:  amiga/amimenu.c auxil/help include/pcconf.h include/rm.h
#   src/decl.c src/getline.c src/mail.c src/topl.c src/wield.c
# Wrapped by billr@saab on Sun Jul 23 21:33:18 1989
PATH=/bin:/usr/bin:/usr/ucb ; export PATH
if test -f 'amiga/amimenu.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'amiga/amimenu.c'\"
else
echo shar: Extracting \"'amiga/amimenu.c'\" \(5924 characters\)
sed "s/^X//" >'amiga/amimenu.c' <<'END_OF_FILE'
X/*
X *  amimenu.c	    (C) Copyright 1989 by Olaf Seibert (KosmoSoft)
X *
X *  Originally by John Toebes.
X */
X/* NetHack may be freely redistributed.  See license for details. */
X
X#define TEXT(nam,str) \
Xstatic struct IntuiText nam = \
X  {0,1,JAM2,0,0,(struct TextAttr*)NULL,(UBYTE*)str,(struct IntuiText*)NULL}
X
X	/* Commands */
X	TEXT(T_HELP,  "?   Display help");
X	TEXT(T_O,     "O   Set options");
X	TEXT(T_SHELL, "!   AmigaDos commands");
X	TEXT(T_v,     "v   Version number");
X	TEXT(T_CR,    "^R  Redraw screen");
X	TEXT(T_CP,    "^P  Repeat last message");
X	TEXT(T_Q,     "Q   Quit game");
X	TEXT(T_S,     "S   Save the game");
X
X	/* Inventory */
X	TEXT(T_i,     "i   Inventory");
X	TEXT(T_p,     "p   Pay your bill");
X	TEXT(T_d,     "d   Drop an object");
X	TEXT(T_D,     "D   Drop several things");
X	TEXT(T_COMMA, ",   Pickup an object");
X	TEXT(T_AT,    "@   Toggle pickup");
X	TEXT(T_SLASH, "/   Identify something");
X	TEXT(T_C,     "C   Christen a monster");
X
X	/* Actions */
X	TEXT(T_a,     "a   Apply/use something");
X	TEXT(T_e,     "e   Eat something");
X	TEXT(T_q,     "q   Quaff a potion");
X	TEXT(T_r,     "r   Read a scroll");
X	TEXT(T_t,     "t   Throw/shoot weapon");
X	TEXT(T_z,     "z   Zap a wand");
X	TEXT(T_Z,     "Z   Cast a spell");
X	TEXT(T_X,     "X   Learn a spell");
X	TEXT(T_HASH,  "#   Extended command");
X
X	/* Preparations */
X	TEXT(T_w,     "w   Wield a weapon");
X	TEXT(T_P,     "P   Put on ring");
X	TEXT(T_R,     "R   Remove ring");
X	TEXT(T_T,     "T   Take off armor");
X	TEXT(T_W,     "W   Wear armor");
X	TEXT(T_WPN,   ")   Current weapon");
X	TEXT(T_ARMOR, "[   Current armor");
X	TEXT(T_RING,  "=   Current rings");
X	TEXT(T_AMU,  "\"   Current amulet");
X	TEXT(T_TOOL,  "(   Current tools");
X
X	/* Movement */
X	TEXT(T_o,     "o   Open door");
X	TEXT(T_c,     "c   Close door");
X	TEXT(T_KICK,  "^D  Kick door");
X	TEXT(T_s,     "s   Search");
X	TEXT(T_UP,    "<   Go up stairs");
X	TEXT(T_DOWN,  ">   Go down stairs");
X	TEXT(T_CT,    "^T  Teleport");
X	TEXT(T_WAIT,  ".   Wait a moment");
X	TEXT(T_E,     "E   Engrave msg on floor");
X
X#define IFLAGS ITEMENABLED|ITEMTEXT|HIGHCOMP
X#define IDATA(cmd,str,off) 0,off,WDT,9,IFLAGS,0,(APTR)&str,NULL,cmd,(struct MenuItem*)NULL,0
X
X/* Commands */
X
X#undef	WDT
X#define WDT 184
X
Xstatic struct MenuItem cmdsub[] = {
X    { &cmdsub[1], IDATA('?', T_HELP,   0) }, /*   Display help */
X    { &cmdsub[2], IDATA('O', T_O,     10) }, /*   Set options */
X    { &cmdsub[3], IDATA('!', T_SHELL, 20) }, /*   AmigaDos commands */
X    { &cmdsub[4], IDATA('v', T_v,     30) }, /*   Version number */
X    { &cmdsub[5], IDATA(022, T_CR,    40) }, /*R  Redraw screen */
X    { &cmdsub[6], IDATA(020 ,T_CP,    50) }, /*P  Repeat last message */
X    { &cmdsub[7], IDATA('Q', T_Q,     60) }, /*   Quit game */
X    { NULL,	  IDATA('S', T_S,     70) }, /*   Save the game */
X};
X
X/* Inventory */
X
X#undef	WDT
X#define WDT 200
X
Xstatic struct MenuItem invsub[] = {
X    { &invsub[1], IDATA('i', T_i,      0) }, /*   Inventory */
X    { &invsub[2], IDATA('p', T_p,     10) }, /*   Pay your bill */
X    { &invsub[3], IDATA('d', T_d,     20) }, /*   Drop an object */
X    { &invsub[4], IDATA('D', T_D,     30) }, /*   Drop several things */
X    { &invsub[5], IDATA(',', T_COMMA, 40) }, /*   Pickup an object */
X    { &invsub[6], IDATA('/', T_SLASH, 50) }, /*   Identify something */
X    { NULL,	  IDATA('C', T_C,     60) }, /*   Christen a monster */
X};
X
X/* Actions */
X
X#undef	WDT
X#define WDT 184
X
Xstatic struct MenuItem actsub[] = {
X    { &actsub[1], IDATA('a', T_a,     0) }, /*   Apply/use something */
X    { &actsub[2], IDATA('e', T_e,    10) }, /*   Eat something */
X    { &actsub[3], IDATA('q', T_q,    20) }, /*   Quaff a potion */
X    { &actsub[4], IDATA('r', T_r,    30) }, /*   Read a scroll */
X    { &actsub[5], IDATA('t', T_t,    40) }, /*   Throw/shoot weapon */
X    { &actsub[6], IDATA('z', T_z,    50) }, /*   Zap a wand */
X    { &actsub[7], IDATA('Z', T_Z,    60) }, /*   Cast a spell */
X    { &actsub[8], IDATA('X', T_X,    70) }, /*   Learn a spell */
X    { NULL	, IDATA('#', T_HASH, 80) }, /*   Extended command */
X};
X
X/* Preparations */
X
X#undef	WDT
X#define WDT 144
X
Xstatic struct MenuItem armsub[] = {
X    { &armsub[1], IDATA('w', T_w,      0) }, /*   Wield a weapon */
X    { &armsub[2], IDATA('R', T_R,     10) }, /*   Remove ring */
X    { &armsub[3], IDATA('P', T_P,     20) }, /*   Put on ring */
X    { &armsub[4], IDATA('T', T_T,     30) }, /*   Take off armor */
X    { &armsub[5], IDATA('W', T_W,     40) }, /*   Wear armor */
X    { &armsub[6], IDATA(')', T_WPN,   50) }, /*   Current weapon */
X    { &armsub[7], IDATA('[', T_ARMOR, 60) }, /*   Current armor */
X    { &armsub[8], IDATA('=', T_RING,  70) }, /*   Current rings */
X    { &armsub[9], IDATA('"', T_AMU,   80) }, /*   Current amulet */
X    { NULL	, IDATA('(', T_TOOL,  90) }, /*   Current tools */
X};
X
X/* Movement */
X
X#undef	WDT
X#define WDT 192
X
Xstatic struct MenuItem movsub[] = {
X    { &movsub[1], IDATA('o', T_o,     0) }, /*   Open door */
X    { &movsub[2], IDATA('c', T_c,    10) }, /*   Close door */
X    { &movsub[3], IDATA(004, T_KICK, 20) }, /*D  Kick door */
X    { &movsub[4], IDATA('s', T_s,    30) }, /*   Search */
X    { &movsub[5], IDATA('<', T_UP,   40) }, /*   Go up stairs */
X    { &movsub[6], IDATA('>', T_DOWN, 50) }, /*   Go down stairs */
X    { &movsub[7], IDATA(024, T_CT,   60) }, /*T  Teleport */
X    { &movsub[8], IDATA('.', T_WAIT, 70) }, /*   Wait a moment */
X    { NULL	, IDATA('E', T_E,    80) }, /*   Engrave msg on floor */
X};
X
X/* Menustrip */
X
X/* Width = #letters * 8 + 8 + 10 */
X
Xstruct Menu HackMenu[] = {
X   { &HackMenu[1], 10,0, 72,0,MENUENABLED,"Commands",     &cmdsub[0] }, /*8*/
X   { &HackMenu[2], 92,0, 80,0,MENUENABLED,"Inventory",    &invsub[0] }, /*9*/
X   { &HackMenu[3],182,0, 64,0,MENUENABLED,"Actions",      &actsub[0] }, /*7*/
X   { &HackMenu[4],256,0,104,0,MENUENABLED,"Preparations", &armsub[0] }, /*12*/
X   { NULL,	  370,0, 72,0,MENUENABLED,"Movement",     &movsub[0] }, /*8*/
X};
X
END_OF_FILE
if test 5924 -ne `wc -c <'amiga/amimenu.c'`; then
    echo shar: \"'amiga/amimenu.c'\" unpacked with wrong size!
fi
# end of 'amiga/amimenu.c'
fi
if test -f 'auxil/help' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'auxil/help'\"
else
echo shar: Extracting \"'auxil/help'\" \(6251 characters\)
sed "s/^X//" >'auxil/help' <<'END_OF_FILE'
X	Welcome to NetHack!		   ( description of version 3.0 )
X
X	NetHack is a Dungeons and Dragons like game where you (the adventurer)
Xdescend into the depths of the dungeon in search of the Amulet of Yendor
X(reputed to be hidden somewhere below the twentieth level).  You are
Xaccompanied by a dog or cat that can help you in many ways and can be trained
Xto do all sorts of things.  On the way you will find useful (or useless)
Xitems (quite possibly with magic properties), and assorted monsters.  You
Xattack a monster by trying to move into the space a monster is in (but often
Xit is much wiser to leave it alone).
X
X	Unlike most adventure games, which give you a verbal description of
Xyour location, NetHack gives you a visual image of the dungeon level you are
Xon.
X
X	NetHack uses the following symbols:
X
X	- and |  The walls of a room.
X	.	 The floor of a room.
X	#	 A corridor, or kitchen sink (if your dungeon has sinks).
X	>	 A way to the next level.
X	<	 A way to the previous level.
X	@	 You (usually) or another human.
X	)	 A weapon of some sort.
X	[	 A suit or piece of armor.
X	%	 A piece of food (not necessarily healthy).
X	/	 A wand.
X	=	 A ring.
X	?	 A scroll.
X	!	 A potion.
X	(	 Some other useful object (pick-axe, key, lamp...)
X	$	 A pile of gold.
X	*	 A gem or rock (possibly valuable, possibly worthless).
X	+	 A doorway, or a spell book containing a spell
X		 you can learn (if your dungeon has spell books).
X	^	 A trap (once you detect it).
X	" 	 An amulet, or a spider web.
X	0	 An iron ball.
X	_	 An altar (if your dungeon has altars), or an iron chain.
X	}	 A pool of water or moat.
X	{	 A fountain (your dungeon may not have fountains).
X	\	 An opulent throne (you may not have thrones either).
X	`	 A boulder or statue.
X	A to Z, a to z, and several others:  Monsters.
X
X		 You can find out what a character represents by typing
X		 '/' followed by the character, as in "/A", which will
X		 tell you that 'A' is an Ape.
X
X
Xy k u	7 8 9	Move commands:
X \|/	 \|/		yuhjklbn: go one step in specified direction
Xh-.-l	4-.-6		YUHJKLBN: go in specified direction until you
X /|\	 /|\			    hit a wall or run into something
Xb j n	1 2 3		g<dir>:   run in direction <dir> until something
X      numberpad 		    interesting is seen
X			G<dir>,   same, except a branching corridor isn't
X			^<dir>:     considered interesting
X			m<dir>:   move without picking up objects
X		If the numberpad option is set, the number keys move instead.
X
XCommands:
X	NetHack knows the following commands:
X	?	Help menu.
X	/	(followed by any symbol):  tell what this symbol represents.
X		You may choose to specify a location or give a symbol argument.
X	&	Tell what a command does.
X	<	Go up a staircase (if you are standing on it).
X	>	Go down a staircase (if you are standing on it).
X	.	Rest, do nothing for one turn.
X	a	Apply (use) an tool (pick-axe, key, lamp...)
X	A	Remove all armor.
X	^A	Redo the previous command
X	c	Close a door.
X	C	Call (name) an individual monster.
X	d	Drop something.  d7a:  drop seven items of object a.
X	D	Drop several things.  In answer to the question
X		"What kinds of things do you want to drop? [!%= au]"
X		you should type zero or more object symbols possibly
X		followed by 'a' and/or 'u'.
X		Da - drop all objects, without asking for confirmation.
X		Du - drop only unpaid objects (when in a shop).
X		D%u - drop only unpaid food.
X	^D	Kick (for doors, usually).
X	e	Eat food.
X	E	Engrave a message on the floor.
X		E- - write in the dust with your fingers.
X
X
X
X	i	Print your inventory.
X	I	Print selected parts of your inventory, as in
X		I* - list all gems in inventory.
X		Iu - list all unpaid items.
X		Ix - list all used up items that are on your shopping bill.
X		I$ - count your money.
X	o	Open a door.
X	O	Set options.  You will be asked to enter an option line.
X		If the line is empty, the current options are reported.
X		Descriptions of possible options and their formats can be
X		obtained by entering "?".  Options are usually set before
X		the game with a NETHACKOPTIONS environment variable, not
X		with the 'O' command.
X	p	Pay your shopping bill.
X	P	Put on a ring.
X	^P	Repeat last message (subsequent ^P's repeat earlier messages).
X	q	Drink (quaff) a potion.
X	Q	Quit the game.
X	r	Read a scroll or spell book.
X	R	Remove ring.
X	^R	Redraw the screen.
X	s	Search for secret doors and traps around you.
X	S	Save the game.
X	t	Throw an object or shoot a projectile.
X	T	Take off armor.
X	^T	Teleport, if you are able.
X	v	Prints the version number.
X	V	Prints a longer identification of the version, including the
X		history of the game.
X	w	Wield weapon.  w- means wield nothing, use bare hands.
X	W	Wear armor.
X	z	Zap a wand.
X	Z	Cast a spell.
X	^Z	Suspend the game.
X	:	Look at what is here.
X	,	Pick up some things.
X	@	Toggle the pickup option.
X	^	Ask for the type of a trap you found earlier.
X	)	Tell what weapon you are wielding.
X	[	Tell what armor you are wearing.
X	=	Tell what rings you are wearing.
X	" 	Tell what amulet you are wearing.
X	(	Tell what tools you are using.
X	$	Count your gold pieces.
X	+	List the spells you know.
X	\	Show what types of objects have been discovered.
X	!	Escape to a shell.
X	#	Introduces one of the "extended" commands.  To get a list of
X		the commands you can use with "#" type "#?".  The extended
X		commands you can use depends upon what options the game was
X		compiled with, along with your class and what type of monster
X		you most closely resemble at a given moment.
X
X	If the "number_pad" option is on, some additional letter commands
X	are available:
X
X	j	Jump to another location.
X	k	Kick (for doors, usually).
X	l	Loot a box on the floor.
X	N	Name an object or type of object.
X	u	Untrap a trapped object or door.
X
X	You can put a number before a command to repeat it that many times,
X	as in "40." or "20s.".  If you have the number_pad option set, you
X	must type 'n' to prefix the count, as in "n40." or "n20s".
X
X 
X	Some information is displayed on the bottom line.  You see your
X	attributes, your alignment, what dungeon level you are on, how many
X	hit points you have now (and will have when fully recovered), what
X	your armor class is (the lower the better), your experience level,
X	and the state of your stomach.  Optionally, you may or may not see
X	other information such as spell points, how much gold you have, etc.
X
X	Have Fun, and Happy Hacking!
X
END_OF_FILE
if test 6251 -ne `wc -c <'auxil/help'`; then
    echo shar: \"'auxil/help'\" unpacked with wrong size!
fi
# end of 'auxil/help'
fi
if test -f 'include/pcconf.h' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'include/pcconf.h'\"
else
echo shar: Extracting \"'include/pcconf.h'\" \(2369 characters\)
sed "s/^X//" >'include/pcconf.h' <<'END_OF_FILE'
X/*	SCCS Id: @(#)pcconf.h	3.0	88/07/21
X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
X/* NetHack may be freely redistributed.  See license for details. */
X
X#ifdef MSDOS
X#ifndef PCCONF_H
X#define PCCONF_H
X
X/*
X *  The following options are configurable:
X */
X
X#define DGK			/* MS DOS specific enhancements by dgk */
X
X#define TERMLIB		/* enable use of termcap file /etc/termcap */
X			/* or ./termcap for MSDOS (SAC) */
X			/* compile and link in Fred Fish's termcap library, */
X			/* enclosed in TERMCAP.ARC, to use this */
X#define ANSI_DEFAULT	/* allows NetHack to run without a ./termcap */
X
X#define RANDOM		/* have Berkeley random(3) */
X
X#define PATHLEN		64	/* maximum pathlength */
X#define FILENAME	80	/* maximum filename length (conservative) */
X#ifndef MSDOS_H
X#include "msdos.h"	/* contains necessary externs for [os_name].c */
X#endif
X#define glo(x)	name_file(lock, (int)x)	/* name_file used for bones */
Xextern const char *configfile;
X/*#define SHELL			/* via exec of COMMAND.COM */
X
X#ifdef DGK
X/*	Selectable DGK options:
X */
X/*#define DECRAINBOW	/* enable use of DEC Rainbow graphics */
X
X/*	Non-Selectable DGK options:
X */
X# define FROMPERM	 1	/* for ramdisk use */
X# define TOPERM		 2	/* for ramdisk use */
X
X#endif /* DGK /**/
X
X/*
X *  The remaining code shouldn't need modification.
X */
X
X#ifndef SYSTEM_H
X#include "system.h"
X#endif
X#define index	strchr
X#define rindex	strrchr
X
X#include <time.h>
X
X#ifdef RANDOM
X/* Use the high quality random number routines. */
X#define Rand()	random()
X#define Srand(seed)	srandom(seed)
X#else
X#define Rand()	rand()
X#define Srand(seed)	srand(seed)
X#endif /* RANDOM */
X
X#ifdef __TURBOC__
X#define	alloc	malloc
X# if __TURBOC__ < 0x0200 /* version 2.0 has signal() */
X#define	signal	ssignal
X# endif
X/* rename the next two functions - they clash with the Turbo C library */
X#define getdate getdate_
X#define itoa itoa_
X#endif
X
X#ifndef TOS
X#define	FCMASK	0660	/* file creation mask */
X#endif
X
X#include <fcntl.h>
X
X#define	exit	msexit		/* do chdir first */
X
X#ifndef REDO
X#undef	Getchar
X#define Getchar tgetch
X#endif
X
X#ifndef TOS
X#  define MSDOSCOLOR /* */
X/* configurable colors */
X#  define HI_MON  HI_RED	/* red slaps! */
X#  define HI_OBJ  HI_GREEN
X#  define HI_GOLD HI_YELLOW
X#  define HI_ZAP  HI_BLUE	/* blue zaps! */
X#endif
X
X#ifndef EXTERN_H
X#include "extern.h"
X#endif
X
X#endif /* PCCONF_H /* */
X#endif /* MSDOS /* */
END_OF_FILE
if test 2369 -ne `wc -c <'include/pcconf.h'`; then
    echo shar: \"'include/pcconf.h'\" unpacked with wrong size!
fi
# end of 'include/pcconf.h'
fi
if test -f 'include/rm.h' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'include/rm.h'\"
else
echo shar: Extracting \"'include/rm.h'\" \(6133 characters\)
sed "s/^X//" >'include/rm.h' <<'END_OF_FILE'
X/*	SCCS Id: @(#)rm.h	3.0	88/10/25
X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
X/* NetHack may be freely redistributed.  See license for details. */
X
X#ifndef RM_H
X#define RM_H
X
X/*
X * The dungeon presentation graphics code and data structures were rewritten
X * and generalized for NetHack's release 2 by Eric S. Raymond (eric@snark)
X * building on Don G. Kneller's MS-DOS implementation. See options.c for
X * the code that permits the user to set the contents of the symbol structure.
X */
X
X/* Level location types */
X#define STONE		0
X#define HWALL		1
X#define VWALL		2
X#define TLCORNER	3
X#define TRCORNER	4
X#define BLCORNER	5
X#define BRCORNER	6
X#define CROSSWALL	7	/* For pretty mazes and special levels */
X#define TUWALL		8
X#define TDWALL		9
X#define TLWALL		10
X#define TRWALL		11
X#define SDOOR		12
X#define SCORR		13
X#define POOL		14
X#define MOAT		15	/* pool that doesn't boil, adjust messages */
X#define DRAWBRIDGE_UP	16
X#define DOOR		17
X#define CORR		18
X#define ROOM		19
X#define STAIRS		20
X#define LADDER		21
X#define FOUNTAIN	22
X#define THRONE		23
X#define SINK		24
X#define ALTAR		25
X#define DRAWBRIDGE_DOWN	26
X
X/*
X * Avoid using the level types in inequalities:
X * these types are subject to change.
X * Instead, use one of the macros below.
X */
X#define IS_WALL(typ)	((typ) && (typ) <= TRWALL)
X#define IS_STWALL(typ)	((typ) <= TRWALL)	/* STONE <= (typ) <= TRWALL */
X#define IS_ROCK(typ)	((typ) < POOL)		/* absolutely nonaccessible */
X#define IS_DOOR(typ)	((typ) == DOOR)
X#define ACCESSIBLE(typ)	((typ) >= DOOR)		/* good position */
X#define IS_ROOM(typ)	((typ) >= ROOM)		/* ROOM, STAIRS, furniture.. */
X#define ZAP_POS(typ)	((typ) >= POOL)
X#define SPACE_POS(typ)	((typ) > DOOR)
X#define IS_CORNER(typ)	((typ) >= TLCORNER && (typ) <= BRCORNER)
X#define IS_T(typ)	((typ) >= CRWALL && (typ) <= TRWALL)
X#define IS_POOL(typ)	((typ) >= POOL && (typ) <= DRAWBRIDGE_UP)
X#define IS_THRONE(typ)	((typ) == THRONE)
X#define IS_FOUNTAIN(typ) ((typ) == FOUNTAIN)
X#define IS_SINK(typ)	((typ) == SINK)
X#define IS_ALTAR(typ)	((typ) == ALTAR)
X#define IS_DRAWBRIDGE(typ) ((typ) == DRAWBRIDGE_UP || (typ) == DRAWBRIDGE_DOWN)
X#define IS_FURNITURE(typ) ((typ) >= STAIRS && (typ) <= ALTAR)
X
X/*
X * The level-map symbols may be compiled in or defined at initialization time
X */
X
X/* screen symbols for using character graphics. */
Xstruct symbols {
X    unsigned char stone, vwall, hwall, tlcorn, trcorn, blcorn, brcorn;
X    unsigned char crwall, tuwall, tdwall, tlwall, trwall;
X    unsigned char vbeam, hbeam, lslant, rslant;
X    unsigned char door, room, corr, upstair, dnstair, trap, web;
X    unsigned char pool;
X    unsigned char fountain;
X    unsigned char sink;
X    unsigned char throne;
X    unsigned char altar;
X    unsigned char upladder, dnladder, dbvwall, dbhwall;
X};
Xextern struct symbols showsyms;
X#ifdef REINCARNATION
Xextern struct symbols savesyms;
X#endif
Xextern const struct symbols defsyms;
X
X#define STONE_SYM	showsyms.stone
X#define VWALL_SYM	showsyms.vwall
X#define HWALL_SYM	showsyms.hwall
X#define TLCORN_SYM	showsyms.tlcorn
X#define TRCORN_SYM	showsyms.trcorn
X#define BLCORN_SYM	showsyms.blcorn
X#define BRCORN_SYM	showsyms.brcorn
X#define CRWALL_SYM	showsyms.crwall
X#define TUWALL_SYM	showsyms.tuwall
X#define TDWALL_SYM	showsyms.tdwall
X#define TLWALL_SYM	showsyms.tlwall
X#define TRWALL_SYM	showsyms.trwall
X#define VBEAM_SYM	showsyms.vbeam
X#define HBEAM_SYM	showsyms.hbeam
X#define LSLANT_SYM	showsyms.lslant
X#define RSLANT_SYM	showsyms.rslant
X#define DOOR_SYM	showsyms.door
X#define ROOM_SYM	showsyms.room
X#define	CORR_SYM	showsyms.corr
X#define UP_SYM		showsyms.upstair
X#define DN_SYM		showsyms.dnstair
X#define TRAP_SYM	showsyms.trap
X#define WEB_SYM		showsyms.web
X#define	POOL_SYM	showsyms.pool
X#define FOUNTAIN_SYM	showsyms.fountain
X#define SINK_SYM	showsyms.sink
X#define THRONE_SYM	showsyms.throne
X#define ALTAR_SYM	showsyms.altar
X#define UPLADDER_SYM	showsyms.upladder
X#define DNLADDER_SYM	showsyms.dnladder
X#define DB_VWALL_SYM	showsyms.dbvwall
X#define DB_HWALL_SYM	showsyms.dbhwall
X
X#define	ERRCHAR	']'
X
X#define MAXPCHARS	28	/* maximum number of mapped characters */
X
X/*
X * The 5 possible states of doors
X */
X
X#define D_NODOOR	0
X#define D_BROKEN	1
X#define D_ISOPEN	2
X#define D_CLOSED	4
X#define D_LOCKED	8
X#define D_TRAPPED	16
X
X/*
X * The 3 possible alignments for altars
X */
X#define A_CHAOS		0
X#define A_NEUTRAL	1
X#define A_LAW		2
X
X/*
X * Some altars are considered as shrines, so we need a flag.
X */
X#define A_SHRINE	4
X
X/*
X * Thrones should only be looted once.
X */
X#define T_LOOTED	1
X
X/*
X * The four directions for a DrawBridge.
X */
X#define DB_NORTH	0
X#define DB_SOUTH	1
X#define DB_EAST 	2
X#define DB_WEST 	4
X#define DB_DIR		7	/* mask for direction */
X
X/*
X * What's under a drawbridge.
X */
X#define DB_MOAT		0
X#define DB_FLOOR	8
X#define DB_UNDER	8	/* mask for underneath */
X
X/* 
X * Some walls may be non diggable.
X */
X#define W_DIGGABLE	0
X#define W_NONDIGGABLE	1
X#define W_GATEWAY	16	/* is a drawbridge wall */
X
X/*
X * Ladders (in Vlad's tower) may be up or down.
X */
X#define LA_UP		1
X#define LA_DOWN 	2
X
X/*
X * at() display character types, in order of precedence.
X */
X#define AT_APP		(uchar)0
X/* specific overrides */
X#define AT_RED		(uchar)1	/* flame */
X#define AT_BLUE 	(uchar)4	/* water */
X#define AT_WHITE	(uchar)7	/* lightning */
X/* non-specific */
X#define AT_ZAP		(uchar)8
X#define AT_MON		(uchar)9
X#define AT_U		AT_MON
X#define AT_OBJ		(uchar)10
X#define AT_GLD		AT_OBJ
X#define AT_MAP		(uchar)11
X
X/*
X * The structure describing a coordinate position.
X * Before adding fields, remember that this will significantly affect
X * the size of temporary files and save files.
X */
Xstruct rm {
X	uchar scrsym;
X	Bitfield(typ,5);
X	Bitfield(new,1);
X	Bitfield(seen,1);
X	Bitfield(lit,1);
X	Bitfield(doormask,5);
X	Bitfield(mmask,1);
X	Bitfield(omask,1);
X	Bitfield(gmask,1);
X};
X
X#define altarmask	doormask
X#define diggable	doormask
X#define ladder		doormask
X#define drawbridgemask	doormask
X
Xextern struct rm levl[COLNO][ROWNO];
X
X#if defined(DGK) && !defined(TOS)
X#define ACTIVE	1
X#define SWAPPED	2
X
Xstruct finfo {
X	int	where;
X	long	time;
X	long	size;
X};
Xextern struct finfo fileinfo[];
X#define ZFINFO	{ 0, 0L, 0L }
X#endif
X
X#endif /* RM_H /**/
END_OF_FILE
if test 6133 -ne `wc -c <'include/rm.h'`; then
    echo shar: \"'include/rm.h'\" unpacked with wrong size!
fi
# end of 'include/rm.h'
fi
if test -f 'src/decl.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'src/decl.c'\"
else
echo shar: Extracting \"'src/decl.c'\" \(5954 characters\)
sed "s/^X//" >'src/decl.c' <<'END_OF_FILE'
X/*	SCCS Id: @(#)decl.c	3.0	88/10/25
X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
X/* NetHack may be freely redistributed.  See license for details. */
X
X#include	"hack.h"
X
Xint multi = 0;
Xint warnlevel = 0;		/* used by movemon and dochugw */
Xint nroom = 0;
Xint occtime = 0;
X
Xint x_maze_max, y_maze_max;	/* initialized in main, used in mkmaze.c */
X
X#ifdef REDO
Xint in_doagain = 0;
X#endif
X
X/*
X *	The following integers will be initialized at load time with
X *	the level numbers of some "important" things in the game.
X */
X
X int
X	medusa_level = 0,	/* level that the medusa lives on */
X	bigroom_level = 0,	/* level consisting of a single big room */
X#ifdef REINCARNATION
X	rogue_level = 0,	/* level near which rogue level gen'd */
X#endif
X#ifdef ORACLE
X	oracle_level = 0,	/* level near which Oracle gen'd */
X#endif
X#ifdef STRONGHOLD
X	stronghold_level = 3,	/* level the castle is on */
X	/* Not 0, otherwise they start the game in Hell and burn immediately */
X	tower_level = 0,	/* level of the top of Vlad's 3-level tower */
X#endif
X	wiz_level = 0;		/* level that the wiz lives on */
Xboolean is_maze_lev = FALSE;    /* if this is a maze level */
X
Xint smeq[MAXNROFROOMS+1] = DUMMY;
Xint doorindex = 0;
X
Xchar *save_cm = 0;
Xchar *killer = 0;
Xchar *nomovemsg = 0;
Xconst char nul[40] = DUMMY;		/* contains zeros */
Xchar plname[PL_NSIZ] = DUMMY;		/* player name */
Xchar pl_character[PL_CSIZ] = DUMMY;
Xchar pl_fruit[PL_FSIZ] = DUMMY;
Xint current_fruit = 0;
Xstruct fruit *ffruit = 0;
X#ifdef STRONGHOLD
Xchar tune[6] = DUMMY;
X#  ifdef MUSIC
Xschar music_heard = 0;
X#  endif
X#endif
Xchar *occtxt = DUMMY;
Xconst char quitchars[] = " \r\n\033";
Xconst char vowels[] = "aeiouAEIOU";
Xconst char ynchars[] = "yn";
Xconst char ynqchars[] = "ynq";
Xconst char ynaqchars[] = "ynaq";
Xconst char nyaqchars[] = "nyaq";
Xchar *HI = DUMMY, *HE = DUMMY, *AS = DUMMY, *AE = DUMMY, *CD = DUMMY;
X	/* set up in termcap.c */
Xint CO = 0, LI = 0;	/* set up in termcap.c: usually COLNO and ROWNO+3 */
X
X#ifdef MSDOSCOLOR
Xchar *HI_RED, *HI_YELLOW, *HI_GREEN, *HI_BLUE, *HI_WHITE; /* termcap.c */
X#endif
X
X#ifdef MSDOS
Xchar hackdir[PATHLEN];		/* where rumors, help, record are */
Xconst char *configfile = "NetHack.cnf";	/* read by read_config_file() */
Xchar levels[PATHLEN];		/* where levels are */
X#endif /* MSDOS */
X#ifdef DGK
Xchar lock[FILENAME];		/* pathname of level files */
Xchar permbones[PATHLEN];	/* where permanent copy of bones go */
Xint ramdisk = FALSE;		/* whether to copy bones to levels or not */
Xint saveprompt = TRUE;
Xconst char *alllevels = "levels.*";
Xconst char *allbones = "bones.*";
X#else
Xchar lock[PL_NSIZ+4] = "1lock";	/* long enough for login name .99 */
X#endif
X
Xint dig_effort = 0;	/* effort expended on current pos */
Xuchar dig_level = 0;
Xcoord dig_pos = DUMMY;
Xboolean dig_down = FALSE;
X
Xxchar dlevel = 1;
Xxchar maxdlevel = 1;
Xint done_stopprint = 0;
Xint done_hup = 0;
Xxchar xupstair = 0, yupstair = 0, xdnstair = 0, ydnstair = 0;
X#ifdef STRONGHOLD
Xxchar xupladder = 0, yupladder = 0, xdnladder = 0, ydnladder = 0;
X#endif
Xxchar curx = 0, cury = 0;
Xxchar seelx = 0, seehx = 0, seely = 0, seehy = 0; /* corners of lit room */
Xxchar seelx2 = 0, seehx2 = 0, seely2 = 0, seehy2 = 0; /* corners of lit room */
Xxchar scrlx = 0, scrhx = 0, scrly = 0, scrhy = 0; /* corners of new scr. area*/
Xxchar fountsound = 0;
Xxchar sinksound = 0; /* numbers of other things that make noise */
X
Xboolean in_mklev = FALSE;
Xboolean	stoned = FALSE;			/* done to monsters hit by 'c' */
Xboolean	unweapon = FALSE;
X#ifdef KOPS
Xboolean allow_kops = TRUE;
X#endif
X
Xcoord bhitpos = DUMMY;
Xcoord doors[DOORMAX] = DUMMY;
X
Xstruct mkroom rooms[MAXNROFROOMS+1] = DUMMY;
Xstruct rm levl[COLNO][ROWNO] = DUMMY;		/* level map */
Xstruct monst *fmon = 0;
Xstruct trap *ftrap = 0;
Xstruct gold *fgold = 0;
Xstruct monst youmonst = DUMMY;	/* dummy; used as return value for boomhit */
Xstruct flag flags = DUMMY;
Xstruct you u = DUMMY;
X
Xstruct obj *fobj = 0, *fcobj = 0, *invent = 0, *uwep = 0, *uarm = 0,
X#ifdef SHIRT
X	*uarmu = 0,		/* under-wear, so to speak */
X#endif
X#ifdef POLYSELF
X	*uskin = 0,		/* dragon armor, if a dragon */
X#endif
X	*uarmc = 0, *uarmh = 0, *uarms = 0, *uarmg = 0, *uarmf = 0, *uamul = 0,
X	*uright = 0, *uleft = 0, *ublindf = 0, *uchain = 0, *uball = 0;
X
Xconst struct symbols defsyms = {
X    ' ', /* stone */
X    '|', /* vwall */
X    '-', /* hwall */
X    '-', /* tlcorn */
X    '-', /* trcorn */
X    '-', /* blcorn */
X    '-', /* brcorn */
X    '-', /* crwall */
X    '-', /* tuwall */
X    '-', /* tdwall */
X    '|', /* tlwall */
X    '|', /* trwall */
X    '|', /* vbeam */
X    '-', /* hbeam */
X    '\\', /* lslant */
X    '/', /* rslant */
X    '+', /* door */
X    '.', /* room */
X    '#', /* corr */
X    '<', /* upstair */
X    '>', /* dnstair */
X    '^', /* trap */
X    '"', /* web */
X    '}', /* pool */
X    '{', /* fountain */	/* used ifdef FOUNTAINS */
X    '#', /* sink */	/* used ifdef SINKS */
X    '\\', /* throne */	/* used ifdef THRONES */
X    '_', /* altar */	/* used ifdef ALTARS */
X    '<', /* upladder */	/* used ifdef STRONGHOLD */
X    '>', /* dnladder */	/* used ifdef STRONGHOLD */
X    '#', /* dbvwall */	/* used ifdef STRONGHOLD */
X    '#', /* dbhwall */	/* used ifdef STRONGHOLD */
X};
Xstruct symbols showsyms = DUMMY; /* will contain the symbols actually used */
X#ifdef REINCARNATION
Xstruct symbols savesyms = DUMMY;
X#endif
X
X#ifdef SPELLS
Xstruct spell spl_book[MAXSPELL + 1] = DUMMY;
X#endif
X
Xlong moves = 1;
Xlong wailmsg = 0;
X
Xstruct obj zeroobj = DUMMY;	/* used to zero all elements of a struct obj */
X
Xstruct obj *billobjs = 0;
X
Xconst char black[] = "black";
Xconst char amber[] = "amber";
X#ifdef THEOLOGY
Xconst char golden[] = "golden";
X#endif
Xconst char light_blue[] = "light blue";
Xconst char red[] = "red";
Xconst char green[] = "green";
Xconst char silver[] = "silver";
Xconst char blue[] = "blue";
Xconst char purple[] = "purple";
Xconst char white[] = "white";
X
Xconst char nothing_happens[] = "Nothing happens.";
Xconst char thats_enough_tries[] = "That's enough tries!";
END_OF_FILE
if test 5954 -ne `wc -c <'src/decl.c'`; then
    echo shar: \"'src/decl.c'\" unpacked with wrong size!
fi
# end of 'src/decl.c'
fi
if test -f 'src/getline.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'src/getline.c'\"
else
echo shar: Extracting \"'src/getline.c'\" \(5973 characters\)
sed "s/^X//" >'src/getline.c' <<'END_OF_FILE'
X/*	SCCS Id: @(#)getline.c	3.0	89/06/16
X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
X/* NetHack may be freely redistributed.  See license for details. */
X
X#include "hack.h"
X#include "func_tab.h"
X
X/*
X * Some systems may have getchar() return EOF for various reasons, and
X * we should not quit before seeing at least NR_OF_EOFS consecutive EOFs.
X */
X#ifdef SYSV
X#define	NR_OF_EOFS	20
X#endif
X
Xchar morc = 0;	/* tell the outside world what char he used */
X
Xextern char erase_char, kill_char;	/* from appropriate tty.c file */
X
X/*
X * Read a line closed with '\n' into the array char bufp[BUFSZ].
X * (The '\n' is not stored. The string is closed with a '\0'.)
X * Reading can be interrupted by an escape ('\033') - now the
X * resulting string is "\033".
X */
Xvoid
Xgetlin(bufp)
Xregister char *bufp;
X{
X	register char *obufp = bufp;
X	register int c;
X
X	flags.toplin = 2;		/* nonempty, no --More-- required */
X	for(;;) {
X		(void) fflush(stdout);
X		if((c = Getchar()) == EOF) {
X			*bufp = 0;
X			return;
X		}
X		if(c == '\033') {
X			*obufp = c;
X			obufp[1] = 0;
X			return;
X		}
X		if(c == erase_char || c == '\b') {
X			if(bufp != obufp) {
X				bufp--;
X				putstr("\b \b");/* putsym converts \b */
X			} else	bell();
X		} else if(c == '\n') {
X			*bufp = 0;
X			return;
X		} else if(' ' <= c && c < '\177' && 
X			    (bufp-obufp < BUFSZ-1 || bufp-obufp < COLNO)) {
X				/* avoid isprint() - some people don't have it
X				   ' ' is not always a printing char */
X			*bufp = c;
X			bufp[1] = 0;
X			putstr(bufp);
X			bufp++;
X		} else if(c == kill_char || c == '\177') { /* Robert Viduya */
X				/* this test last - @ might be the kill_char */
X			while(bufp != obufp) {
X				bufp--;
X				if(curx == 1 && cury > 1) {
X					putstr("\b \b\b");
X					curx = CO;
X				} else putstr("\b \b");
X			}
X		} else
X			bell();
X	}
X}
X
Xvoid
Xgetret() {
X	cgetret("");
X}
X
Xvoid
Xcgetret(s)
Xregister char *s;
X{
X	putsym('\n');
X	if(flags.standout)
X		standoutbeg();
X	putstr("Hit ");
X	putstr(flags.cbreak ? "space" : "return");
X	putstr(" to continue: ");
X	if(flags.standout)
X		standoutend();
X	xwaitforspace(s);
X}
X
X
Xvoid
Xxwaitforspace(s)
Xregister char *s;	/* chars allowed besides space or return */
X{
X	register int c;
X
X	morc = 0;
X
X	while((c = readchar()) != '\n') {
X	    if(flags.cbreak) {
X		if(c == ' ') break;
X		if(s && index(s,c)) {
X			morc = c;
X			break;
X		}
X		bell();
X	    }
X	}
X}
X
Xstatic int last_multi;
X
Xchar *
Xparse()
X{
X#ifdef LINT	/* static char in_line[COLNO]; */
X	char in_line[COLNO];
X#else
X	static char in_line[COLNO];
X#endif
X	register int foo;
X
X	multi = 0;
X	flags.move = 1;
X	curs_on_u();
X
X	if (!flags.num_pad || (foo = readchar()) == 'n')
X	    while((foo = readchar()) >= '0' && foo <= '9') {
X		multi = 10*multi+foo-'0';
X		if (multi < 0 || multi > LARGEST_INT)
X			multi = LARGEST_INT;
X		if (multi > 9) {
X			remember_topl();
X			home();
X			cl_end();
X			Printf("Count: %d", multi);
X		}
X		last_multi = multi;
X	    }
X# ifdef REDO
X	if (foo == DOAGAIN || in_doagain)
X		multi = last_multi;
X	else {
X		savech(0);	/* reset input queue */
X		savech(foo);
X	}
X# endif
X	if(multi) {
X		multi--;
X		save_cm = in_line;
X	}
X	in_line[0] = foo;
X	in_line[1] = 0;
X	if(foo == 'g' || foo == 'G'){
X		in_line[1] = Getchar();
X#ifdef REDO
X		savech(in_line[1]);
X#endif
X		in_line[2] = 0;
X	}
X	if(foo == 'm' || foo == 'M'){
X		in_line[1] = Getchar();
X#ifdef REDO
X		savech(in_line[1]);
X#endif
X		in_line[2] = 0;
X	}
X	clrlin();
X	return(in_line);
X}
X
X#ifdef UNIX
Xstatic void
Xend_of_input()
X{
X	settty("End of input?\n");
X	clearlocks();
X	exit(0);
X}
X#endif
X
Xchar
Xreadchar() {
X	register int sym;
X
X	(void) fflush(stdout);
X#ifdef UNIX
X	if((sym = Getchar()) == EOF)
X# ifdef NR_OF_EOFS
X	{ /*
X	   * Some SYSV systems seem to return EOFs for various reasons
X	   * (?like when one hits break or for interrupted systemcalls?),
X	   * and we must see several before we quit.
X	   */
X		register int cnt = NR_OF_EOFS;
X		while (cnt--) {
X		    clearerr(stdin);	/* omit if clearerr is undefined */
X		    if((sym = Getchar()) != EOF) goto noteof;
X		}
X		end_of_input();
X	     noteof:	;
X	}
X# else
X		end_of_input();
X# endif /* NR_OF_EOFS /**/
X#else
X	sym = Getchar();
X#endif /* UNIX */
X	if(flags.toplin == 1)
X		flags.toplin = 2;
X	return((char) sym);
X}
X
X#ifdef COM_COMPL
X/* Read in an extended command - doing command line completion for
X * when enough characters have been entered to make a unique command.
X * This is just a modified getlin().   -jsb
X */
Xvoid
Xget_ext_cmd(bufp)
Xregister char *bufp;
X{
X	register char *obufp = bufp;
X	register int c;
X	int com_index, oindex;
X
X	flags.toplin = 2;		/* nonempty, no --More-- required */
X
X	for(;;) {
X		(void) fflush(stdout);
X		if((c = readchar()) == EOF) {
X			*bufp = 0;
X			return;
X		}
X		if(c == '\033') {
X			*obufp = c;
X			obufp[1] = 0;
X			return;
X		}
X		if(c == erase_char || c == '\b') {
X			if(bufp != obufp) {
X				bufp--;
X				putstr("\b \b"); /* putsym converts \b */
X			} else	bell();
X		} else if(c == '\n') {
X			*bufp = 0;
X			return;
X		} else if(' ' <= c && c < '\177') {
X				/* avoid isprint() - some people don't have it
X				   ' ' is not always a printing char */
X			*bufp = c;
X			bufp[1] = 0;
X			oindex = 0;
X			com_index = -1;
X
X			while(extcmdlist[oindex].ef_txt != NULL){
X				if(!strncmp(obufp, extcmdlist[oindex].ef_txt,
X				    strlen(obufp)))
X					if(com_index == -1) /* No matches yet*/
X					    com_index = oindex;
X					else /* More than 1 match */
X					    com_index = -2;
X				oindex++;
X			}
X			if(com_index >= 0){
X				Strcpy(obufp, extcmdlist[com_index].ef_txt);
X				/* finish printing our string */
X				putstr(bufp);
X				bufp = obufp; /* reset it */
X				if(strlen(obufp) < BUFSIZ-1 &&
X				 strlen(obufp) < COLNO)
X					/* set bufp at the end of our string */
X					bufp += strlen(obufp);
X			} else {
X				putstr(bufp);
X				if(bufp-obufp < BUFSZ-1 && bufp-obufp < COLNO)
X					bufp++;
X			}
X		} else if(c == kill_char || c == '\177') { /* Robert Viduya */
X				/* this test last - @ might be the kill_char */
X			while(bufp != obufp) {
X				bufp--;
X				putstr("\b \b");
X			}
X		} else
X			bell();
X	}
X
X}
X#endif /* COM_COMPL */
END_OF_FILE
if test 5973 -ne `wc -c <'src/getline.c'`; then
    echo shar: \"'src/getline.c'\" unpacked with wrong size!
fi
# end of 'src/getline.c'
fi
if test -f 'src/mail.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'src/mail.c'\"
else
echo shar: Extracting \"'src/mail.c'\" \(5907 characters\)
sed "s/^X//" >'src/mail.c' <<'END_OF_FILE'
X/*	SCCS Id: @(#)mail.c	3.0	89/07/07
X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
X/* NetHack may be freely redistributed.  See license for details. */
X
X/* block some unused #defines to avoid overloading some cpp's */
X#define MONATTK_H
X#include "hack.h"	/* mainly for index() which depends on BSD */
X
X#ifdef MAIL
X
X# ifdef UNIX
X#include <sys/stat.h>
X# endif
X
X/*
X * Notify user when new mail has arrived. [Idea from Merlyn Leroy, but
X * I don't know the details of his implementation.]
X * { Later note: he disliked my calling a general mailreader and felt that
X *   hack should do the paging itself. But when I get mail, I want to put it
X *   in some folder, reply, etc. - it would be unreasonable to put all these
X *   functions in hack. }
X * The motion of the mail daemon is less restrained than usual:
X * diagonal moves from a DOOR are possible. He might also use SDOOR's. Also,
X * the mail daemon is visible in a ROOM, even when you are Blind.
X * Its path should be longer when you are Telepat-hic and Blind.
X *
X * Possible extensions:
X *	- Open the file MAIL and do fstat instead of stat for efficiency.
X *	  (But sh uses stat, so this cannot be too bad.)
X *	- Examine the mail and produce a scroll of mail named "From somebody".
X *	- Invoke MAILREADER in such a way that only this single letter is read.
X *	- Do something to the text when the scroll is enchanted or cancelled.
X */
X
X/*
X * { Note by Olaf Seibert: On the Amiga, we usually don't get mail.
X *   So we go through most of the effects at 'random' moments. }
X */
X
X/*
X * I found many bugs in this code, some dating back to Hack.
X * Here are some minor problems i didn't fix:  -3.
X *
X *	- The code sometimes pops up the mail daemon next to you on
X *	  the corridor side of doorways when there are open spaces in
X *	  the room.
X *	- It may also do this with adjoining castle rooms.
X */
X
X# ifdef AMIGA
Xint mustgetmail = -1;
X# endif
X
X# ifdef UNIX
Xstatic struct stat omstat,nmstat;
Xstatic char *mailbox;
Xstatic long laststattime;
X
Xvoid
Xgetmailstatus() {
X	if(!(mailbox = getenv("MAIL")))
X		return;
X	if(stat(mailbox, &omstat)){
X#  ifdef PERMANENT_MAILBOX
X		pline("Cannot get status of MAIL=%s .", mailbox);
X		mailbox = 0;
X#  else
X		omstat.st_mtime = 0;
X#  endif
X	}
X}
X# endif /* UNIX */
X
X/* make md run through the cave */
Xstatic void
Xmdrush(md,away)
Xregister struct monst *md;
Xboolean away;
X{
X	register int uroom = inroom(u.ux, u.uy);
X	if(uroom >= 0 && inroom(md->mx,md->my) == uroom) {
X		register int tmp = rooms[uroom].fdoor;
X		register int cnt = rooms[uroom].doorct;
X		register int fx = u.ux, fy = u.uy;
X		while(cnt--) {
X			if(dist(fx,fy) < dist(doors[tmp].x, doors[tmp].y)){
X				fx = doors[tmp].x;
X				fy = doors[tmp].y;
X			}
X			tmp++;
X		}
X		if (has_dnstairs(&rooms[uroom]))
X			if(dist(fx,fy) < dist(xdnstair, ydnstair)){
X				fx = xdnstair;
X				fy = ydnstair;
X			}
X		if (has_upstairs(&rooms[uroom]))
X			if(dist(fx,fy) < dist(xupstair, yupstair)){
X				fx = xupstair;
X				fy = yupstair;
X			}
X		tmp_at(-1, md->data->mlet);	/* open call */
X		tmp_at(-3, (int)AT_MON);
X		if(away) {	/* interchange origin and destination */
X			unpmon(md);
X			levl[md->mx][md->my].mmask = 0;
X			levl[fx][fy].mmask = 1;
X			tmp = fx; fx = md->mx; md->mx = tmp;
X			tmp = fy; fy = md->my; md->my = tmp;
X		}
X		while(fx != md->mx || fy != md->my) {
X			register int dx,dy,nfx = fx,nfy = fy,d1,d2;
X
X			tmp_at(fx,fy);
X			d1 = dist2(fx,fy,md->mx,md->my);
X			for(dx = -1; dx <= 1; dx++) for(dy = -1; dy <= 1; dy++)
X			    if((dx || dy) && 
X			       !IS_STWALL(levl[fx+dx][fy+dy].typ)) {
X				d2 = dist2(fx+dx,fy+dy,md->mx,md->my);
X				if(d2 < d1) {
X				    d1 = d2;
X				    nfx = fx+dx;
X				    nfy = fy+dy;
X				}
X			    }
X			if(nfx != fx || nfy != fy) {
X			    fx = nfx;
X			    fy = nfy;
X			} else {
X			    if(!away) {
X				levl[md->mx][md->my].mmask = 0;
X				levl[fx][fy].mmask = 1;
X				md->mx = fx;
X				md->my = fy;
X			    }
X			    break;
X			} 
X		}
X		tmp_at(-1,-1);			/* close call */
X	}
X	if(!away)
X		pmon(md);
X}
X
Xstatic void
Xnewmail() {
X	/* deliver a scroll of mail */
X	register boolean invload =
X	((inv_weight() + (int)objects[SCR_MAIL].oc_weight) > 0 ||
X	 inv_cnt() >= 52 || Fumbling);
X	register struct monst *md = 
X	makemon(&mons[PM_MAIL_DAEMON], u.ux, u.uy);
X
X	if(!md)	return;
X
X	mdrush(md,0);
X
X	pline("\"Hello, %s!  I have some mail for you.\"", plname);
X
X	if(dist(md->mx,md->my) > 2)
X		verbalize("Catch!");
X	more();
X	if(invload) {
X		struct obj *obj = mksobj_at(SCR_MAIL,u.ux,u.uy);
X		obj->known = obj->dknown = TRUE;
X		makeknown(SCR_MAIL);
X		stackobj(fobj);		
X		verbalize("Oops!");
X		more();
X	} else {
X		/* set known and do prinv() */
X		(void) identify(addinv(mksobj(SCR_MAIL,FALSE)));
X	}
X
X	/* disappear again */
X	mdrush(md,1);
X	mongone(md);
X
X	/* force the graphics character set off */
X	nscr();
X}
X
X# ifdef AMIGA
Xvoid
Xckmailstatus() {
X	if (mustgetmail < 0)
X	    return;
X	if (--mustgetmail <= 0) {
X		newmail();
X		mustgetmail = -1;
X	}
X}
X
Xvoid
Xreadmail()
X{
X	pline("It says: \"How nice to get a letter down here!\"");
X}
X# endif /* AMIGA */
X
X# ifdef UNIX
Xvoid
Xckmailstatus() {
X	if(!mailbox
X#  ifdef MAILCKFREQ
X		    || moves < laststattime + MAILCKFREQ
X#  endif
X							)
X		return;
X
X	laststattime = moves;
X	if(stat(mailbox, &nmstat)){
X#  ifdef PERMANENT_MAILBOX
X		pline("Cannot get status of MAIL=%s anymore.", mailbox);
X		mailbox = 0;
X#  else
X		nmstat.st_mtime = 0;
X#  endif
X	} else if(nmstat.st_mtime > omstat.st_mtime) {
X		if(nmstat.st_size)
X			newmail();
X		getmailstatus();	/* might be too late ... */
X	}
X}
X
Xvoid
Xreadmail() {
X#  ifdef DEF_MAILREADER			/* This implies that UNIX is defined */
X	register char *mr = 0;
X	more();
X	if(!(mr = getenv("MAILREADER")))
X		mr = DEF_MAILREADER;
X	if(child(1)){
X		(void) execl(mr, mr, NULL);
X		exit(1);
X	}
X#  else
X	(void) page_file(mailbox, FALSE);
X#  endif
X	/* get new stat; not entirely correct: there is a small time
X	   window where we do not see new mail */
X	getmailstatus();
X}
X# endif /* UNIX */
X
X#endif /* MAIL */
END_OF_FILE
if test 5907 -ne `wc -c <'src/mail.c'`; then
    echo shar: \"'src/mail.c'\" unpacked with wrong size!
fi
# end of 'src/mail.c'
fi
if test -f 'src/topl.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'src/topl.c'\"
else
echo shar: Extracting \"'src/topl.c'\" \(5783 characters\)
sed "s/^X//" >'src/topl.c' <<'END_OF_FILE'
X/*	SCCS Id: @(#)topl.c	3.0	89/01/09
X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
X/* NetHack may be freely redistributed.  See license for details. */
X
X#include "hack.h"
X
Xchar toplines[BUFSIZ];
Xxchar tlx, tly;			/* set by pline; used by addtopl */
X
Xstruct topl {
X	struct topl *next_topl;
X	char *topl_text;
X} *old_toplines, *last_redone_topl;
X#define	OTLMAX	20		/* max nr of old toplines remembered */
X
Xstatic void
Xredotoplin() {
X	home();
X	if(index(toplines, '\n')) cl_end();
X	if((*toplines & 0x80) && AS) {
X		/* kludge for the / command, the only time we ever want a */
X		/* graphics character on the top line */
X		putstr(AS);
X		xputc(*toplines);
X		putstr(AE);
X		putstr(toplines+1);
X	} else putstr(toplines);
X	cl_end();
X	tlx = curx;
X	tly = cury;
X	flags.toplin = 1;
X	if(tly > 1)
X		more();
X}
X
Xint
Xdoredotopl(){
X	if(last_redone_topl)
X		last_redone_topl = last_redone_topl->next_topl;
X	if(!last_redone_topl)
X		last_redone_topl = old_toplines;
X	if(last_redone_topl){
X		Strcpy(toplines, last_redone_topl->topl_text);
X	}
X	redotoplin();
X	return 0;
X}
X
Xvoid
Xremember_topl() {
X	register struct topl *tl;
X	register int cnt = OTLMAX;
X	if(last_redone_topl &&
X	   !strcmp(toplines, last_redone_topl->topl_text)) return;
X	if(old_toplines &&
X	   !strcmp(toplines, old_toplines->topl_text)) return;
X	last_redone_topl = 0;
X	tl = (struct topl *)
X		alloc((unsigned)(strlen(toplines) + sizeof(struct topl) + 1));
X	tl->next_topl = old_toplines;
X	tl->topl_text = (char *)(tl + 1);
X	Strcpy(tl->topl_text, toplines);
X	old_toplines = tl;
X	while(cnt && tl){
X		cnt--;
X		tl = tl->next_topl;
X	}
X	if(tl && tl->next_topl){
X		free((genericptr_t) tl->next_topl);
X		tl->next_topl = 0;
X	}
X}
X
Xvoid
Xaddtopl(s) char *s; {
X	curs(tlx,tly);
X	if(tlx + strlen(s) > CO) putsym('\n');
X	putstr(s);
X	tlx = curx;
X	tly = cury;
X	flags.toplin = 1;
X}
X
Xstatic void
Xxmore(s)
Xchar *s;	/* allowed chars besides space/return */
X{
X	if(flags.toplin) {
X		curs(tlx, tly);
X		if(tlx + 8 > CO) putsym('\n'), tly++;
X	}
X
X	if(flags.standout)
X		standoutbeg();
X	putstr("--More--");
X	if(flags.standout)
X		standoutend();
X
X	xwaitforspace(s);
X	if(flags.toplin && tly > 1) {
X		home();
X		cl_end();
X		docorner(1, tly-1);
X		tlx = tly = 1;
X	}
X	flags.toplin = 0;
X}
X
Xvoid
Xmore(){
X	xmore("");
X}
X
Xvoid
Xcmore(s)
Xregister char *s;
X{
X	xmore(s);
X}
X
Xvoid
Xclrlin(){
X	if(flags.toplin) {
X		home();
X		cl_end();
X		if(tly > 1) {
X			docorner(1, tly-1);
X			tlx = tly = 1;
X		}
X		remember_topl();
X	}
X	flags.toplin = 0;
X}
X
X/*VARARGS1*/
X/* Because the modified mstatusline has 9 arguments KAA */
Xvoid
Xpline(line,arg1,arg2,arg3,arg4,arg5,arg6,arg7,arg8,arg9)
X#ifndef TOS
Xregister
X#endif
Xconst char *line,*arg1,*arg2,*arg3,*arg4,*arg5,*arg6,*arg7,*arg8,*arg9;
X{
X	char pbuf[BUFSZ];
X	register char *bp = pbuf, *tl;
X	register int n,n0;
X
X	if(!line || !*line) return;
X	if(!index(line, '%')) Strcpy(pbuf,line); else
X	Sprintf(pbuf,line,arg1,arg2,arg3,arg4,arg5,arg6,arg7,arg8,arg9);
X/*	if(flags.toplin == 1 && !strcmp(pbuf, toplines)) return;*/
X	nscr();		/* %% */
X
X	/* If there is room on the line, print message on same line */
X	/* But messages like "You die..." deserve their own line */
X	n0 = strlen(bp);
X	if(flags.toplin == 1 && tly == 1 &&
X	    n0 + strlen(toplines) + 3 < CO-8 &&  /* leave room for --More-- */
X	    strncmp(bp, "You die", 7)) {
X		Strcat(toplines, "  ");
X		Strcat(toplines, bp);
X		tlx += 2;
X		addtopl(bp);
X		return;
X	}
X	if(flags.toplin == 1 && !strcmp(pbuf, toplines) &&
X	    (n0 + strlen(toplines) + 3 >= CO-8)) {
X		more();
X		home();
X		putstr("");
X		cl_end();
X		goto again;
X	}
X	if(flags.toplin == 1) more();
X	else if(tly > 1) {	/* for when flags.toplin == 2 && tly > 1 */
X		docorner(1, tly-1);	/* reset tly = 1 if redraw screen */
X		tlx = tly = 1;	/* from home--cls() and docorner(1,n) */
X	}
Xagain:
X	remember_topl();
X	toplines[0] = 0;
X	while(n0){
X		if(n0 >= CO){
X			/* look for appropriate cut point */
X			n0 = 0;
X			for(n = 0; n < CO; n++) if(bp[n] == ' ')
X				n0 = n;
X			if(!n0) for(n = 0; n < CO-1; n++)
X				if(!letter(bp[n])) n0 = n;
X			if(!n0) n0 = CO-2;
X		}
X		(void) strncpy((tl = eos(toplines)), bp, n0);
X		tl[n0] = 0;
X		bp += n0;
X
X		/* remove trailing spaces, but leave one */
X		while(n0 > 1 && tl[n0-1] == ' ' && tl[n0-2] == ' ')
X			tl[--n0] = 0;
X
X		n0 = strlen(bp);
X		if(n0 && tl[0]) Strcat(tl, "\n");
X	}
X	redotoplin();
X}
X
X/*VARARGS1*/
Xvoid
XYou(line,arg1,arg2,arg3,arg4,arg5,arg6,arg7,arg8,arg9)
X#ifndef TOS
Xregister
X#endif
Xconst char *line,*arg1,*arg2,*arg3,*arg4,*arg5,*arg6,*arg7,*arg8,*arg9;
X{
X	char *tmp;
X	tmp = (char *)alloc((unsigned int)(strlen(line) + 5));
X	Strcpy(tmp, "You ");
X	Strcat(tmp, line);
X	pline(tmp, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8, arg9);
X	free(tmp);
X	return;
X}
X
X/*VARARGS1*/
Xvoid
XYour(line,arg1,arg2,arg3,arg4,arg5,arg6,arg7,arg8,arg9)
X#ifndef TOS
Xregister
X#endif
Xconst char *line,*arg1,*arg2,*arg3,*arg4,*arg5,*arg6,*arg7,*arg8,*arg9;
X{
X	char *tmp;
X	tmp = (char *)alloc((unsigned int)(strlen(line) + 6));
X	Strcpy(tmp, "Your ");
X	Strcat(tmp, line);
X	pline(tmp, arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8, arg9);
X	free(tmp);
X	return;
X}
X
Xvoid
Xputsym(c)
Xchar c;
X{
X	switch(c) {
X	case '\b':
X		backsp();
X		curx--;
X		if(curx == 1 && cury > 1)
X			curs(CO, cury-1);
X		return;
X	case '\n':
X		curx = 1;
X		cury++;
X		if(cury > tly) tly = cury;
X		break;
X	default:
X		if(curx == CO)
X			putsym('\n');	/* 1 <= curx <= CO; avoid CO */
X		curx++;
X	}
X	(void) putchar(c);
X}
X
Xvoid
Xputstr(s)
Xregister char *s;
X{
X	while(*s) putsym(*s++);
X}
X
Xchar
Xyn_function(resp, def)
Xchar *resp, def;
X/*
X *   Generic yes/no function
X */
X{
X	register char q;
X	char rtmp[8];
X
X	Sprintf(rtmp, "[%s] ", resp);
X	addtopl(rtmp);
X
X	do {
X		q = lowc(readchar());
X
X		if (index(quitchars, q)) q = def;
X		else if (!index(resp, q)) {
X			bell();
X			q = (char)0;
X		}
X	} while(!q);
X
X	Sprintf(rtmp, "%c", q);
X	addtopl(rtmp);
X	flags.toplin = 2;
X
X	return q;
X}
END_OF_FILE
if test 5783 -ne `wc -c <'src/topl.c'`; then
    echo shar: \"'src/topl.c'\" unpacked with wrong size!
fi
# end of 'src/topl.c'
fi
if test -f 'src/wield.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'src/wield.c'\"
else
echo shar: Extracting \"'src/wield.c'\" \(5838 characters\)
sed "s/^X//" >'src/wield.c' <<'END_OF_FILE'
X/*	SCCS Id: @(#)wield.c	3.0	87/05/10
X/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
X/* NetHack may be freely redistributed.  See license for details. */
X
X#include	"hack.h"
X
X/* Note: setuwep() with a null obj, and uwepgone(), are NOT the same!  Sometimes
X * unwielding a weapon can kill you, and lifesaving will then put it back into
X * your hand.  If lifesaving is permitted to do this, use
X * setwuep((struct obj *)0); otherwise use uwepgone().
X * (The second function should probably be #ifdef NAMED_ITEMS since only then
X * may unwielding a weapon kill you, but...)
X */
Xvoid
Xsetuwep(obj)
Xregister struct obj *obj;
X{
X	setworn(obj, W_WEP);
X	if (!obj) unweapon = TRUE;	/* for "bare hands" message */
X}
X
Xvoid
Xuwepgone()
X{
X	if (uwep) {
X		setnotworn(uwep);
X		unweapon = TRUE;
X	}
X}
X
Xstatic const char wield_objs[] = { '#', '-', WEAPON_SYM, 0 };
X
Xint
Xdowield()
X{
X	register struct obj *wep;
X	register int res = 0;
X
X	multi = 0;
X#ifdef POLYSELF
X	if (cantwield(uasmon)) {
X		pline("Don't be ridiculous!");
X		return(0);
X	}
X#endif
X	if(!(wep = getobj(wield_objs, "wield"))) /* nothing */;
X	else if(uwep == wep)
X		You("are already wielding that!");
X	else if(welded(uwep))
X		weldmsg(uwep, TRUE);
X	else if(wep == &zeroobj) {
X	    if(uwep == 0)
X		You("are already empty %s.", body_part(HANDED));
X	    else  {
X	  	You("are empty %s.", body_part(HANDED));
X	  	setuwep((struct obj *) 0);
X	  	res++;
X	    }
X	} else if(!uarmg &&
X#ifdef POLYSELF
X		!resists_ston(uasmon) &&
X#endif
X		(wep->otyp == CORPSE && wep->corpsenm == PM_COCKATRICE)) {
X	    /* Prevent wielding cockatrice when not wearing gloves --KAA */
X	    You("wield the cockatrice corpse in your bare %s.",
X			makeplural(body_part(HAND)));
X	    You("turn to stone...");
X	    killer="cockatrice corpse";
X	    done("stoned");
X	} else if(uarms && bimanual(wep))
X	    You("cannot wield a two-handed %s and hold a shield.",
X		 is_sword(wep) ? "sword" : "weapon");
X	else if(wep->owornmask & (W_ARMOR | W_RING | W_AMUL | W_TOOL))
X		You("cannot wield that!");
X	else {
X		res++;
X		if(wep->cursed && (wep->olet == WEAPON_SYM ||
X			wep->otyp == HEAVY_IRON_BALL || wep->otyp == PICK_AXE ||
X			wep->otyp == TIN_OPENER)) {
X		    pline("The %s %s to your %s!",
X			aobjnam(wep, "weld"),
X			(wep->quan == 1) ? "itself" : "themselves", /* a3 */
X			body_part(HAND));
X		    wep->bknown = 1;
X		} else {
X			/* The message must be printed before setuwep (since
X			 * you might die and be revived from changing weapons),
X			 * and the message must be before the death message and
X			 * Lifesaved rewielding.  Yet we want the message to say
X			 * "weapon in hand", thus this kludge.
X			 */
X			long dummy = wep->owornmask;
X			wep->owornmask |= W_WEP;
X			prinv(wep);
X			wep->owornmask = dummy;
X		}
X		setuwep(wep);
X	}
X	if(res && uwep)
X		unweapon = (uwep->otyp >= BOW || uwep->otyp <= BOOMERANG) ?
X		TRUE : FALSE;
X	return(res);
X}
X
Xvoid
Xcorrode_weapon(){
X	if(!uwep || uwep->olet != WEAPON_SYM) return;	/* %% */
X	if(uwep->rustfree || objects[uwep->otyp].oc_material != METAL)
X		Your("%s not affected.", aobjnam(uwep, "are"));
X	else if (uwep->spe > -6) {
X		Your("%s!", aobjnam(uwep, "corrode"));
X		uwep->spe--;
X	} else	Your("%s quite rusted now.", aobjnam(uwep, "look"));
X}
X
Xint
Xchwepon(otmp, amount)
Xregister struct obj *otmp;
Xregister int amount;
X{
X	register const char *color = Hallucination ? hcolor() :
X				     (amount < 0) ? black : blue;
X	register char *xtime;
X
X	if(!uwep || (uwep->olet != WEAPON_SYM && uwep->otyp != PICK_AXE)) {
X		char buf[36];
X
X		Sprintf(buf, "Your %s %s.", makeplural(body_part(HAND)),
X			(amount > 0) ? "twitch" : "itch");
X		strange_feeling(otmp, buf);
X		return(0);
X	}
X
X#ifdef WORM
X	if(uwep->otyp == WORM_TOOTH && amount > 0) {
X		uwep->otyp = CRYSKNIFE;
X		Your("weapon seems sharper now.");
X		uwep->cursed = 0;
X		return(1);
X	}
X
X	if(uwep->otyp == CRYSKNIFE && amount < 0) {
X		uwep->otyp = WORM_TOOTH;
X		Your("weapon looks duller now.");
X		return(1);
X	}
X#endif
X#ifdef NAMED_ITEMS
X	if(is_artifact(uwep) && restr_name(uwep, ONAME(uwep)) &&
X		amount<0) {
X	    if (!Blind)
X		Your("%s faintly %s.", aobjnam(uwep, "glow"), color);
X	    return(1);
X	}
X#endif
X	/* there is a (soft) upper and lower limit to uwep->spe */
X	if(abs(uwep->spe) > 5 && rn2(3)) {
X	    if (!Blind)
X	    Your("%s violently %s for a while and then evaporate%s.",
X		aobjnam(uwep,"glow"), color, uwep->quan == 1 ? "s" : "");
X	    else
X		Your("%s.", aobjnam(uwep, "evaporate"));
X
X	    while(uwep)		/* let all of them disappear */
X				/* note: uwep->quan = 1 is nogood if unpaid */
X		useup(uwep);
X	    return(1);
X	}
X	if (!Blind) {
X	    xtime = (amount*amount == 1) ? "moment" : "while";
X	    Your("%s %s for a %s.",
X		  aobjnam(uwep, "glow"), color, xtime);
X	}
X	uwep->spe += amount;
X	if(amount > 0) uwep->cursed = 0;
X	return(1);
X}
X
Xint
Xwelded(obj)
Xregister struct obj *obj;
X{
X	if (obj && obj == uwep && obj->cursed &&
X		  (obj->olet == WEAPON_SYM || obj->otyp == HEAVY_IRON_BALL ||
X		   obj->otyp == TIN_OPENER || obj->otyp == PICK_AXE))
X	{
X		obj->bknown = 1;
X		return 1;
X	}
X	return 0;
X}
X
X/* The reason for "specific" is historical; some parts of the code used
X * the object name and others just used "weapon"/"sword".  This function
X * replaced all of those.  Which one we use is really arbitrary.
X */
Xvoid
Xweldmsg(obj, specific)
Xregister struct obj *obj;
Xboolean specific;
X{
X	char buf[BUFSZ];
X
X	if (specific) {
X		long savewornmask = obj->owornmask;
X		obj->owornmask &= ~W_WEP;
X		Strcpy(buf, Doname2(obj));
X		obj->owornmask = savewornmask;
X	} else
X		Sprintf(buf, "Your %s%s",
X			is_sword(obj) ? "sword" : "weapon",
X			((obj->quan > 1) ? "s" : ""));
X	Strcat(buf, (obj->quan==1) ? " is" : " are");
X#ifdef POLYSELF
X	Sprintf(eos(buf), " welded to your %s!",
X		bimanual(obj) ? makeplural(body_part(HAND)) : body_part(HAND));
X#else
X	Sprintf(eos(buf), " welded to your hand%s!",
X		bimanual(obj) ? "s" : "");
X#endif
X	pline(buf);
X}
END_OF_FILE
if test 5838 -ne `wc -c <'src/wield.c'`; then
    echo shar: \"'src/wield.c'\" unpacked with wrong size!
fi
# end of 'src/wield.c'
fi
echo shar: End of archive 33 \(of 38\).
cp /dev/null ark33isdone
MISSING=""
for I in 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 ; do
    if test ! -f ark${I}isdone ; then
	MISSING="${MISSING} ${I}"
    fi
done
if test "${MISSING}" = "" ; then
    echo You have unpacked all 38 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