Source:NetHack 3.0.0/end.c

Below is the full text to end.c from the source code of NetHack 3.0.0. To link to a particular line, write [[NetHack 3.0.0/end.c#line123 ]], for example.

Warning! This is the source code from an old release. For the latest release, see Source code

1.   /*	SCCS Id: @(#)end.c	3.0	88/05/03 2.   /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */ 3.    /* NetHack may be freely redistributed. See license for details. */ 4.     5.    #ifndef TOS 6.   #include   7.    #endif 8.    9.    /* block some unused #defines to avoid overloading some cpp's */ 10.  #define MONATTK_H 11.  #include "hack.h"  12. 13.  #include "eshk.h"  14. 15.  void end_box_display; 16.   17.   int 18.  done1 19.  {  20.   #ifndef TOS 21.  	(void) signal(SIGINT,SIG_IGN); 22.  #endif 23.  	if(flags.ignintr) { 24.  #ifndef TOS 25.  		(void) signal(SIGINT, (SIG_RET_TYPE) done1); 26.  #endif 27.  		clrlin; 28.  		curs_on_u; 29.  		(void) fflush(stdout); 30.  		if(multi > 0) nomul(0); 31.  		return 0; 32.  	}  33.   	return done2; 34.  }  35.    36.   int 37.  done2 38.  {  39.   	pline("Really quit? "); 40.  	if(yn == 'n') { 41.  #ifndef TOS 42.  		(void) signal(SIGINT, (SIG_RET_TYPE) done1); 43.  #endif 44.  		clrlin; 45.  		curs_on_u; 46.  		(void) fflush(stdout); 47.  		if(multi > 0) nomul(0); 48.  		return 0; 49.  	}  50.   #if defined(WIZARD) && defined(UNIX) 51.  	if(wizard) { 52.  	    pline("Dump core? "); 53.  	    if(yn == 'y') { 54.  		(void) signal(SIGINT, (SIG_RET_TYPE) done1); 55.  		settty(NULL); 56.  #ifdef SYSV 57.  		(void) 58.  #endif 59.  		    abort; 60.  	    }  61.   	}  62.   #endif 63.  #ifndef LINT 64.  	done("quit"); 65.  #endif 66.  	return 0; 67.  }  68.    69.   static 70.  int 71.  done_intr{ 72.  	done_stopprint++; 73.  #ifndef TOS 74.  	(void) signal(SIGINT, SIG_IGN); 75.  #ifdef UNIX 76.  	(void) signal(SIGQUIT, SIG_IGN); 77.  #endif 78.  #endif /* TOS /* */ 79.  	return 0; 80.  }  81.    82.   #ifdef UNIX 83.  static 84.  int 85.  done_hangup{ 86.  	done_hup++; 87.  	(void)signal(SIGHUP, SIG_IGN); 88.  	(void)done_intr; 89.  	return 0; 90.  }  91.   #endif 92.   93.   void 94.  done_in_by(mtmp) 95.  register struct monst *mtmp; 96.  {  97.   	char buf[BUFSZ]; 98.   99.   	You("die..."); 100. 	buf[0] = '\0'; 101. 	if (mtmp->minvis) 102. 		Sprintf(eos(buf), "invisible "); 103. 	if (Hallucination) 104. 		Sprintf(eos(buf), "hallucinogen-distorted "); 105.  106.  	if(mtmp->data->mlet == S_GHOST) { 107. 		register char *gn = (char *) mtmp->mextra; 108. 		if (!Hallucination && !mtmp->minvis && *gn) 109. 			Sprintf(eos(buf), "the "); 110. 		Sprintf(eos(buf), (*gn ? "ghost of %s" : "ghost%s"), gn); 111. 	} else if(mtmp->isshk) { 112. 		Sprintf(eos(buf), "%s %s, the shopkeeper",  113.  			(ESHK(mtmp)->ismale ? "Mr." : "Ms."), shkname(mtmp)); 114. 	} else if (mtmp->iswiz) 115. 		Sprintf(eos(buf), "the %s", mons[PM_WIZARD_OF_YENDOR].mname); 116. 	else Sprintf(eos(buf), "%s", mtmp->data->mname); 117. 	if (mtmp->mnamelth) Sprintf(eos(buf), " called %s", NAME(mtmp)); 118. 	killer = buf; 119. 	if (mtmp->data->mlet == S_WRAITH) 120. 		u.ugrave_arise = PM_WRAITH; 121. 	else if (mtmp->data->mlet == S_MUMMY) 122. 		u.ugrave_arise = (pl_character[0]=='E') ? 123. 						PM_ELF_MUMMY : PM_HUMAN_MUMMY; 124. 	else if (mtmp->data->mlet == S_VAMPIRE) 125. 		u.ugrave_arise = PM_VAMPIRE; 126. 	if (u.ugrave_arise > -1 && (mons[u.ugrave_arise].geno & G_GENOD)) 127. 		u.ugrave_arise = -1; 128. 	if (mtmp->data->mlet == S_COCKATRICE) 129. 		done("stoned"); 130. 	else 131. 		done("died"); 132. 	return; 133. }  134.   135.  /*VARARGS1*/ 136. boolean panicking; 137. extern boolean hu;	/* from save.c */ 138.  139.  void 140. panic(str,a1,a2,a3,a4,a5,a6) 141. char *str; 142. {  143.  	if(panicking++) 144. #ifdef SYSV 145. 	    (void) 146. #endif 147. 		abort;    /* avoid loops - this should never happen*/ 148. 				    /* was exit(1) */ 149. 	home; cls; 150. 	(void) puts(" Suddenly, the dungeon collapses."); 151. #ifdef WIZARD 152. # ifndef MSDOS 153. 	if(!wizard) { 154. 	    pline("Report error to %s and it may be possible to rebuild.",WIZARD); 155. 	    more; 156. 	}  157.  	Sprintf (SAVEF, "%s.e", SAVEF); 158. 	hu = FALSE; 159. 	(void) dosave0; 160. # endif 161. #endif 162. 	(void) fputs(" ERROR:  ", stdout); 163. 	Printf(str,a1,a2,a3,a4,a5,a6); 164. 	more;				/* contains a fflush */ 165. #ifdef WIZARD 166. # ifdef UNIX 167. 	if (wizard) 168. #  ifdef SYSV 169. 		(void) 170. #  endif 171. 		    abort;	/* generate core dump */ 172. # endif 173. #endif 174. 	done("panicked"); 175. }  176.   177.  /* called with arg "died", "drowned", "escaped", "quit", "choked", "panicked", 178.    "burned", "starved", "stoned", or "tricked" */ 179. /* Be careful not to call panic from here! */ 180.  void 181. done(st1) 182. register char *st1; 183. {  184.  	struct permonst *upmon; 185. 	char buf[BUFSZ], buf1[BUFSZ], buf2[BUFSZ]; 186. 	char	c; 187. 	boolean taken; 188. #ifdef WIZARD 189. 	if (wizard && *st1=='t') { 190. 		You("are a very tricky wizard, it seems."); 191. 		return; 192. 	}  193.  #endif 194. 	if(Lifesaved && index("bcds", *st1)){ 195. 		u.uswldtim = 0; 196. 		if(u.uhpmax < 0) u.uhpmax = 10;	/* arbitrary */ 197. 		u.uhp = u.uhpmax; 198. 		adjattrib(A_CON, -1, TRUE); 199. 		pline("But wait..."); 200. 		makeknown(AMULET_OF_LIFE_SAVING); 201. 		Your("medallion %s!",  202.  		      !Blind ? "begins to glow" : "feels warm"); 203. 		You("feel much better!"); 204. 		pline("The medallion crumbles to dust!"); 205. 		useup(uamul); 206. 		Lifesaved = 0; 207. 		if (u.uhunger < 500) u.uhunger = 500; 208. 		nomovemsg = "You survived that attempt on your life."; 209. 		curs_on_u; 210. 		flags.move = 0; 211. 		if(multi > 0) multi = 0; else multi = -1; 212. 		flags.botl = 1; 213. 		u.ugrave_arise = -1; 214. 		if (!strncmp(killer, "genocide", 8)) { 215. 			pline("Unfortunately you are still genocided..."); 216. 			done("died"); 217. 		}  218.  		return; 219. 	}  220.  #if defined(WIZARD) || defined(EXPLORE_MODE) 221. 	if((wizard || discover) && index("bcds", *st1)){ 222. 		pline("Die? "); 223. 		if(yn == 'y') goto die; 224. 		u.uswldtim = 0; 225. 		if(u.uhpmax < 0) u.uhpmax = 100;	/* arbitrary */ 226. 		u.uhp = u.uhpmax; 227. 		if (u.uhunger < 500) u.uhunger = 500; 228. 		pline("Ok, so you don't die."); 229. 		nomovemsg = "You survived that attempt on your life."; 230. 		curs_on_u; 231. 		flags.move = 0; 232. 		if(multi > 0) multi = 0; else multi = -1; 233. 		flags.botl = 1; 234. 		u.ugrave_arise = -1; 235. 		return; 236. 	}  237.  #endif /* WIZARD || EXPLORE_MODE */ 238. die: 239. #ifndef TOS 240. 	(void) signal(SIGINT, (SIG_RET_TYPE) done_intr); 241. #ifdef UNIX 242. 	(void) signal(SIGQUIT, (SIG_RET_TYPE) done_intr); 243. 	(void) signal(SIGHUP, (SIG_RET_TYPE) done_hangup); 244. #endif 245. #endif /* TOS /* */ 246. 	upmon = player_mon; 247. 	if(u.ugrave_arise > -1) /* create no corpse */ ; 248. 	else if(*st1 == 's' && st1[2] == 'o') 249. 		(mk_named_object(STATUE, upmon, u.ux, u.uy, plname, 250. 					strlen(plname)))->spe = 0; 251. 	else 252. 		(void) mk_named_object(CORPSE, upmon, u.ux, u.uy, plname,  253.  							strlen(plname)); 254. 	if(*st1 == 'q' && u.uhp < 1){ 255. 		st1 = "died"; 256. 		killer = "quit while already on Charon's boat"; 257. 	}  258.  	if(*st1 == 's' && st1[2] == 'a') killer = "starvation"; else 259. 	if(*st1 == 'd' && st1[1] == 'r') killer = "drowning"; else 260. 	if(*st1 == 'p') killer = "panic"; else 261. 	if(*st1 == 't') killer = "trickery"; else 262. 	if(!index("bcds", *st1)) killer = st1; 263. 	taken = paybill; 264. 	paygd; 265. 	clearlocks; 266. 	if(flags.toplin == 1) more; 267.  268.  	if(invent) { 269. 	    if(taken) 270. 		pline("Do you want to see what you had when you %s? ",  271.  			(*st1=='q') ? "quit" : "died"); 272. 	    else 273. 		pline("Do you want your possessions identified? "); 274. 	    /* New dump format by maartenj@cs.vu.nl */ 275. 	    if ((c = yn_function(ynqchars,'y')) == 'y') { 276. 		struct obj *obj; 277.  278.  		for(obj = invent; obj && !done_stopprint; obj = obj->nobj) { 279. 		    makeknown(obj->otyp); 280. 		    obj->known = obj->bknown = obj->dknown = 1; 281. 		}  282.  		doinv(NULL); 283. 		end_box_display; 284. 	    }  285.  	    if (c == 'q')  done_stopprint++; 286. 	    if (taken) { 287. 		/* paybill has already given the inventory locations in the shop 288. 		 * and put it on the main object list 289. 		 */  290.  		struct obj *obj; 291.  292.  		for(obj = invent; obj; obj = obj->nobj) { 293. 		    obj->owornmask = 0; 294. 		    if(rn2(5)) curse(obj); 295. 		}  296.  	        invent = (struct obj *) 0; 297. 	    }  298.  	}  299.   300.  	if(index("bcds", *st1)){ 301. #ifdef WIZARD 302. 	    if(wizard) { 303. 		pline("Save bones? "); 304. 		if(yn == 'y') savebones; 305. 	    }  else 306. #endif 307. 		savebones; 308. 	    if(!flags.notombstone) outrip; 309. 	}  310.  	if(*st1 == 'c') killer = st1;		/* after outrip */ 311. 	if(*st1 == 's' && st1[2] == 'o') { 312. 		Sprintf(buf, "turned to stone by %s",killer); 313. 		/* No a or an; topten.c will do that. */ 314.  		killer = buf; 315. 		st1 = "turned to stone"; 316. 	}  317.  	Strcpy(buf1, st1); 318. 	if(u.uhave_amulet) Strcat(killer," (with the Amulet)"); 319. 	settty(NULL);	/* does a clear_screen */ 320. 	Strcpy(buf2, plname); 321. 	if('a' <= buf2[0] && buf2[0] <= 'z') buf2[0] += 'A'-'a'; 322. 	if(!done_stopprint) 323. 	    Printf("Goodbye %s the %s...\n\n", buf2,  324.  #ifdef ENDGAME  325.  		   *st1 != 'a' ? pl_character : "Demigod"); 326. #else 327. 		   pl_character);  328.  #endif  329.  	{ long int tmp;  330.  	  tmp = u.ugold - u.ugold0;  331.  	  if(tmp < 0)  332.  		tmp = 0;  333.  	  if(*st1 == 'd' || *st1 == 'b')  334.  		tmp -= tmp/10;  335.  	  u.urexp += tmp;  336.  	  u.urexp += 50 * maxdlevel;  337.  	  if(maxdlevel > 20)  338.  		u.urexp += 1000*((maxdlevel > 30) ? 10 : maxdlevel - 20); 339.  #ifdef ENDGAME  340.  	  if(*st1 == 'a') u.urexp *= 2;  341.  #endif  342.  	}  343.  	if(*st1 == 'e') {  344.  		register struct monst *mtmp;  345.  		register struct obj *otmp;  346.  		long i;  347.  		register unsigned int worthlessct = 0;  348.   349.  		killer = st1;  350.  		keepdogs;  351.  		mtmp = mydogs;  352.  		if(mtmp) {  353.  			if(!done_stopprint) Printf("You");  354.  			while(mtmp) {  355.  				if(!done_stopprint)  356.  					Printf(" and %s", mon_nam(mtmp));  357.  				if(mtmp->mtame)  358.  					u.urexp += mtmp->mhp;  359.  				mtmp = mtmp->nmon;  360.  			}  361.  			if(!done_stopprint)  362.  		    Printf("\nescaped from the dungeon with %ld points,\n", 363. 			u.urexp);  364.  		} else  365.  		if(!done_stopprint)  366.  		  Printf("You escaped from the dungeon with %ld points,\n", 367. 		    u.urexp);  368.  		get_all_from_box; /* don't forget things in boxes and bags */  369.  		for(otmp = invent; otmp; otmp = otmp->nobj) {  370.  			if(otmp->olet == GEM_SYM && otmp->otyp < LUCKSTONE) {  371.  				makeknown(otmp->otyp);  372.  				i = (long) otmp->quan *  373.  					objects[otmp->otyp].g_val;  374.  				if(i == 0) {  375.  					worthlessct += otmp->quan;  376.  					continue;  377.  				}  378.  				u.urexp += i;  379.  				Printf("        %s (worth %ld Zorkmids),\n", 380. 				    doname(otmp), i);  381.  			} else if(otmp->olet == AMULET_SYM) {  382.  				otmp->known = 1;  383.  				i = (otmp->spe < 0) ? 2 :  384.  					otmp->otyp == AMULET_OF_YENDOR ?  385.  							5000 : 500;  386.  				u.urexp += i;  387.  				Printf("        %s (worth %ld Zorkmids),\n", 388. 				    doname(otmp), i);  389.  			}  390.  		}  391.  		if(worthlessct)  392.  		  Printf("        %u worthless piece%s of colored glass,\n", 393. 			worthlessct, plur((long)worthlessct));  394.  		if(u.uhave_amulet) killer = "escaped (with Amulet)";  395.  		else killer = "escaped";  396.  	} else  397.  		if(!done_stopprint) {  398.  		    Printf("You %s ", 399. 			!strcmp(st1, "tricked") ? "were tricked" : st1); 400.  #ifdef ENDGAME  401.  		    if (*st1 != 'a') {  402.  			if(dlevel == ENDLEVEL)  403.  			     Printf("in the endgame ");  404.  		    	else Printf("on dungeon level %d ", dlevel);  405.  		    }  406.  #else  407.  		    Printf("on dungeon level %d ", dlevel);  408.  #endif  409.  		    Printf("with %ld points,\n", u.urexp);  410.  		}  411.  	if(!done_stopprint)  412.  	  Printf("and %ld piece%s of gold, after %ld move%s.\n", 413. 	    u.ugold, plur(u.ugold), moves, plur(moves));  414.  	if(!done_stopprint)  415.    Printf("You were level %u with a maximum of %d hit points when you %s.\n", 416. 	    u.ulevel, u.uhpmax, buf1);  417.  	if(*st1 == 'e' && !done_stopprint){  418.  		getret;	/* all those pieces of coloured glass ... */  419.  		cls;  420.  	}  421.  #if defined(WIZARD) || defined(EXPLORE_MODE)  422.  	if(wizard || discover)  423.  		Printf("\nSince you were in %s mode, the score list \  424.  will not be checked.\n", wizard ? "wizard" : "discover"); 425.  	else  426.  #endif  427.  		topten;  428.  /* "So when I die, the first thing I will see in Heaven is a score list?" */  429.  	if(done_stopprint) Printf("\n\n");  430.  #ifdef APOLLO  431.  	getret;  432.  #endif  433.  	exit(0);  434.  }  435.   436.  void  437.  clearlocks{  438.  #if defined(DGK) && !defined(TOS)  439.  	eraseall(levels, alllevels);  440.  	if (ramdisk)  441.  		eraseall(permbones, alllevels);  442.  #else  443.  #if defined(UNIX) || (defined(MSDOS) && !defined(TOS))  444.  	register int x;  445.  #ifdef UNIX  446.  	(void) signal(SIGHUP,SIG_IGN);  447.  #endif  448.  	for(x = maxdlevel; x >= 0; x--) {  449.  		glo(x);  450.  		(void) unlink(lock);	/* not all levels need be present */  451.  	}  452.  #endif  453.  #endif  454.  }  455.   456.  #ifdef NOSAVEONHANGUP  457.  int  458.  hangup  459.  {  460.  	(void) signal(SIGINT, SIG_IGN); 461. 	clearlocks; 462. 	exit(1); 463. }  464.  #endif 465.  466.  void 467. end_box_display 468. {  469.  	register struct obj *box, *obj; 470. 	char buf[BUFSZ]; 471.  472.  	for(box=invent; box; box=box->nobj) { 473. 	    if (Is_container(box) && box->otyp != BAG_OF_TRICKS) { 474. 		int cnt=0; 475.  476.  		for(obj=fcobj; obj; obj=obj->nobj) { 477. 		    if (obj->cobj == box) { 478. 			if (!cnt) { 479. 			    Sprintf(buf, "Contents of the %s:",xname(box)); 480. 			    cornline(0, buf); 481. 			}  482.  			makeknown(obj->otyp); 483. 			obj->known = obj->bknown = obj->dknown = 1; 484. 			cornline(1,doname(obj)); 485. 			cnt++; 486. 		    }  487.  		}  488.  		if (!cnt) pline("The %s is empty.", xname(box)); 489. 		else cornline(2,""); 490. 	    }  491.  	}  492.  }