]> git.cameronkatri.com Git - bsdgames-darwin.git/blob - hack/hack.end.c
ANSIfy function declarations. All object file diffs inspected.
[bsdgames-darwin.git] / hack / hack.end.c
1 /* $NetBSD: hack.end.c,v 1.11 2009/06/07 18:30:39 dholland Exp $ */
2
3 /*
4 * Copyright (c) 1985, Stichting Centrum voor Wiskunde en Informatica,
5 * Amsterdam
6 * All rights reserved.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions are
10 * met:
11 *
12 * - Redistributions of source code must retain the above copyright notice,
13 * this list of conditions and the following disclaimer.
14 *
15 * - Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
18 *
19 * - Neither the name of the Stichting Centrum voor Wiskunde en
20 * Informatica, nor the names of its contributors may be used to endorse or
21 * promote products derived from this software without specific prior
22 * written permission.
23 *
24 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
25 * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
26 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
27 * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
28 * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
29 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
30 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
31 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
32 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
33 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
34 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
35 */
36
37 /*
38 * Copyright (c) 1982 Jay Fenlason <hack@gnu.org>
39 * All rights reserved.
40 *
41 * Redistribution and use in source and binary forms, with or without
42 * modification, are permitted provided that the following conditions
43 * are met:
44 * 1. Redistributions of source code must retain the above copyright
45 * notice, this list of conditions and the following disclaimer.
46 * 2. Redistributions in binary form must reproduce the above copyright
47 * notice, this list of conditions and the following disclaimer in the
48 * documentation and/or other materials provided with the distribution.
49 * 3. The name of the author may not be used to endorse or promote products
50 * derived from this software without specific prior written permission.
51 *
52 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
53 * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
54 * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
55 * THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
56 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
57 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
58 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
59 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
60 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
61 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
62 */
63
64 #include <sys/cdefs.h>
65 #ifndef lint
66 __RCSID("$NetBSD: hack.end.c,v 1.11 2009/06/07 18:30:39 dholland Exp $");
67 #endif /* not lint */
68
69 #include <signal.h>
70 #include <unistd.h>
71 #include <stdlib.h>
72 #include "hack.h"
73 #include "extern.h"
74 #define Sprintf (void) sprintf
75
76 xchar maxdlevel = 1;
77
78 int
79 dodone(void)
80 {
81 done1(0);
82 return 0;
83 }
84
85
86 /*ARGSUSED*/
87 void
88 done1(int n __unused)
89 {
90 (void) signal(SIGINT, SIG_IGN);
91 pline("Really quit?");
92 if (readchar() != 'y') {
93 (void) signal(SIGINT, done1);
94 clrlin();
95 (void) fflush(stdout);
96 if (multi > 0)
97 nomul(0);
98 return;
99 }
100 done("quit");
101 /* NOTREACHED */
102 }
103
104 int done_stopprint;
105 int done_hup;
106
107 /*ARGSUSED*/
108 void
109 done_intr(int n __unused)
110 {
111 done_stopprint++;
112 (void) signal(SIGINT, SIG_IGN);
113 (void) signal(SIGQUIT, SIG_IGN);
114 }
115
116 void
117 done_hangup(int n)
118 {
119 done_hup++;
120 (void) signal(SIGHUP, SIG_IGN);
121 done_intr(n);
122 }
123
124 void
125 done_in_by(struct monst *mtmp)
126 {
127 static char buf[BUFSZ];
128 pline("You die ...");
129 if (mtmp->data->mlet == ' ') {
130 Sprintf(buf, "the ghost of %s", (char *) mtmp->mextra);
131 killer = buf;
132 } else if (mtmp->mnamelth) {
133 Sprintf(buf, "%s called %s",
134 mtmp->data->mname, NAME(mtmp));
135 killer = buf;
136 } else if (mtmp->minvis) {
137 Sprintf(buf, "invisible %s", mtmp->data->mname);
138 killer = buf;
139 } else
140 killer = mtmp->data->mname;
141 done("died");
142 }
143
144 /*
145 * called with arg "died", "drowned", "escaped", "quit", "choked",
146 * "panicked", "burned", "starved" or "tricked"
147 */
148 /* Be careful not to call panic from here! */
149 void
150 done(const char *st1)
151 {
152
153 #ifdef WIZARD
154 if (wizard && *st1 == 'd') {
155 u.uswldtim = 0;
156 if (u.uhpmax < 0)
157 u.uhpmax = 100; /* arbitrary */
158 u.uhp = u.uhpmax;
159 pline("For some reason you are still alive.");
160 flags.move = 0;
161 if (multi > 0)
162 multi = 0;
163 else
164 multi = -1;
165 flags.botl = 1;
166 return;
167 }
168 #endif /* WIZARD */
169 (void) signal(SIGINT, done_intr);
170 (void) signal(SIGQUIT, done_intr);
171 (void) signal(SIGHUP, done_hangup);
172 if (*st1 == 'q' && u.uhp < 1) {
173 st1 = "died";
174 killer = "quit while already on Charon's boat";
175 }
176 if (*st1 == 's')
177 killer = "starvation";
178 else if (*st1 == 'd' && st1[1] == 'r')
179 killer = "drowning";
180 else if (*st1 == 'p')
181 killer = "panic";
182 else if (*st1 == 't')
183 killer = "trickery";
184 else if (!strchr("bcd", *st1))
185 killer = st1;
186 paybill();
187 clearlocks();
188 if (flags.toplin == 1)
189 more();
190 if (strchr("bcds", *st1)) {
191 #ifdef WIZARD
192 if (!wizard)
193 #endif /* WIZARD */
194 savebones();
195 if (!flags.notombstone)
196 outrip();
197 }
198 if (*st1 == 'c')
199 killer = st1; /* after outrip() */
200 settty((char *) 0); /* does a clear_screen() */
201 if (!done_stopprint)
202 printf("Goodbye %s %s...\n\n", pl_character, plname);
203 {
204 long int tmp;
205 tmp = u.ugold - u.ugold0;
206 if (tmp < 0)
207 tmp = 0;
208 if (*st1 == 'd' || *st1 == 'b')
209 tmp -= tmp / 10;
210 u.urexp += tmp;
211 u.urexp += 50 * maxdlevel;
212 if (maxdlevel > 20)
213 u.urexp += 1000 * ((maxdlevel > 30) ? 10 : maxdlevel - 20);
214 }
215 if (*st1 == 'e') {
216 struct monst *mtmp;
217 struct obj *otmp;
218 int i;
219 unsigned worthlessct = 0;
220 boolean has_amulet = FALSE;
221
222 killer = st1;
223 keepdogs();
224 mtmp = mydogs;
225 if (mtmp) {
226 if (!done_stopprint)
227 printf("You");
228 while (mtmp) {
229 if (!done_stopprint)
230 printf(" and %s", monnam(mtmp));
231 if (mtmp->mtame)
232 u.urexp += mtmp->mhp;
233 mtmp = mtmp->nmon;
234 }
235 if (!done_stopprint)
236 printf("\nescaped from the dungeon with %ld points,\n",
237 u.urexp);
238 } else if (!done_stopprint)
239 printf("You escaped from the dungeon with %ld points,\n",
240 u.urexp);
241 for (otmp = invent; otmp; otmp = otmp->nobj) {
242 if (otmp->olet == GEM_SYM) {
243 objects[otmp->otyp].oc_name_known = 1;
244 i = otmp->quan * objects[otmp->otyp].g_val;
245 if (i == 0) {
246 worthlessct += otmp->quan;
247 continue;
248 }
249 u.urexp += i;
250 if (!done_stopprint)
251 printf("\t%s (worth %d Zorkmids),\n",
252 doname(otmp), i);
253 } else if (otmp->olet == AMULET_SYM) {
254 otmp->known = 1;
255 i = (otmp->spe < 0) ? 2 : 5000;
256 u.urexp += i;
257 if (!done_stopprint)
258 printf("\t%s (worth %d Zorkmids),\n",
259 doname(otmp), i);
260 if (otmp->spe >= 0) {
261 has_amulet = TRUE;
262 killer = "escaped (with amulet)";
263 }
264 }
265 }
266 if (worthlessct)
267 if (!done_stopprint)
268 printf("\t%u worthless piece%s of coloured glass,\n",
269 worthlessct, plur(worthlessct));
270 if (has_amulet)
271 u.urexp *= 2;
272 } else if (!done_stopprint)
273 printf("You %s on dungeon level %d with %ld points,\n",
274 st1, dlevel, u.urexp);
275 if (!done_stopprint)
276 printf("and %ld piece%s of gold, after %ld move%s.\n",
277 u.ugold, plur(u.ugold), moves, plur(moves));
278 if (!done_stopprint)
279 printf("You were level %u with a maximum of %d hit points when you %s.\n",
280 u.ulevel, u.uhpmax, st1);
281 if (*st1 == 'e' && !done_stopprint) {
282 getret(); /* all those pieces of coloured glass ... */
283 cls();
284 }
285 #ifdef WIZARD
286 if (!wizard)
287 #endif /* WIZARD */
288 topten();
289 if (done_stopprint)
290 printf("\n\n");
291 exit(0);
292 }
293
294 #define newttentry() (struct toptenentry *) alloc(sizeof(struct toptenentry))
295 #define NAMSZ 8
296 #define DTHSZ 40
297 #define PERSMAX 1
298 #define POINTSMIN 1 /* must be > 0 */
299 #define ENTRYMAX 100 /* must be >= 10 */
300 #define PERS_IS_UID /* delete for PERSMAX per name; now per uid */
301 struct toptenentry {
302 struct toptenentry *tt_next;
303 long int points;
304 int level, maxlvl, hp, maxhp;
305 int uid;
306 char plchar;
307 char sex;
308 char name[NAMSZ + 1];
309 char death[DTHSZ + 1];
310 char date[7];/* yymmdd */
311 } *tt_head;
312
313 void
314 topten(void)
315 {
316 int uid = getuid();
317 int rank, rank0 = -1, rank1 = 0;
318 int occ_cnt = PERSMAX;
319 struct toptenentry *t0, *t1, *tprev;
320 const char *recfile = RECORD;
321 const char *reclock = "record_lock";
322 int sleepct = 300;
323 FILE *rfile;
324 int flg = 0;
325 #define HUP if(!done_hup)
326 while (link(recfile, reclock) == -1) {
327 HUP perror(reclock);
328 if (!sleepct--) {
329 HUP puts("I give up. Sorry.");
330 HUP puts("Perhaps there is an old record_lock around?");
331 return;
332 }
333 HUP printf("Waiting for access to record file. (%d)\n",
334 sleepct);
335 HUP(void) fflush(stdout);
336 sleep(1);
337 }
338 if (!(rfile = fopen(recfile, "r"))) {
339 HUP puts("Cannot open record file!");
340 goto unlock;
341 }
342 HUP(void) putchar('\n');
343
344 /* create a new 'topten' entry */
345 t0 = newttentry();
346 t0->level = dlevel;
347 t0->maxlvl = maxdlevel;
348 t0->hp = u.uhp;
349 t0->maxhp = u.uhpmax;
350 t0->points = u.urexp;
351 t0->plchar = pl_character[0];
352 t0->sex = (flags.female ? 'F' : 'M');
353 t0->uid = uid;
354 (void) strncpy(t0->name, plname, NAMSZ);
355 (t0->name)[NAMSZ] = 0;
356 (void) strncpy(t0->death, killer, DTHSZ);
357 (t0->death)[DTHSZ] = 0;
358 (void) strcpy(t0->date, getdatestr());
359
360 /* assure minimum number of points */
361 if (t0->points < POINTSMIN)
362 t0->points = 0;
363
364 t1 = tt_head = newttentry();
365 tprev = 0;
366 /* rank0: -1 undefined, 0 not_on_list, n n_th on list */
367 for (rank = 1;;) {
368 if (fscanf(rfile, "%6s %d %d %d %d %d %ld %c%c %[^,],%[^\n]",
369 t1->date, &t1->uid,
370 &t1->level, &t1->maxlvl,
371 &t1->hp, &t1->maxhp, &t1->points,
372 &t1->plchar, &t1->sex, t1->name, t1->death) != 11
373 || t1->points < POINTSMIN)
374 t1->points = 0;
375 if (rank0 < 0 && t1->points < t0->points) {
376 rank0 = rank++;
377 if (tprev == 0)
378 tt_head = t0;
379 else
380 tprev->tt_next = t0;
381 t0->tt_next = t1;
382 occ_cnt--;
383 flg++; /* ask for a rewrite */
384 } else
385 tprev = t1;
386 if (t1->points == 0)
387 break;
388 if (
389 #ifdef PERS_IS_UID
390 t1->uid == t0->uid &&
391 #else
392 strncmp(t1->name, t0->name, NAMSZ) == 0 &&
393 #endif /* PERS_IS_UID */
394 t1->plchar == t0->plchar && --occ_cnt <= 0) {
395 if (rank0 < 0) {
396 rank0 = 0;
397 rank1 = rank;
398 HUP printf("You didn't beat your previous score of %ld points.\n\n",
399 t1->points);
400 }
401 if (occ_cnt < 0) {
402 flg++;
403 continue;
404 }
405 }
406 if (rank <= ENTRYMAX) {
407 t1 = t1->tt_next = newttentry();
408 rank++;
409 }
410 if (rank > ENTRYMAX) {
411 t1->points = 0;
412 break;
413 }
414 }
415 if (flg) { /* rewrite record file */
416 (void) fclose(rfile);
417 if (!(rfile = fopen(recfile, "w"))) {
418 HUP puts("Cannot write record file\n");
419 goto unlock;
420 }
421 if (!done_stopprint)
422 if (rank0 > 0) {
423 if (rank0 <= 10)
424 puts("You made the top ten list!\n");
425 else
426 printf("You reached the %d%s place on the top %d list.\n\n",
427 rank0, ordin(rank0), ENTRYMAX);
428 }
429 }
430 if (rank0 == 0)
431 rank0 = rank1;
432 if (rank0 <= 0)
433 rank0 = rank;
434 if (!done_stopprint)
435 outheader();
436 t1 = tt_head;
437 for (rank = 1; t1->points != 0; rank++, t1 = t1->tt_next) {
438 if (flg)
439 fprintf(rfile, "%6s %d %d %d %d %d %ld %c%c %s,%s\n",
440 t1->date, t1->uid,
441 t1->level, t1->maxlvl,
442 t1->hp, t1->maxhp, t1->points,
443 t1->plchar, t1->sex, t1->name, t1->death);
444 if (done_stopprint)
445 continue;
446 if (rank > (int)flags.end_top &&
447 (rank < rank0 - (int)flags.end_around || rank > rank0 + (int)flags.end_around)
448 && (!flags.end_own ||
449 #ifdef PERS_IS_UID
450 t1->uid != t0->uid))
451 #else
452 strncmp(t1->name, t0->name, NAMSZ)))
453 #endif /* PERS_IS_UID */
454 continue;
455 if (rank == rank0 - (int)flags.end_around &&
456 rank0 > (int)flags.end_top + (int)flags.end_around + 1 &&
457 !flags.end_own)
458 (void) putchar('\n');
459 if (rank != rank0)
460 (void) outentry(rank, t1, 0);
461 else if (!rank1)
462 (void) outentry(rank, t1, 1);
463 else {
464 int t0lth = outentry(0, t0, -1);
465 int t1lth = outentry(rank, t1, t0lth);
466 if (t1lth > t0lth)
467 t0lth = t1lth;
468 (void) outentry(0, t0, t0lth);
469 }
470 }
471 if (rank0 >= rank)
472 if (!done_stopprint)
473 (void) outentry(0, t0, 1);
474 (void) fclose(rfile);
475 free(t0);
476 unlock:
477 (void) unlink(reclock);
478 }
479
480 void
481 outheader(void)
482 {
483 char linebuf[BUFSZ];
484 char *bp;
485 (void) strcpy(linebuf, "Number Points Name");
486 bp = eos(linebuf);
487 while (bp < linebuf + COLNO - 9)
488 *bp++ = ' ';
489 (void) strcpy(bp, "Hp [max]");
490 puts(linebuf);
491 }
492
493 /* so>0: standout line; so=0: ordinary line; so<0: no output, return lth */
494 int
495 outentry(int rank, struct toptenentry *t1, int so)
496 {
497 boolean quit = FALSE, gotkilled = FALSE, starv = FALSE;
498 char linebuf[BUFSZ];
499
500 linebuf[0] = 0;
501 if (rank)
502 Sprintf(eos(linebuf), "%3d", rank);
503 else
504 Sprintf(eos(linebuf), " ");
505 Sprintf(eos(linebuf), " %6ld %8s", t1->points, t1->name);
506 if (t1->plchar == 'X')
507 Sprintf(eos(linebuf), " ");
508 else
509 Sprintf(eos(linebuf), "-%c ", t1->plchar);
510 if (!strncmp("escaped", t1->death, 7)) {
511 if (!strcmp(" (with amulet)", t1->death + 7))
512 Sprintf(eos(linebuf), "escaped the dungeon with amulet");
513 else
514 Sprintf(eos(linebuf), "escaped the dungeon [max level %d]",
515 t1->maxlvl);
516 } else {
517 if (!strncmp(t1->death, "quit", 4)) {
518 quit = TRUE;
519 if (t1->maxhp < 3 * t1->hp && t1->maxlvl < 4)
520 Sprintf(eos(linebuf), "cravenly gave up");
521 else
522 Sprintf(eos(linebuf), "quit");
523 } else if (!strcmp(t1->death, "choked"))
524 Sprintf(eos(linebuf), "choked on %s food",
525 (t1->sex == 'F') ? "her" : "his");
526 else if (!strncmp(t1->death, "starv", 5))
527 Sprintf(eos(linebuf), "starved to death"), starv = TRUE;
528 else
529 Sprintf(eos(linebuf), "was killed"), gotkilled = TRUE;
530 Sprintf(eos(linebuf), " on%s level %d",
531 (gotkilled || starv) ? "" : " dungeon", t1->level);
532 if (t1->maxlvl != t1->level)
533 Sprintf(eos(linebuf), " [max %d]", t1->maxlvl);
534 if (quit && t1->death[4])
535 Sprintf(eos(linebuf), t1->death + 4);
536 }
537 if (gotkilled)
538 Sprintf(eos(linebuf), " by %s%s",
539 (!strncmp(t1->death, "trick", 5) || !strncmp(t1->death, "the ", 4))
540 ? "" :
541 strchr(vowels, *t1->death) ? "an " : "a ",
542 t1->death);
543 Sprintf(eos(linebuf), ".");
544 if (t1->maxhp) {
545 char *bp = eos(linebuf);
546 char hpbuf[10];
547 int hppos;
548 Sprintf(hpbuf, (t1->hp > 0) ? itoa(t1->hp) : "-");
549 hppos = COLNO - 7 - strlen(hpbuf);
550 if (bp <= linebuf + hppos) {
551 while (bp < linebuf + hppos)
552 *bp++ = ' ';
553 (void) strcpy(bp, hpbuf);
554 Sprintf(eos(bp), " [%d]", t1->maxhp);
555 }
556 }
557 if (so == 0)
558 puts(linebuf);
559 else if (so > 0) {
560 char *bp = eos(linebuf);
561 if (so >= COLNO)
562 so = COLNO - 1;
563 while (bp < linebuf + so)
564 *bp++ = ' ';
565 *bp = 0;
566 standoutbeg();
567 fputs(linebuf, stdout);
568 standoutend();
569 (void) putchar('\n');
570 }
571 return (strlen(linebuf));
572 }
573
574 char *
575 itoa(int a)
576 {
577 static char buf[12];
578 Sprintf(buf, "%d", a);
579 return (buf);
580 }
581
582 const char *
583 ordin(int n)
584 {
585 int dg = n % 10;
586
587 return ((dg == 0 || dg > 3 || n / 10 == 1) ? "th" : (dg == 1) ? "st" :
588 (dg == 2) ? "nd" : "rd");
589 }
590
591 void
592 clearlocks(void)
593 {
594 int x;
595 (void) signal(SIGHUP, SIG_IGN);
596 for (x = maxdlevel; x >= 0; x--) {
597 glo(x);
598 (void) unlink(lock); /* not all levels need be present */
599 }
600 }
601
602 #ifdef NOSAVEONHANGUP
603 /*ARGSUSED*/
604 void
605 hangup(int n __unused)
606 {
607 (void) signal(SIGINT, SIG_IGN);
608 clearlocks();
609 exit(1);
610 }
611 #endif /* NOSAVEONHANGUP */
612
613 char *
614 eos(char *s)
615 {
616 while (*s)
617 s++;
618 return (s);
619 }
620
621 /* it is the callers responsibility to check that there is room for c */
622 void
623 charcat(char *s, int c)
624 {
625 while (*s)
626 s++;
627 *s++ = c;
628 *s = 0;
629 }
630
631 /*
632 * Called with args from main if argc >= 0. In this case, list scores as
633 * requested. Otherwise, find scores for the current player (and list them
634 * if argc == -1).
635 */
636 void
637 prscore(int argc, char **argv)
638 {
639 char **players = NULL;
640 int playerct;
641 int rank;
642 struct toptenentry *t1, *t2;
643 const char *recfile = RECORD;
644 FILE *rfile;
645 int flg = 0;
646 int i;
647 #ifdef nonsense
648 long total_score = 0L;
649 char totchars[10];
650 int totcharct = 0;
651 #endif /* nonsense */
652 int outflg = (argc >= -1);
653 #ifdef PERS_IS_UID
654 int uid = -1;
655 #else
656 char *player0;
657 #endif /* PERS_IS_UID */
658
659 if (!(rfile = fopen(recfile, "r"))) {
660 puts("Cannot open record file!");
661 return;
662 }
663 if (argc > 1 && !strncmp(argv[1], "-s", 2)) {
664 if (!argv[1][2]) {
665 argc--;
666 argv++;
667 } else if (!argv[1][3] && strchr("CFKSTWX", argv[1][2])) {
668 argv[1]++;
669 argv[1][0] = '-';
670 } else
671 argv[1] += 2;
672 }
673 if (argc <= 1) {
674 #ifdef PERS_IS_UID
675 uid = getuid();
676 playerct = 0;
677 #else
678 player0 = plname;
679 if (!*player0)
680 player0 = "hackplayer";
681 playerct = 1;
682 players = &player0;
683 #endif /* PERS_IS_UID */
684 } else {
685 playerct = --argc;
686 players = ++argv;
687 }
688 if (outflg)
689 putchar('\n');
690
691 t1 = tt_head = newttentry();
692 for (rank = 1;; rank++) {
693 if (fscanf(rfile, "%6s %d %d %d %d %d %ld %c%c %[^,],%[^\n]",
694 t1->date, &t1->uid,
695 &t1->level, &t1->maxlvl,
696 &t1->hp, &t1->maxhp, &t1->points,
697 &t1->plchar, &t1->sex, t1->name, t1->death) != 11)
698 t1->points = 0;
699 if (t1->points == 0)
700 break;
701 #ifdef PERS_IS_UID
702 if (!playerct && t1->uid == uid)
703 flg++;
704 else
705 #endif /* PERS_IS_UID */
706 for (i = 0; i < playerct; i++) {
707 if (strcmp(players[i], "all") == 0 ||
708 strncmp(t1->name, players[i], NAMSZ) == 0 ||
709 (players[i][0] == '-' &&
710 players[i][1] == t1->plchar &&
711 players[i][2] == 0) ||
712 (digit(players[i][0]) && rank <= atoi(players[i])))
713 flg++;
714 }
715 t1 = t1->tt_next = newttentry();
716 }
717 (void) fclose(rfile);
718 if (!flg) {
719 if (outflg) {
720 printf("Cannot find any entries for ");
721 if (playerct < 1)
722 printf("you.\n");
723 else {
724 if (playerct > 1)
725 printf("any of ");
726 for (i = 0; i < playerct; i++)
727 printf("%s%s", players[i], (i < playerct - 1) ? ", " : ".\n");
728 printf("Call is: %s -s [playernames]\n", hname);
729 }
730 }
731 return;
732 }
733 if (outflg)
734 outheader();
735 t1 = tt_head;
736 for (rank = 1; t1->points != 0; rank++, t1 = t2) {
737 t2 = t1->tt_next;
738 #ifdef PERS_IS_UID
739 if (!playerct && t1->uid == uid)
740 goto outwithit;
741 else
742 #endif /* PERS_IS_UID */
743 for (i = 0; i < playerct; i++) {
744 if (strcmp(players[i], "all") == 0 ||
745 strncmp(t1->name, players[i], NAMSZ) == 0 ||
746 (players[i][0] == '-' &&
747 players[i][1] == t1->plchar &&
748 players[i][2] == 0) ||
749 (digit(players[i][0]) && rank <= atoi(players[i]))) {
750 outwithit:
751 if (outflg)
752 (void) outentry(rank, t1, 0);
753 #ifdef nonsense
754 total_score += t1->points;
755 if (totcharct < sizeof(totchars) - 1)
756 totchars[totcharct++] = t1->plchar;
757 #endif /* nonsense */
758 break;
759 }
760 }
761 free((char *) t1);
762 }
763 #ifdef nonsense
764 totchars[totcharct] = 0;
765
766 /*
767 * We would like to determine whether he is experienced. However, the
768 * information collected here only tells about the scores/roles that
769 * got into the topten (top 100?). We should maintain a .hacklog or
770 * something in his home directory.
771 */
772 flags.beginner = (total_score < 6000);
773 for (i = 0; i < 6; i++)
774 if (!strchr(totchars, "CFKSTWX"[i])) {
775 flags.beginner = 1;
776 if (!pl_character[0])
777 pl_character[0] = "CFKSTWX"[i];
778 break;
779 }
780 #endif /* nonsense */
781 }