comparison xrogue/rip.c @ 133:e6179860cb76

Import XRogue 8.0 from the Roguelike Restoration Project (r1490)
author John "Elwin" Edwards
date Tue, 21 Apr 2015 08:55:20 -0400
parents
children ce0cf824c192
comparison
equal deleted inserted replaced
124:d10fc4a065ac 133:e6179860cb76
1 /*
2 rip.c - File for the fun ends Death or a total win
3
4 XRogue: Expeditions into the Dungeons of Doom
5 Copyright (C) 1991 Robert Pietkivitch
6 All rights reserved.
7
8 Based on "Advanced Rogue"
9 Copyright (C) 1984, 1985 Michael Morgan, Ken Dalka and AT&T
10 All rights reserved.
11
12 Based on "Rogue: Exploring the Dungeons of Doom"
13 Copyright (C) 1980, 1981 Michael Toy, Ken Arnold and Glenn Wichman
14 All rights reserved.
15
16 See the file LICENSE.TXT for full copyright and licensing information.
17 */
18
19 #define REALLIFE 1 /* Print out machine and logname */
20 #define EDITSCORE 2 /* Edit the current score file */
21 #define ADDSCORE 3 /* Add a new score */
22
23 #include <curses.h>
24 #include <time.h>
25 #include <signal.h>
26 #include <ctype.h>
27 #include <sys/types.h>
28 #include <fcntl.h>
29 #include "mach_dep.h"
30 #include "network.h"
31 #include "rogue.h"
32
33 /* Network machines (for mutual score keeping) */
34 struct network Network[] = {
35 { "", "" },
36 };
37
38 static char *rip[] = {
39 " ___________",
40 " / \\",
41 " / \\",
42 " / R. I. P. \\",
43 " / \\",
44 " / \\",
45 " | |",
46 " | |",
47 " | killed by |",
48 " | |",
49 " | |",
50 " | |",
51 " *| * * * |*",
52 " _________)|//\\\\///\\///\\//\\//\\/|(_________",
53 NULL
54 };
55
56 char *killname();
57
58 /*UNUSED*/
59 void
60 byebye(sig)
61 int sig;
62 {
63 NOOP(sig);
64 exit_game(EXIT_ENDWIN);
65 }
66
67
68 /*
69 * death:
70 * Do something really fun when he dies
71 */
72
73 death(monst)
74 register short monst;
75 {
76 register char **dp = rip, *killer;
77 register struct tm *lt;
78 time_t date;
79 char buf[LINELEN];
80 struct tm *localtime();
81
82 time(&date);
83 lt = localtime(&date);
84 clear();
85 move(8, 0);
86 while (*dp)
87 printw("%s\n", *dp++);
88 mvaddstr(14, 28-((strlen(whoami)+1)/2), whoami);
89 sprintf(buf, "%lu Points", pstats.s_exp );
90 mvaddstr(15, 28-((strlen(buf)+1)/2), buf);
91 killer = killname(monst);
92 mvaddstr(17, 28-((strlen(killer)+1)/2), killer);
93 mvaddstr(18, 25, (sprintf(prbuf, "%4d", 1900+lt->tm_year), prbuf));
94 move(lines-1, 0);
95 refresh();
96 score(pstats.s_exp, KILLED, monst);
97 exit_game(EXIT_ENDWIN);
98 }
99
100 char *
101 killname(monst)
102 register short monst;
103 {
104 static char mons_name[LINELEN/2];
105 int i;
106
107 if (monst > NUMMONST) return("a strange monster");
108
109 if (monst >= 0) {
110 switch (monsters[monst].m_name[0]) {
111 case 'a':
112 case 'e':
113 case 'i':
114 case 'o':
115 case 'u':
116 sprintf(mons_name, "an %s", monsters[monst].m_name);
117 break;
118 default:
119 sprintf(mons_name, "a %s", monsters[monst].m_name);
120 }
121 return(mons_name);
122 }
123 for (i = 0; i< DEATHNUM; i++) {
124 if (deaths[i].reason == monst)
125 break;
126 }
127 if (i >= DEATHNUM)
128 return ("strange death");
129 return (deaths[i].name);
130 }
131
132 /*
133 * score -- figure score and post it.
134 */
135
136 /* VARARGS2 */
137 score(amount, flags, monst)
138 unsigned long amount;
139 int flags;
140 short monst;
141 {
142 struct sc_ent top_ten[NUMSCORE];
143 register struct sc_ent *scp;
144 register int i;
145 register struct sc_ent *sc2;
146 register FILE *outf;
147 register char *killer;
148 register int prflags = 0;
149 short upquest=0, wintype=0, uplevel=0, uptype=0; /* For network updating */
150 char upsystem[SYSLEN], uplogin[LOGLEN];
151 char *thissys; /* Holds the name of this system */
152
153 #define REASONLEN 3
154 static char *reason[] = {
155 "killed",
156 "quit",
157 "A total winner",
158 "somehow left",
159 };
160 char *packend;
161
162 memset(top_ten,0,sizeof(top_ten));
163
164 signal(SIGINT, byebye);
165 if (level == 0 && max_level == 0)
166 amount = 0; /*don't count if quit early */
167 if (flags != WINNER && flags != SCOREIT && flags != UPDATE) {
168 if (flags == CHICKEN) {
169 packend = "when you quit";
170 amount = amount / 100;
171 }
172 else
173 packend = "at your untimely demise";
174 mvaddstr(lines - 1, 0, retstr);
175 refresh();
176 getstr(prbuf);
177 showpack(packend);
178 }
179 purse = 0; /* Steal all the gold */
180
181 /*
182 * Open file and read list
183 */
184
185 if ((outf = fopen(score_file, "rb+")) == NULL)
186 {
187 if ((outf = fopen(score_file, "wb+")) == NULL)
188 {
189 mvprintw(lines - 1, 0, "Unable to open or create score file: %s",score_file);
190 refresh();
191 return;
192 }
193 }
194
195 thissys = md_gethostname();
196
197 /*
198 * If this is a SCOREIT optin (rogue -s), don't call byebye. The
199 * endwin() calls in byebye() will and this results in a core dump.
200 */
201 if (flags == SCOREIT) signal(SIGINT, SIG_DFL);
202 else signal(SIGINT, byebye);
203
204 if (flags != SCOREIT && flags != UPDATE)
205 {
206 mvaddstr(lines - 1, 0, retstr);
207 refresh();
208 fflush(stdout);
209 getstr(prbuf);
210 }
211
212 /* Check for special options */
213 if (strcmp(prbuf, "names") == 0)
214 prflags = REALLIFE;
215 else if (wizard) {
216 if (strcmp(prbuf, "edit") == 0) prflags = EDITSCORE;
217 else if (strcmp(prbuf, "add") == 0) {
218 prflags = ADDSCORE;
219 waswizard = FALSE; /* We want the new score recorded */
220 }
221 }
222
223 /* Read the score and convert it to a compatible format */
224
225 fseek(outf, 0, SEEK_SET);
226 rs_read_scorefile(outf, top_ten, NUMSCORE);
227
228 /* Get some values if this is an update */
229 if (flags == UPDATE) {
230 int errcheck, errors = 0;
231
232 upquest = (short) netread(&errcheck, sizeof(short), stdin);
233 if (errcheck) errors++;
234
235 if (fread(whoami, 1, NAMELEN, stdin) != NAMELEN) errors++;
236
237 wintype = (short) netread(&errcheck, sizeof(short), stdin);
238 if (errcheck) errors++;
239
240 uplevel = (short) netread(&errcheck, sizeof(short), stdin);
241 if (errcheck) errors++;
242
243 uptype = (short) netread(&errcheck, sizeof(short), stdin);
244 if (errcheck) errors++;
245
246 if (fread(upsystem, 1, SYSLEN, stdin) != SYSLEN)
247 errors++;
248 if (fread(uplogin, 1, LOGLEN, stdin) != LOGLEN)
249 errors++;
250
251 if (errors) {
252 fclose(outf);
253 return;
254 }
255 }
256
257 /*
258 * Insert player in list if need be
259 */
260 if (!waswizard) {
261 char *login= NULL;
262
263 if (flags != UPDATE) {
264 login = md_getusername();
265
266 if ((login == NULL) || (*login == 0))
267 login = "another rogue fiend";
268 }
269
270 if (flags == UPDATE)
271 (void) update(top_ten, amount, upquest, whoami, wintype,
272 uplevel, monst, uptype, upsystem, uplogin);
273 else {
274 if (prflags == ADDSCORE) { /* Overlay characteristic by new ones */
275 char buffer[LINELEN];
276
277 clear();
278 mvaddstr(1, 0, "Score: ");
279 mvaddstr(2, 0, "Quest (number): ");
280 mvaddstr(3, 0, "Name: ");
281 mvaddstr(4, 0, "System: ");
282 mvaddstr(5, 0, "Login: ");
283 mvaddstr(6, 0, "Level: ");
284 mvaddstr(7, 0, "Char type: ");
285 mvaddstr(8, 0, "Result: ");
286
287 /* Get the score */
288 move(1, 7);
289 get_str(buffer, stdscr);
290 amount = atol(buffer);
291
292 /* Get the character's quest -- must be a number */
293 move(2, 16);
294 get_str(buffer, stdscr);
295 quest_item = atoi(buffer);
296
297 /* Get the character's name */
298 move(3, 6);
299 get_str(buffer, stdscr);
300 strncpy(whoami, buffer, NAMELEN);
301
302 /* Get the system */
303 move(4, 8);
304 get_str(buffer, stdscr);
305 strncpy(thissys, buffer, SYSLEN);
306
307 /* Get the login */
308 move(5, 7);
309 get_str(buffer, stdscr);
310 strncpy(login, buffer, LOGLEN);
311
312 /* Get the level */
313 move(6, 7);
314 get_str(buffer, stdscr);
315 level = max_level = (short) atoi(buffer);
316
317 /* Get the character type */
318 move(7, 11);
319 get_str(buffer, stdscr);
320 for (i=0; i<NUM_CHARTYPES; i++) {
321 if (EQSTR(buffer, char_class[i].name, strlen(buffer)))
322 break;
323 }
324 player.t_ctype = i;
325
326 /* Get the win type */
327 move(8, 8);
328 get_str(buffer, stdscr);
329 switch (buffer[0]) {
330 case 'W':
331 case 'w':
332 case 'T':
333 case 't':
334 flags = WINNER;
335 break;
336
337 case 'Q':
338 case 'q':
339 flags = CHICKEN;
340 break;
341
342 case 'k':
343 case 'K':
344 default:
345 flags = KILLED;
346 break;
347 }
348
349 /* Get the monster if player was killed */
350 if (flags == KILLED) {
351 mvaddstr(9, 0, "Death type: ");
352 get_str(buffer, stdscr);
353 if (buffer[0] == 'M' || buffer[0] == 'm')
354 do {
355 monst = makemonster(TRUE, "choose");
356 } while (monst < 0); /* Force a choice */
357 else monst = getdeath();
358 }
359 }
360
361 if (update(top_ten, amount, (short) quest_item, whoami, flags,
362 (flags == WINNER) ? (short) max_level : (short) level,
363 monst, player.t_ctype, thissys, login)
364 ) {
365 /* Send this update to the other systems in the network */
366 int i, j;
367 char cmd[256]; /* Command for remote execution */
368 FILE *rmf, *popen(); /* For input to remote command */
369
370 for (i=0; Network[i].system[0] != 0; i++)
371 if (Network[i].system[0] != '!' &&
372 strcmp(Network[i].system, thissys)) {
373 sprintf(cmd, NETCOMMAND,
374 Network[i].system, Network[i].rogue);
375
376 /* Execute the command */
377 if ((rmf=popen(cmd, "w")) != NULL) {
378 unsigned long temp; /* Temporary value */
379
380 /* Write out the parameters */
381 (void) netwrite((unsigned long) amount,
382 sizeof(unsigned long), rmf);
383
384 (void) netwrite((unsigned long) monst,
385 sizeof(short), rmf);
386
387 (void) netwrite((unsigned long) quest_item,
388 sizeof(short), rmf);
389
390 (void) fwrite(whoami, 1, strlen(whoami), rmf);
391 for (j=strlen(whoami); j<NAMELEN; j++)
392 putc('\0', rmf);
393
394 (void) netwrite((unsigned long) flags,
395 sizeof(short), rmf);
396
397 temp = (unsigned long)
398 (flags==WINNER ? max_level : level);
399 (void) netwrite(temp, sizeof(short), rmf);
400
401 (void) netwrite((unsigned long) player.t_ctype,
402 sizeof(short), rmf);
403
404 (void) fwrite(thissys, 1,
405 strlen(thissys), rmf);
406 for (j=strlen(thissys); j<SYSLEN; j++)
407 putc('\0', rmf);
408
409 (void) fwrite(login, 1, strlen(login), rmf);
410 for (j=strlen(login); j<LOGLEN; j++)
411 putc('\0', rmf);
412
413 /* Close off the command */
414 (void) pclose(rmf);
415 }
416 }
417 }
418 }
419 }
420
421 /*
422 * SCOREIT -- rogue -s option. Never started curses if this option.
423 * UPDATE -- network scoring update. Never started curses if this option.
424 * EDITSCORE -- want to delete or change a score.
425 */
426 /* if (flags != SCOREIT && flags != UPDATE && prflags != EDITSCORE)
427 endwin(); */
428
429 if (flags != UPDATE) {
430 if (flags != SCOREIT) {
431 clear();
432 refresh();
433 endwin();
434 }
435 /*
436 * Print the list
437 */
438 printf("\nTop %d Adventurers:\nRank Score\tName\n",
439 NUMSCORE);
440 for (scp = top_ten; scp < &top_ten[NUMSCORE]; scp++) {
441 char *class;
442
443 if (scp->sc_score != 0) {
444 class = char_class[scp->sc_ctype].name;
445
446 /* Make sure we have an in-bound reason */
447 if (scp->sc_flags > REASONLEN) scp->sc_flags = REASONLEN;
448
449 printf("%3d %10lu\t%s (%s)", scp - top_ten + 1,
450 scp->sc_score, scp->sc_name, class);
451
452 if (prflags == REALLIFE) printf(" [in real life %.*s!%.*s]",
453 SYSLEN, scp->sc_system, LOGLEN, scp->sc_login);
454
455 printf(":\n\t\t%s on level %d", reason[scp->sc_flags],
456 scp->sc_level);
457
458 switch (scp->sc_flags) {
459 case KILLED:
460 printf(" by");
461 killer = killname(scp->sc_monster);
462 printf(" %s", killer);
463 break;
464
465 case WINNER:
466 printf(" with the %s",
467 rel_magic[scp->sc_quest].mi_name);
468 break;
469 }
470
471 if (prflags == EDITSCORE)
472 {
473 fflush(stdout);
474 getstr(prbuf);
475 printf("\n");
476 if (prbuf[0] == 'd') {
477 for (sc2 = scp; sc2 < &top_ten[NUMSCORE-1]; sc2++)
478 *sc2 = *(sc2 + 1);
479 top_ten[NUMSCORE-1].sc_score = 0;
480 for (i = 0; i < NAMELEN; i++)
481 top_ten[NUMSCORE-1].sc_name[i] = rnd(255);
482 top_ten[NUMSCORE-1].sc_flags = RN;
483 top_ten[NUMSCORE-1].sc_level = RN;
484 top_ten[NUMSCORE-1].sc_monster = RN;
485 scp--;
486 }
487 else if (prbuf[0] == 'e') {
488 printf("Death type: ");
489 getstr(prbuf);
490 if (prbuf[0] == 'M' || prbuf[0] == 'm')
491 do {
492 scp->sc_monster =
493 makemonster(TRUE, "choose");
494 } while (scp->sc_monster < 0); /* Force a choice */
495 else scp->sc_monster = getdeath();
496 clear();
497 refresh();
498 }
499 }
500 else printf("\n");
501 }
502 }
503 /* if (prflags == EDITSCORE) endwin();*/ /* End editing windowing */
504 }
505 fseek(outf, 0L, SEEK_SET);
506
507 if (flags != SCOREIT)
508 rs_write_scorefile(outf,top_ten,NUMSCORE);
509 fclose(outf);
510 }
511
512 /*
513 * showpack:
514 * Display the contents of the hero's pack
515 */
516
517 showpack(howso)
518 char *howso;
519 {
520 reg char *iname;
521 reg int cnt, packnum;
522 reg struct linked_list *item;
523 reg struct object *obj;
524
525 idenpack();
526 cnt = 1;
527 clear();
528 mvprintw(0, 0, "Contents of your pack %s:\n",howso);
529 packnum = 'a';
530 for (item = pack; item != NULL; item = next(item)) {
531 obj = OBJPTR(item);
532 iname = inv_name(obj, FALSE);
533 mvprintw(cnt, 0, "%c) %s\n",packnum++,iname);
534 if (++cnt >= lines - 2 &&
535 next(item) != NULL) {
536 cnt = 1;
537 mvaddstr(lines - 1, 0, morestr);
538 refresh();
539 wait_for(' ');
540 clear();
541 }
542 }
543 mvprintw(cnt + 1,0,"--- %ld Gold Pieces ---",purse);
544 refresh();
545 }
546
547 total_winner()
548 {
549 register struct linked_list *item;
550 register struct object *obj;
551 register long worth;
552 register char c;
553 register long oldpurse;
554
555 clear();
556 standout();
557 addstr(" \n");
558 addstr(" @ @ @ @ @ @@@ @ @ \n");
559 addstr(" @ @ @@ @@ @ @ @ @ \n");
560 addstr(" @ @ @@@ @ @ @ @ @ @@@ @@@@ @@@ @ @@@ @ \n");
561 addstr(" @@@@ @ @ @ @ @ @ @ @ @ @ @ @ @ @ \n");
562 addstr(" @ @ @ @ @ @ @ @@@@ @ @ @@@@@ @ @ @ \n");
563 addstr(" @ @ @ @ @ @@ @ @ @ @ @ @ @ @ @ @ \n");
564 addstr(" @@@ @@@ @@ @ @ @ @@@@ @@@@ @@@ @@@ @@ @ \n");
565 addstr(" \n");
566 addstr(" Congratulations, you have made it to the light of day! \n");
567 standend();
568 addstr("\nYou have joined the elite ranks of those who have escaped the\n");
569 addstr("Dungeons of Doom alive. You journey home and sell all your loot at\n");
570 addstr("a great profit and are appointed ");
571 switch (player.t_ctype) {
572 case C_FIGHTER: addstr("Leader of the Fighter's Guild.\n");
573 when C_RANGER: addstr("King of the Northern Land.\n");
574 when C_PALADIN: addstr("King of the Southern Land.\n");
575 when C_MAGICIAN:addstr("High Wizard of the Sorcerer's Guild.\n");
576 when C_CLERIC: addstr("Bishop of the Monastery.\n");
577 when C_THIEF: addstr("Leader of the Thief's Guild.\n");
578 when C_MONK: addstr("Master of the Temple.\n");
579 when C_ASSASSIN: addstr("Leader of the Assassin's Guild.\n");
580 when C_DRUID: addstr("High Priest of the Monastery.\n");
581 otherwise: addstr("Town Drunk in the Tavern.\n");
582 }
583 mvaddstr(lines - 1, 0, spacemsg);
584 refresh();
585 wait_for(' ');
586 clear();
587 mvaddstr(0, 0, " Worth Item");
588 oldpurse = purse;
589 for (c = 'a', item = pack; item != NULL; c++, item = next(item))
590 {
591 obj = OBJPTR(item);
592 worth = get_worth(obj);
593 if (obj->o_group == 0)
594 worth *= obj->o_count;
595 whatis(item);
596 mvprintw(c-'a'+1, 0, "%c) %6ld %s", c, worth, inv_name(obj, FALSE));
597 purse += worth;
598 }
599 mvprintw(c - 'a' + 1, 0," %5ld Gold Pieces ", oldpurse);
600 refresh();
601 score(pstats.s_exp + (long) purse, WINNER, '\0');
602 exit_game(EXIT_ENDWIN);
603 }
604
605
606 void
607 delete_score(top_ten, idx)
608 struct sc_ent top_ten[NUMSCORE];
609 int idx;
610 {
611 for(;idx < NUMSCORE-1;idx++)
612 top_ten[idx] = top_ten[idx+1];
613
614 top_ten[NUMSCORE-1].sc_score = 0L;
615 }
616
617 int
618 insert_score(top_ten, sc)
619 struct sc_ent top_ten[NUMSCORE];
620 struct sc_ent *sc;
621 {
622 int i,j;
623
624 if (top_ten[NUMSCORE-1].sc_score > 0)
625 return(-1); /* no room */
626
627 for(i = 0; i < NUMSCORE; i++) {
628 if (sc->sc_score > top_ten[i].sc_score) {
629 for(j = NUMSCORE-1; j > i; j--)
630 top_ten[j] = top_ten[j-1];
631 top_ten[i] = *sc;
632 return(i);
633 }
634 }
635
636 return(-1);
637 }
638
639 /* PCS = player-class-system (used to determines uniqueness of player) */
640
641 int
642 is_pcs_match(sc1,sc2)
643 struct sc_ent *sc1;
644 struct sc_ent *sc2;
645 {
646 return( (strcmp(sc1->sc_name,sc2->sc_name) == 0) &&
647 (sc1->sc_ctype == sc2->sc_ctype) &&
648 (strcmp(sc1->sc_system, sc2->sc_system)==0) );
649 }
650
651 int
652 count_pcs_matches(top_ten,sc,lowest)
653 struct sc_ent top_ten[NUMSCORE];
654 struct sc_ent *sc;
655 int *lowest;
656 {
657 int i, matches = 0;
658
659 *lowest = -1;
660
661 for(i = 0; i < NUMSCORE; i++) {
662 if (is_pcs_match(sc,&top_ten[i])) {
663 matches++;
664 *lowest = i;
665 }
666 }
667 return(matches);
668 }
669
670 int
671 find_most_pcs_matches(top_ten,sc,num,idx)
672 struct sc_ent top_ten[NUMSCORE];
673 struct sc_ent *sc;
674 int *num, *idx;
675 {
676 int i, matches, max_match=0, max_match_idx=-1, lowest;
677
678 for(i = NUMSCORE-1; i > 0; i--) {
679 matches = count_pcs_matches(top_ten,&top_ten[i],&lowest);
680
681 if (matches > max_match) {
682 max_match = matches;
683 max_match_idx = lowest;
684 }
685 }
686
687 matches = count_pcs_matches(top_ten,sc,&lowest) + 1;
688
689 if (matches > max_match) {
690 *num = matches;
691 *idx = lowest;
692 }
693 else {
694 *num = max_match;
695 *idx = max_match_idx;
696 }
697
698 return(0);
699 }
700
701
702 int
703 add_score(top_ten,sc)
704 struct sc_ent top_ten[NUMSCORE];
705 struct sc_ent *sc;
706 {
707 int idx, count;
708
709 if (insert_score(top_ten,sc) == -1) {
710 /* Simple insert if space available in table */
711
712 find_most_pcs_matches(top_ten,sc,&count,&idx);
713
714 /* EVERY ENTRY UNIQUE, */
715 /* INSERT IF SCORE > LOWEST MATCH SCORE */
716 if (count == 1) {
717 if (sc->sc_score > top_ten[idx].sc_score) {
718 delete_score(top_ten,idx);
719 insert_score(top_ten,sc);
720 }
721 }
722 /* CURRENT PCS HAS HIGHEST DUPE COUNT */
723 /* INSERT IF SCORE > LOWEST MATCH SCORE */
724 else if (is_pcs_match(sc,&top_ten[idx])) {
725 if (sc->sc_score > top_ten[idx].sc_score) {
726 delete_score(top_ten,idx);
727 insert_score(top_ten,sc);
728 }
729 }
730 /* UNRELATED PCS HAS HIGHEST DUPE COUNT */
731 /* DELETE LOWEST DUPE TO MAKE ROOM AND INSERT */
732 else {
733 delete_score(top_ten,idx);
734 insert_score(top_ten,sc);
735 }
736 }
737 }
738
739 update(top_ten, amount, quest, whoami, flags, level, monst, ctype, system, login)
740 struct sc_ent top_ten[];
741 unsigned long amount;
742 short quest, flags, level, monst, ctype;
743 char *whoami, *system, *login;
744 {
745 struct sc_ent sc;
746
747 sc.sc_score = amount;
748 sc.sc_quest = quest;
749 strncpy(sc.sc_name, whoami, NAMELEN);
750 sc.sc_name[NAMELEN-1] = 0;
751 sc.sc_flags = flags;
752 sc.sc_level = level;
753 sc.sc_monster = monst;
754 sc.sc_ctype = ctype;
755 strncpy(sc.sc_system, system, SYSLEN);
756 sc.sc_system[SYSLEN - 1] = 0;
757 strncpy(sc.sc_login, login, LOGLEN);
758 sc.sc_login[LOGLEN-1] = 0;
759
760 add_score(top_ten, &sc);
761 return(1);
762 }
763