-/* SCCS Id: @(#)extern.h 3.4 2002/03/29 */
+/* SCCS Id: @(#)extern.h 3.4 2002/08/22 */
/* Copyright (c) Steve Creps, 1988. */
/* NetHack may be freely redistributed. See license for details. */
E void NDECL(set_lock_and_bones);
#endif
E void FDECL(set_levelfile_name, (char *,int));
-E int FDECL(create_levelfile, (int));
-E int FDECL(open_levelfile, (int));
+E int FDECL(create_levelfile, (int,char *));
+E int FDECL(open_levelfile, (int,char *));
E void FDECL(delete_levelfile, (int));
E void NDECL(clearlocks);
E int FDECL(create_bonesfile, (d_level*,char **));
E void FDECL(inven_inuse, (BOOLEAN_P));
E int FDECL(dorecover, (int));
-E void NDECL(trickery);
+E void FDECL(trickery, (char *));
E void FDECL(getlev, (int,int,XCHAR_P,BOOLEAN_P));
E void NDECL(minit);
E boolean FDECL(lookup_id_mapping, (unsigned, unsigned *));
#include "hack.h"
#include "lev.h"
-#include <errno.h>
-#ifdef _MSC_VER /* MSC 6.0 defines errno quite differently */
-# if (_MSC_VER >= 600)
-# define SKIP_ERRNO
-# endif
-#endif
-#ifndef SKIP_ERRNO
-#ifdef _DCC
-const
-#endif
-extern int errno;
-#endif
-
#ifdef SINKS
# ifdef OVLB
STATIC_DCL void FDECL(trycall, (struct obj *));
currentlevel_rewrite()
{
register int fd;
+ char whynot[BUFSZ];
/* since level change might be a bit slow, flush any buffered screen
* output (like "you fall through a trap door") */
mark_synch();
- fd = create_levelfile(ledger_no(&u.uz));
-
- if(fd < 0) {
+ fd = create_levelfile(ledger_no(&u.uz), whynot);
+ if (fd < 0) {
/*
* This is not quite impossible: e.g., we may have
* exceeded our quota. If that is the case then we
* Another possibility is that the directory was not
* writable.
*/
- pline("Cannot create level file for level %d.",
- ledger_no(&u.uz));
+ pline("%s", whynot);
return -1;
}
familiar = FALSE;
boolean new = FALSE; /* made a new level? */
struct monst *mtmp;
+ char whynot[BUFSZ];
if (dunlev(newlevel) > dunlevs_in_dungeon(newlevel))
newlevel->dlevel = dunlevs_in_dungeon(newlevel);
new = TRUE; /* made the level */
} else {
/* returning to previously visited level; reload it */
- fd = open_levelfile(new_ledger);
+ fd = open_levelfile(new_ledger, whynot);
if (fd < 0) {
- pline("Cannot open file (#%d) for level %d (errno %d).",
- (int) new_ledger, depth(&u.uz), errno);
+ pline("%s", whynot);
pline("Probably someone removed it.");
+ killer = whynot;
done(TRICKED);
/* we'll reach here if running in wizard mode */
error("Cannot continue this game.");
-/* SCCS Id: @(#)end.c 3.4 2001/09/24 */
+/* SCCS Id: @(#)end.c 3.4 2002/08/22 */
/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
/* NetHack may be freely redistributed. See license for details. */
struct obj *corpse = (struct obj *)0;
long umoney;
+ if (how == TRICKED) {
+ if (killer) {
+ paniclog("trickery", killer);
+ killer = 0;
+ }
+#ifdef WIZARD
+ if (wizard) {
+ You("are a very tricky wizard, it seems.");
+ return;
+ }
+#endif
+ }
+
/* kilbuf: used to copy killer in case it comes from something like
* xname(), which would otherwise get overwritten when we call
* xname() when listing possessions
killer_format = KILLED_BY;
Strcpy(kilbuf, (!killer || how >= PANICKED ? deaths[how] : killer));
killer = kilbuf;
-#ifdef WIZARD
- if (wizard && how == TRICKED) {
- You("are a very tricky wizard, it seems.");
- return;
- }
-#endif
+
if (how < PANICKED) u.umortality++;
if (Lifesaved && (how <= GENOCIDED)) {
pline("But wait...");
#include <fcntl.h>
#endif
-#if defined(NOCWD_ASSUMPTIONS)
#include <errno.h>
+#ifdef _MSC_VER /* MSC 6.0 defines errno quite differently */
+# if (_MSC_VER >= 600)
+# define SKIP_ERRNO
+# endif
+#endif
+#ifndef SKIP_ERRNO
+# ifdef _DCC
+const
+# endif
+extern int errno;
#endif
#if defined(UNIX) && defined(QT_GRAPHICS)
#endif
#if defined(UNIX) || defined(VMS)
-#include <errno.h>
-# ifndef SKIP_ERRNO
-extern int errno;
-# endif
#include <signal.h>
#endif
}
int
-create_levelfile(lev)
+create_levelfile(lev, errbuf)
int lev;
+char errbuf[];
{
int fd;
const char *fq_lock;
+ if (errbuf) *errbuf = '\0';
set_levelfile_name(lock, lev);
fq_lock = fqname(lock, LEVELPREFIX, 0);
if (fd >= 0)
level_info[lev].flags |= LFILE_EXISTS;
+ else if (errbuf) /* failure explanation */
+ Sprintf(errbuf,
+ "Cannot create file \"%s\" for level %d (errno %d).",
+ lock, lev, errno);
return fd;
}
int
-open_levelfile(lev)
+open_levelfile(lev, errbuf)
int lev;
+char errbuf[];
{
int fd;
const char *fq_lock;
+ if (errbuf) *errbuf = '\0';
set_levelfile_name(lock, lev);
fq_lock = fqname(lock, LEVELPREFIX, 0);
#ifdef MFLOPPY
# endif
fd = open(fq_lock, O_RDONLY | O_BINARY, 0);
#endif
+
+ /* for failure, return an explanation that our caller can use;
+ settle for `lock' instead of `fq_lock' because the latter
+ might end up being too big for nethack's BUFSZ */
+ if (fd < 0 && errbuf)
+ Sprintf(errbuf,
+ "Cannot open file \"%s\" for level %d (errno %d).",
+ lock, lev, errno);
+
return fd;
}
{
if (lftrack.fd == fd) {
really_close(); /* close it, but reopen it to hold it */
- fd = open_levelfile(0);
+ fd = open_levelfile(0, (char *)0);
lftrack.nethack_thinks_it_is_open = FALSE;
return 0;
}
xchar levc;
struct version_info version_data;
int processed[256];
- char savename[SAVESIZE];
+ char savename[SAVESIZE], errbuf[BUFSZ];
for (lev = 0; lev < 256; lev++)
processed[lev] = 0;
* name of save file nethack would have created
* and game state
*/
- gfd = open_levelfile(0);
+ gfd = open_levelfile(0, errbuf);
if (gfd < 0) {
- raw_printf("Cannot open level 0 for %s.\n", lock);
+ raw_printf("%s\n", errbuf);
return FALSE;
}
if (read(gfd, (genericptr_t) &hpid, sizeof hpid) != sizeof hpid) {
return FALSE;
}
- lfd = open_levelfile(savelev);
+ lfd = open_levelfile(savelev, errbuf);
if (lfd < 0) {
- raw_printf("\nCannot open level of save for %s.\n", lock);
+ raw_printf("\n%s\n", errbuf);
(void)close(gfd);
(void)close(sfd);
delete_savefile();
* maximum level number (for the endlevel) must be < 256
*/
if (lev != savelev) {
- lfd = open_levelfile(lev);
+ lfd = open_levelfile(lev, (char *)0);
if (lfd >= 0) {
/* any or all of these may not exist */
levc = (xchar) lev;
#endif
{
register int nfd;
+ char whynot[BUFSZ];
- nfd = create_levelfile(ltmp);
-
- if (nfd < 0) panic("Cannot open temp level %d!", ltmp);
+ nfd = create_levelfile(ltmp, whynot);
+ if (nfd < 0) {
+ /* BUG: should suppress any attempt to write a panic
+ save file if file creation is now failing... */
+ panic("restlevelfile: %s", whynot);
+ }
#ifdef MFLOPPY
if (!savelev(nfd, ltmp, COUNT_SAVE)) {
}
void
-trickery()
+trickery(reason)
+char *reason;
{
pline("Strange, this map is not as I remember it.");
pline("Somebody is trying some trickery here...");
pline("This game is void.");
+ killer = reason;
done(TRICKED);
}
#else
mread(fd, (genericptr_t) &dlvl, sizeof(dlvl));
#endif
- if((pid && pid != hpid) || (lev && dlvl != lev)) {
+ if ((pid && pid != hpid) || (lev && dlvl != lev)) {
+ char trickbuf[BUFSZ];
+
+ if (pid && pid != hpid)
+ Sprintf(trickbuf, "PID (%d) doesn't match saved PID (%d)!",
+ hpid, pid);
+ else
+ Sprintf(trickbuf, "This is level %d, not %d!", dlvl, lev);
#ifdef WIZARD
- if (wizard) {
- if (pid && pid != hpid)
- pline("PID (%d) doesn't match saved PID (%d)!", hpid, pid);
- else if (lev && dlvl != lev)
- pline("This is level %d, not %d!", dlvl, lev);
- }
+ if (wizard) pline(trickbuf);
#endif
- trickery();
+ trickery(trickbuf);
}
#ifdef RLECOMP
-/* SCCS Id: @(#)save.c 3.4 2002/01/19 */
+/* SCCS Id: @(#)save.c 3.4 2002/08/22 */
/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
/* NetHack may be freely redistributed. See license for details. */
#include "hack.h"
#include "lev.h"
+#include "quest.h"
#ifndef NO_SIGNAL
#include <signal.h>
#include <fcntl.h>
#endif
-#include "quest.h"
-
#ifdef MFLOPPY
long bytes_counted;
static int count_only;
register int fd, ofd;
xchar ltmp;
d_level uz_save;
+ char whynot[BUFSZ];
if (!SAVEF[0])
return 0;
HUP mark_synch(); /* flush any buffered screen output */
fd = create_savefile();
-
if(fd < 0) {
HUP pline("Cannot open save file.");
(void) delete_savefile(); /* ab@unido */
}
mark_synch();
#endif
- ofd = open_levelfile(ltmp);
+ ofd = open_levelfile(ltmp, whynot);
if (ofd < 0) {
- HUP pline("Cannot read level %d.", ltmp);
+ HUP pline("%s", whynot);
(void) close(fd);
(void) delete_savefile();
+ HUP killer = whynot;
HUP done(TRICKED);
return(0);
}
{
int fd, hpid;
static boolean havestate = TRUE;
+ char whynot[BUFSZ];
/* When checkpointing is on, the full state needs to be written
* on each checkpoint. When checkpointing is off, only the pid
* to any internal compression schemes since they must be
* readable by an external utility
*/
- fd = open_levelfile(0);
+ fd = open_levelfile(0, whynot);
if (fd < 0) {
- pline("Cannot open level 0.");
+ pline("%s", whynot);
pline("Probably someone removed it.");
+ killer = whynot;
done(TRICKED);
return;
}
(void) read(fd, (genericptr_t) &hpid, sizeof(hpid));
if (hackpid != hpid) {
- pline("Level 0 pid bad!");
+ Sprintf(whynot,
+ "Level #0 pid (%d) doesn't match ours (%d)!",
+ hpid, hackpid);
+ pline("%s", whynot);
+ killer = whynot;
done(TRICKED);
}
(void) close(fd);
- fd = create_levelfile(0);
+ fd = create_levelfile(0, whynot);
if (fd < 0) {
- pline("Cannot rewrite level 0.");
+ pline("%s", whynot);
+ killer = whynot;
done(TRICKED);
return;
}
-/* SCCS Id: @(#)pcmain.c 3.4 1997/01/22 */
+/* SCCS Id: @(#)pcmain.c 3.4 2002/08/22 */
/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
/* NetHack may be freely redistributed. See license for details. */
/* Set up level 0 file to keep the game state.
*/
- fd = create_levelfile(0);
+ fd = create_levelfile(0, (char *)0);
if (fd < 0) {
raw_print("Cannot create lock file");
} else {