OSDN Git Service

set trivial flags
[jnethack/source.git] / src / dog.c
1 /* NetHack 3.6  dog.c   $NHDT-Date: 1554580624 2019/04/06 19:57:04 $  $NHDT-Branch: NetHack-3.6.2-beta01 $:$NHDT-Revision: 1.85 $ */
2 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
3 /*-Copyright (c) Robert Patrick Rankin, 2011. */
4 /* NetHack may be freely redistributed.  See license for details. */
5
6 /* JNetHack Copyright */
7 /* (c) Issei Numata, Naoki Hamada, Shigehiro Miyashita, 1994-2000  */
8 /* For 3.4-, Copyright (c) SHIRAKATA Kentaro, 2002-2019            */
9 /* JNetHack may be freely redistributed.  See license for details. */
10
11 #include "hack.h"
12
13 STATIC_DCL int NDECL(pet_type);
14
15 void
16 newedog(mtmp)
17 struct monst *mtmp;
18 {
19     if (!mtmp->mextra)
20         mtmp->mextra = newmextra();
21     if (!EDOG(mtmp)) {
22         EDOG(mtmp) = (struct edog *) alloc(sizeof(struct edog));
23         (void) memset((genericptr_t) EDOG(mtmp), 0, sizeof(struct edog));
24     }
25 }
26
27 void
28 free_edog(mtmp)
29 struct monst *mtmp;
30 {
31     if (mtmp->mextra && EDOG(mtmp)) {
32         free((genericptr_t) EDOG(mtmp));
33         EDOG(mtmp) = (struct edog *) 0;
34     }
35     mtmp->mtame = 0;
36 }
37
38 void
39 initedog(mtmp)
40 register struct monst *mtmp;
41 {
42     mtmp->mtame = is_domestic(mtmp->data) ? 10 : 5;
43     mtmp->mpeaceful = 1;
44     mtmp->mavenge = 0;
45     set_malign(mtmp); /* recalc alignment now that it's tamed */
46     mtmp->mleashed = 0;
47     mtmp->meating = 0;
48     EDOG(mtmp)->droptime = 0;
49     EDOG(mtmp)->dropdist = 10000;
50     EDOG(mtmp)->apport = ACURR(A_CHA);
51     EDOG(mtmp)->whistletime = 0;
52     EDOG(mtmp)->hungrytime = 1000 + monstermoves;
53     EDOG(mtmp)->ogoal.x = -1; /* force error if used before set */
54     EDOG(mtmp)->ogoal.y = -1;
55     EDOG(mtmp)->abuse = 0;
56     EDOG(mtmp)->revivals = 0;
57     EDOG(mtmp)->mhpmax_penalty = 0;
58     EDOG(mtmp)->killed_by_u = 0;
59 }
60
61 STATIC_OVL int
62 pet_type()
63 {
64     if (urole.petnum != NON_PM)
65         return  urole.petnum;
66     else if (preferred_pet == 'c')
67         return  PM_KITTEN;
68     else if (preferred_pet == 'd')
69         return  PM_LITTLE_DOG;
70     else
71         return  rn2(2) ? PM_KITTEN : PM_LITTLE_DOG;
72 }
73
74 struct monst *
75 make_familiar(otmp, x, y, quietly)
76 register struct obj *otmp;
77 xchar x, y;
78 boolean quietly;
79 {
80     struct permonst *pm;
81     struct monst *mtmp = 0;
82     int chance, trycnt = 100;
83
84     do {
85         if (otmp) { /* figurine; otherwise spell */
86             int mndx = otmp->corpsenm;
87
88             pm = &mons[mndx];
89             /* activating a figurine provides one way to exceed the
90                maximum number of the target critter created--unless
91                it has a special limit (erinys, Nazgul) */
92             if ((mvitals[mndx].mvflags & G_EXTINCT)
93                 && mbirth_limit(mndx) != MAXMONNO) {
94                 if (!quietly)
95                     /* have just been given "You <do something with>
96                        the figurine and it transforms." message */
97 /*JP
98                     pline("... into a pile of dust.");
99 */
100                     pline("\81D\81D\81D\82»\82µ\82Ä\82¿\82è\82Ì\8eR\82É\82È\82Á\82½\81D");
101                 break; /* mtmp is null */
102             }
103         } else if (!rn2(3)) {
104             pm = &mons[pet_type()];
105         } else {
106             pm = rndmonst();
107             if (!pm) {
108                 if (!quietly)
109 /*JP
110                     There("seems to be nothing available for a familiar.");
111 */
112                     pline("\89º\96l\82Í\8c»\82ê\82È\82©\82Á\82½\81D");
113                 break;
114             }
115         }
116
117         mtmp = makemon(pm, x, y, MM_EDOG | MM_IGNOREWATER | NO_MINVENT);
118         if (otmp && !mtmp) { /* monster was genocided or square occupied */
119             if (!quietly)
120 /*JP
121                 pline_The("figurine writhes and then shatters into pieces!");
122 */
123                 pline("\90l\8c`\82Í\82à\82ª\82«\81C\82­\82¾\82¯\8eU\82Á\82½\81I");
124             break;
125         }
126     } while (!mtmp && --trycnt > 0);
127
128     if (!mtmp)
129         return (struct monst *) 0;
130
131     if (is_pool(mtmp->mx, mtmp->my) && minliquid(mtmp))
132         return (struct monst *) 0;
133
134     initedog(mtmp);
135     mtmp->msleeping = 0;
136     if (otmp) { /* figurine; resulting monster might not become a pet */
137         chance = rn2(10); /* 0==tame, 1==peaceful, 2==hostile */
138         if (chance > 2)
139             chance = otmp->blessed ? 0 : !otmp->cursed ? 1 : 2;
140         /* 0,1,2:  b=80%,10,10; nc=10%,80,10; c=10%,10,80 */
141         if (chance > 0) {
142             mtmp->mtame = 0;   /* not tame after all */
143             if (chance == 2) { /* hostile (cursed figurine) */
144                 if (!quietly)
145 /*JP
146                     You("get a bad feeling about this.");
147 */
148                     You("\8c\99\82È\97\\8a´\82ª\82µ\82½\81D");
149                 mtmp->mpeaceful = 0;
150                 set_malign(mtmp);
151             }
152         }
153         /* if figurine has been named, give same name to the monster */
154         if (has_oname(otmp))
155             mtmp = christen_monst(mtmp, ONAME(otmp));
156     }
157     set_malign(mtmp); /* more alignment changes */
158     newsym(mtmp->mx, mtmp->my);
159
160     /* must wield weapon immediately since pets will otherwise drop it */
161     if (mtmp->mtame && attacktype(mtmp->data, AT_WEAP)) {
162         mtmp->weapon_check = NEED_HTH_WEAPON;
163         (void) mon_wield_item(mtmp);
164     }
165     return mtmp;
166 }
167
168 struct monst *
169 makedog()
170 {
171     register struct monst *mtmp;
172     register struct obj *otmp;
173     const char *petname;
174     int pettype;
175     static int petname_used = 0;
176
177     if (preferred_pet == 'n')
178         return ((struct monst *) 0);
179
180     pettype = pet_type();
181     if (pettype == PM_LITTLE_DOG)
182         petname = dogname;
183     else if (pettype == PM_PONY)
184         petname = horsename;
185     else
186         petname = catname;
187
188     /* default pet names */
189     if (!*petname && pettype == PM_LITTLE_DOG) {
190         /* All of these names were for dogs. */
191         if (Role_if(PM_CAVEMAN))
192 #if 0 /*JP:T*/
193             petname = "Slasher"; /* The Warrior */
194 #else
195             petname = "\83X\83\89\83b\83V\83\83\81[";
196 #endif
197         if (Role_if(PM_SAMURAI))
198 #if 0 /*JP:T*/
199             petname = "Hachi"; /* Shibuya Station */
200 #else
201             petname = "\83n\83`\8cö";
202 #endif
203         if (Role_if(PM_BARBARIAN))
204 #if 0 /*JP:T*/
205             petname = "Idefix"; /* Obelix */
206 #else
207             petname = "\83C\83f\83t\83B\83N\83X";
208 #endif
209         if (Role_if(PM_RANGER))
210 #if 0 /*JP:T*/
211             petname = "Sirius"; /* Orion's dog */
212 #else
213             petname = "\83V\83\8a\83E\83X";
214 #endif
215     }
216
217     mtmp = makemon(&mons[pettype], u.ux, u.uy, MM_EDOG);
218
219     if (!mtmp)
220         return ((struct monst *) 0); /* pets were genocided */
221
222     context.startingpet_mid = mtmp->m_id;
223     /* Horses already wear a saddle */
224     if (pettype == PM_PONY && !!(otmp = mksobj(SADDLE, TRUE, FALSE))) {
225         otmp->dknown = otmp->bknown = otmp->rknown = 1;
226         put_saddle_on_mon(otmp, mtmp);
227     }
228
229     if (!petname_used++ && *petname)
230         mtmp = christen_monst(mtmp, petname);
231
232     initedog(mtmp);
233     return  mtmp;
234 }
235
236 /* record `last move time' for all monsters prior to level save so that
237    mon_arrive() can catch up for lost time when they're restored later */
238 void
239 update_mlstmv()
240 {
241     struct monst *mon;
242
243     /* monst->mlstmv used to be updated every time `monst' actually moved,
244        but that is no longer the case so we just do a blanket assignment */
245     for (mon = fmon; mon; mon = mon->nmon) {
246         if (DEADMONSTER(mon))
247             continue;
248         mon->mlstmv = monstermoves;
249     }
250 }
251
252 void
253 losedogs()
254 {
255     register struct monst *mtmp, *mtmp0, *mtmp2;
256     int dismissKops = 0;
257
258     /*
259      * First, scan migrating_mons for shopkeepers who want to dismiss Kops,
260      * and scan mydogs for shopkeepers who want to retain kops.
261      * Second, dismiss kops if warranted, making more room for arrival.
262      * Third, place monsters accompanying the hero.
263      * Last, place migrating monsters coming to this level.
264      *
265      * Hero might eventually be displaced (due to the third step, but
266      * occurring later), which is the main reason to do the second step
267      * sooner (in turn necessitating the first step, rather than combining
268      * the list scans with monster placement).
269      */
270
271     /* check for returning shk(s) */
272     for (mtmp = migrating_mons; mtmp; mtmp = mtmp->nmon) {
273         if (mtmp->mux != u.uz.dnum || mtmp->muy != u.uz.dlevel)
274             continue;
275         if (mtmp->isshk) {
276             if (ESHK(mtmp)->dismiss_kops) {
277                 if (dismissKops == 0)
278                     dismissKops = 1;
279                 ESHK(mtmp)->dismiss_kops = FALSE; /* reset */
280             } else if (!mtmp->mpeaceful) {
281                 /* an unpacified shk is returning; don't dismiss kops
282                    even if another pacified one is willing to do so */
283                 dismissKops = -1;
284                 /* [keep looping; later monsters might need ESHK reset] */
285             }
286         }
287     }
288     /* make the same check for mydogs */
289     for (mtmp = mydogs; mtmp && dismissKops >= 0; mtmp = mtmp->nmon) {
290         if (mtmp->isshk) {
291             /* hostile shk might accompany hero [ESHK(mtmp)->dismiss_kops
292                can't be set here; it's only used for migrating_mons] */
293             if (!mtmp->mpeaceful)
294                 dismissKops = -1;
295         }
296     }
297
298     /* when a hostile shopkeeper chases hero to another level
299        and then gets paid off there, get rid of summoned kops
300        here now that he has returned to his shop level */
301     if (dismissKops > 0)
302         make_happy_shoppers(TRUE);
303
304     /* place pets and/or any other monsters who accompany hero */
305     while ((mtmp = mydogs) != 0) {
306         mydogs = mtmp->nmon;
307         mon_arrive(mtmp, TRUE);
308     }
309
310     /* time for migrating monsters to arrive;
311        monsters who belong on this level but fail to arrive get put
312        back onto the list (at head), so traversing it is tricky */
313     for (mtmp = migrating_mons; mtmp; mtmp = mtmp2) {
314         mtmp2 = mtmp->nmon;
315         if (mtmp->mux == u.uz.dnum && mtmp->muy == u.uz.dlevel) {
316             /* remove mtmp from migrating_mons list */
317             if (mtmp == migrating_mons) {
318                 migrating_mons = mtmp->nmon;
319             } else {
320                 for (mtmp0 = migrating_mons; mtmp0; mtmp0 = mtmp0->nmon)
321                     if (mtmp0->nmon == mtmp) {
322                         mtmp0->nmon = mtmp->nmon;
323                         break;
324                     }
325                 if (!mtmp0)
326                     panic("losedogs: can't find migrating mon");
327             }
328             mon_arrive(mtmp, FALSE);
329         }
330     }
331 }
332
333 /* called from resurrect() in addition to losedogs() */
334 void
335 mon_arrive(mtmp, with_you)
336 struct monst *mtmp;
337 boolean with_you;
338 {
339     struct trap *t;
340     xchar xlocale, ylocale, xyloc, xyflags, wander;
341     int num_segs;
342     boolean failed_to_place = FALSE;
343
344     mtmp->nmon = fmon;
345     fmon = mtmp;
346     if (mtmp->isshk)
347         set_residency(mtmp, FALSE);
348
349     num_segs = mtmp->wormno;
350     /* baby long worms have no tail so don't use is_longworm() */
351     if (mtmp->data == &mons[PM_LONG_WORM]) {
352         mtmp->wormno = get_wormno();
353         if (mtmp->wormno)
354             initworm(mtmp, num_segs);
355     } else
356         mtmp->wormno = 0;
357
358     /* some monsters might need to do something special upon arrival
359        _after_ the current level has been fully set up; see dochug() */
360     mtmp->mstrategy |= STRAT_ARRIVE;
361
362     /* make sure mnexto(rloc_to(set_apparxy())) doesn't use stale data */
363     mtmp->mux = u.ux, mtmp->muy = u.uy;
364     xyloc = mtmp->mtrack[0].x;
365     xyflags = mtmp->mtrack[0].y;
366     xlocale = mtmp->mtrack[1].x;
367     ylocale = mtmp->mtrack[1].y;
368     memset(mtmp->mtrack, 0, sizeof mtmp->mtrack);
369
370     if (mtmp == u.usteed)
371         return; /* don't place steed on the map */
372     if (with_you) {
373         /* When a monster accompanies you, sometimes it will arrive
374            at your intended destination and you'll end up next to
375            that spot.  This code doesn't control the final outcome;
376            goto_level(do.c) decides who ends up at your target spot
377            when there is a monster there too. */
378         if (!MON_AT(u.ux, u.uy)
379             && !rn2(mtmp->mtame ? 10 : mtmp->mpeaceful ? 5 : 2))
380             rloc_to(mtmp, u.ux, u.uy);
381         else
382             mnexto(mtmp);
383         return;
384     }
385     /*
386      * The monster arrived on this level independently of the player.
387      * Its coordinate fields were overloaded for use as flags that
388      * specify its final destination.
389      */
390
391     if (mtmp->mlstmv < monstermoves - 1L) {
392         /* heal monster for time spent in limbo */
393         long nmv = monstermoves - 1L - mtmp->mlstmv;
394
395         mon_catchup_elapsed_time(mtmp, nmv);
396         mtmp->mlstmv = monstermoves - 1L;
397
398         /* let monster move a bit on new level (see placement code below) */
399         wander = (xchar) min(nmv, 8);
400     } else
401         wander = 0;
402
403     switch (xyloc) {
404     case MIGR_APPROX_XY: /* {x,y}locale set above */
405         break;
406     case MIGR_EXACT_XY:
407         wander = 0;
408         break;
409     case MIGR_WITH_HERO:
410         xlocale = u.ux, ylocale = u.uy;
411         break;
412     case MIGR_STAIRS_UP:
413         xlocale = xupstair, ylocale = yupstair;
414         break;
415     case MIGR_STAIRS_DOWN:
416         xlocale = xdnstair, ylocale = ydnstair;
417         break;
418     case MIGR_LADDER_UP:
419         xlocale = xupladder, ylocale = yupladder;
420         break;
421     case MIGR_LADDER_DOWN:
422         xlocale = xdnladder, ylocale = ydnladder;
423         break;
424     case MIGR_SSTAIRS:
425         xlocale = sstairs.sx, ylocale = sstairs.sy;
426         break;
427     case MIGR_PORTAL:
428         if (In_endgame(&u.uz)) {
429             /* there is no arrival portal for endgame levels */
430             /* BUG[?]: for simplicity, this code relies on the fact
431                that we know that the current endgame levels always
432                build upwards and never have any exclusion subregion
433                inside their TELEPORT_REGION settings. */
434             xlocale = rn1(updest.hx - updest.lx + 1, updest.lx);
435             ylocale = rn1(updest.hy - updest.ly + 1, updest.ly);
436             break;
437         }
438         /* find the arrival portal */
439         for (t = ftrap; t; t = t->ntrap)
440             if (t->ttyp == MAGIC_PORTAL)
441                 break;
442         if (t) {
443             xlocale = t->tx, ylocale = t->ty;
444             break;
445         } else {
446             impossible("mon_arrive: no corresponding portal?");
447         } /*FALLTHRU*/
448     default:
449     case MIGR_RANDOM:
450         xlocale = ylocale = 0;
451         break;
452     }
453
454     if ((mtmp->mspare1 & MIGR_LEFTOVERS) != 0L) {
455         /* Pick up the rest of the MIGR_TO_SPECIES objects */
456         if (migrating_objs)
457             deliver_obj_to_mon(mtmp, 0, DF_ALL);
458     }
459
460     if (xlocale && wander) {
461         /* monster moved a bit; pick a nearby location */
462         /* mnearto() deals w/stone, et al */
463         char *r = in_rooms(xlocale, ylocale, 0);
464
465         if (r && *r) {
466             coord c;
467
468             /* somexy() handles irregular rooms */
469             if (somexy(&rooms[*r - ROOMOFFSET], &c))
470                 xlocale = c.x, ylocale = c.y;
471             else
472                 xlocale = ylocale = 0;
473         } else { /* not in a room */
474             int i, j;
475
476             i = max(1, xlocale - wander);
477             j = min(COLNO - 1, xlocale + wander);
478             xlocale = rn1(j - i, i);
479             i = max(0, ylocale - wander);
480             j = min(ROWNO - 1, ylocale + wander);
481             ylocale = rn1(j - i, i);
482         }
483     } /* moved a bit */
484
485     mtmp->mx = 0; /*(already is 0)*/
486     mtmp->my = xyflags;
487     if (xlocale)
488         failed_to_place = !mnearto(mtmp, xlocale, ylocale, FALSE);
489     else
490         failed_to_place = !rloc(mtmp, TRUE);
491
492     if (failed_to_place)
493         m_into_limbo(mtmp); /* try again next time hero comes to this level */
494 }
495
496 /* heal monster for time spent elsewhere */
497 void
498 mon_catchup_elapsed_time(mtmp, nmv)
499 struct monst *mtmp;
500 long nmv; /* number of moves */
501 {
502     int imv = 0; /* avoid zillions of casts and lint warnings */
503
504 #if defined(DEBUG) || defined(BETA)
505     if (nmv < 0L) { /* crash likely... */
506         panic("catchup from future time?");
507         /*NOTREACHED*/
508         return;
509     } else if (nmv == 0L) { /* safe, but should'nt happen */
510         impossible("catchup from now?");
511     } else
512 #endif
513         if (nmv >= LARGEST_INT) /* paranoia */
514         imv = LARGEST_INT - 1;
515     else
516         imv = (int) nmv;
517
518     /* might stop being afraid, blind or frozen */
519     /* set to 1 and allow final decrement in movemon() */
520     if (mtmp->mblinded) {
521         if (imv >= (int) mtmp->mblinded)
522             mtmp->mblinded = 1;
523         else
524             mtmp->mblinded -= imv;
525     }
526     if (mtmp->mfrozen) {
527         if (imv >= (int) mtmp->mfrozen)
528             mtmp->mfrozen = 1;
529         else
530             mtmp->mfrozen -= imv;
531     }
532     if (mtmp->mfleetim) {
533         if (imv >= (int) mtmp->mfleetim)
534             mtmp->mfleetim = 1;
535         else
536             mtmp->mfleetim -= imv;
537     }
538
539     /* might recover from temporary trouble */
540     if (mtmp->mtrapped && rn2(imv + 1) > 40 / 2)
541         mtmp->mtrapped = 0;
542     if (mtmp->mconf && rn2(imv + 1) > 50 / 2)
543         mtmp->mconf = 0;
544     if (mtmp->mstun && rn2(imv + 1) > 10 / 2)
545         mtmp->mstun = 0;
546
547     /* might finish eating or be able to use special ability again */
548     if (imv > mtmp->meating)
549         finish_meating(mtmp);
550     else
551         mtmp->meating -= imv;
552     if (imv > mtmp->mspec_used)
553         mtmp->mspec_used = 0;
554     else
555         mtmp->mspec_used -= imv;
556
557     /* reduce tameness for every 150 moves you are separated */
558     if (mtmp->mtame) {
559         int wilder = (imv + 75) / 150;
560         if (mtmp->mtame > wilder)
561             mtmp->mtame -= wilder; /* less tame */
562         else if (mtmp->mtame > rn2(wilder))
563             mtmp->mtame = 0; /* untame */
564         else
565             mtmp->mtame = mtmp->mpeaceful = 0; /* hostile! */
566     }
567     /* check to see if it would have died as a pet; if so, go wild instead
568      * of dying the next time we call dog_move()
569      */
570     if (mtmp->mtame && !mtmp->isminion
571         && (carnivorous(mtmp->data) || herbivorous(mtmp->data))) {
572         struct edog *edog = EDOG(mtmp);
573
574         if ((monstermoves > edog->hungrytime + 500 && mtmp->mhp < 3)
575             || (monstermoves > edog->hungrytime + 750))
576             mtmp->mtame = mtmp->mpeaceful = 0;
577     }
578
579     if (!mtmp->mtame && mtmp->mleashed) {
580         /* leashed monsters should always be with hero, consequently
581            never losing any time to be accounted for later */
582         impossible("catching up for leashed monster?");
583         m_unleash(mtmp, FALSE);
584     }
585
586     /* recover lost hit points */
587     if (!regenerates(mtmp->data))
588         imv /= 20;
589     if (mtmp->mhp + imv >= mtmp->mhpmax)
590         mtmp->mhp = mtmp->mhpmax;
591     else
592         mtmp->mhp += imv;
593 }
594
595 /* called when you move to another level */
596 void
597 keepdogs(pets_only)
598 boolean pets_only; /* true for ascension or final escape */
599 {
600     register struct monst *mtmp, *mtmp2;
601     register struct obj *obj;
602     int num_segs;
603     boolean stay_behind;
604
605     for (mtmp = fmon; mtmp; mtmp = mtmp2) {
606         mtmp2 = mtmp->nmon;
607         if (DEADMONSTER(mtmp))
608             continue;
609         if (pets_only) {
610             if (!mtmp->mtame)
611                 continue; /* reject non-pets */
612             /* don't block pets from accompanying hero's dungeon
613                escape or ascension simply due to mundane trifles;
614                unlike level change for steed, don't bother trying
615                to achieve a normal trap escape first */
616             mtmp->mtrapped = 0;
617             mtmp->meating = 0;
618             mtmp->msleeping = 0;
619             mtmp->mfrozen = 0;
620             mtmp->mcanmove = 1;
621         }
622         if (((monnear(mtmp, u.ux, u.uy) && levl_follower(mtmp))
623              /* the wiz will level t-port from anywhere to chase
624                 the amulet; if you don't have it, will chase you
625                 only if in range. -3. */
626              || (u.uhave.amulet && mtmp->iswiz))
627             && ((!mtmp->msleeping && mtmp->mcanmove)
628                 /* eg if level teleport or new trap, steed has no control
629                    to avoid following */
630                 || (mtmp == u.usteed))
631             /* monster won't follow if it hasn't noticed you yet */
632             && !(mtmp->mstrategy & STRAT_WAITFORU)) {
633             stay_behind = FALSE;
634             if (mtmp->mtrapped)
635                 (void) mintrap(mtmp); /* try to escape */
636             if (mtmp == u.usteed) {
637                 /* make sure steed is eligible to accompany hero */
638                 mtmp->mtrapped = 0;       /* escape trap */
639                 mtmp->meating = 0;        /* terminate eating */
640                 mdrop_special_objs(mtmp); /* drop Amulet */
641             } else if (mtmp->meating || mtmp->mtrapped) {
642                 if (canseemon(mtmp))
643 #if 0 /*JP:T*/
644                     pline("%s is still %s.", Monnam(mtmp),
645                           mtmp->meating ? "eating" : "trapped");
646 #else
647                     pline("%s\82Í\82Ü\82¾%s\81D", Monnam(mtmp),
648                           mtmp->meating ? "\90H\82×\82Ä\82¢\82é" : "ã©\82É\82©\82©\82Á\82½\82Ü\82Ü\82¾");
649 #endif
650                 stay_behind = TRUE;
651             } else if (mon_has_amulet(mtmp)) {
652                 if (canseemon(mtmp))
653 /*JP
654                     pline("%s seems very disoriented for a moment.",
655 */
656                     pline("%s\82Í\88ê\8fu\95û\8cü\8a´\8ao\82ð\8e¸\82Á\82½\82æ\82¤\82¾\81D",
657                           Monnam(mtmp));
658                 stay_behind = TRUE;
659             }
660             if (stay_behind) {
661                 if (mtmp->mleashed) {
662 #if 0 /*JP:T*/
663                     pline("%s leash suddenly comes loose.",
664                           humanoid(mtmp->data)
665                               ? (mtmp->female ? "Her" : "His")
666                               : "Its");
667 #else
668                     pline("%s\82É\8c\8b\82Î\82ê\82½\95R\82Í\93Ë\91R\82ä\82é\82ñ\82¾\81D",
669                           humanoid(mtmp->data)
670                               ? (mtmp->female ? "\94Þ\8f\97" : "\94Þ")
671                               : "\82»\82Ì\90\95¨");
672 #endif
673                     m_unleash(mtmp, FALSE);
674                 }
675                 if (mtmp == u.usteed) {
676                     /* can't happen unless someone makes a change
677                        which scrambles the stay_behind logic above */
678                     impossible("steed left behind?");
679                     dismount_steed(DISMOUNT_GENERIC);
680                 }
681                 continue;
682             }
683             if (mtmp->isshk)
684                 set_residency(mtmp, TRUE);
685
686             if (mtmp->wormno) {
687                 register int cnt;
688                 /* NOTE: worm is truncated to # segs = max wormno size */
689                 cnt = count_wsegs(mtmp);
690                 num_segs = min(cnt, MAX_NUM_WORMS - 1);
691                 wormgone(mtmp);
692                 place_monster(mtmp, mtmp->mx, mtmp->my);
693             } else
694                 num_segs = 0;
695
696             /* set minvent's obj->no_charge to 0 */
697             for (obj = mtmp->minvent; obj; obj = obj->nobj) {
698                 if (Has_contents(obj))
699                     picked_container(obj); /* does the right thing */
700                 obj->no_charge = 0;
701             }
702
703             relmon(mtmp, &mydogs);   /* move it from map to mydogs */
704             mtmp->mx = mtmp->my = 0; /* avoid mnexto()/MON_AT() problem */
705             mtmp->wormno = num_segs;
706             mtmp->mlstmv = monstermoves;
707         } else if (mtmp->iswiz) {
708             /* we want to be able to find him when his next resurrection
709                chance comes up, but have him resume his present location
710                if player returns to this level before that time */
711             migrate_to_level(mtmp, ledger_no(&u.uz), MIGR_EXACT_XY,
712                              (coord *) 0);
713         } else if (mtmp->mleashed) {
714             /* this can happen if your quest leader ejects you from the
715                "home" level while a leashed pet isn't next to you */
716 /*JP
717             pline("%s leash goes slack.", s_suffix(Monnam(mtmp)));
718 */
719             pline("%s\82É\8c\8b\82Î\82ê\82½\95R\82Í\82½\82é\82ñ\82¾\81D", Monnam(mtmp));
720             m_unleash(mtmp, FALSE);
721         }
722     }
723 }
724
725 void
726 migrate_to_level(mtmp, tolev, xyloc, cc)
727 register struct monst *mtmp;
728 xchar tolev; /* destination level */
729 xchar xyloc; /* MIGR_xxx destination xy location: */
730 coord *cc;   /* optional destination coordinates */
731 {
732     struct obj *obj;
733     d_level new_lev;
734     xchar xyflags;
735     int num_segs = 0; /* count of worm segments */
736
737     if (mtmp->isshk)
738         set_residency(mtmp, TRUE);
739
740     if (mtmp->wormno) {
741         int cnt = count_wsegs(mtmp);
742
743         /* **** NOTE: worm is truncated to # segs = max wormno size **** */
744         num_segs = min(cnt, MAX_NUM_WORMS - 1); /* used below */
745         wormgone(mtmp); /* destroys tail and takes head off map */
746         /* there used to be a place_monster() here for the relmon() below,
747            but it doesn't require the monster to be on the map anymore */
748     }
749
750     /* set minvent's obj->no_charge to 0 */
751     for (obj = mtmp->minvent; obj; obj = obj->nobj) {
752         if (Has_contents(obj))
753             picked_container(obj); /* does the right thing */
754         obj->no_charge = 0;
755     }
756
757     if (mtmp->mleashed) {
758         mtmp->mtame--;
759         m_unleash(mtmp, TRUE);
760     }
761     relmon(mtmp, &migrating_mons); /* move it from map to migrating_mons */
762
763     new_lev.dnum = ledger_to_dnum((xchar) tolev);
764     new_lev.dlevel = ledger_to_dlev((xchar) tolev);
765     /* overload mtmp->[mx,my], mtmp->[mux,muy], and mtmp->mtrack[] as */
766     /* destination codes (setup flag bits before altering mx or my) */
767     xyflags = (depth(&new_lev) < depth(&u.uz)); /* 1 => up */
768     if (In_W_tower(mtmp->mx, mtmp->my, &u.uz))
769         xyflags |= 2;
770     mtmp->wormno = num_segs;
771     mtmp->mlstmv = monstermoves;
772     mtmp->mtrack[1].x = cc ? cc->x : mtmp->mx;
773     mtmp->mtrack[1].y = cc ? cc->y : mtmp->my;
774     mtmp->mtrack[0].x = xyloc;
775     mtmp->mtrack[0].y = xyflags;
776     mtmp->mux = new_lev.dnum;
777     mtmp->muy = new_lev.dlevel;
778     mtmp->mx = mtmp->my = 0; /* this implies migration */
779     if (mtmp == context.polearm.hitmon)
780         context.polearm.hitmon = (struct monst *) 0;
781 }
782
783 /* return quality of food; the lower the better */
784 /* fungi will eat even tainted food */
785 int
786 dogfood(mon, obj)
787 struct monst *mon;
788 register struct obj *obj;
789 {
790     struct permonst *mptr = mon->data, *fptr = 0;
791     boolean carni = carnivorous(mptr), herbi = herbivorous(mptr),
792             starving, mblind;
793
794     if (is_quest_artifact(obj) || obj_resists(obj, 0, 95))
795         return obj->cursed ? TABU : APPORT;
796
797     switch (obj->oclass) {
798     case FOOD_CLASS:
799         if (obj->otyp == CORPSE || obj->otyp == TIN || obj->otyp == EGG)
800             fptr = &mons[obj->corpsenm];
801
802         if (obj->otyp == CORPSE && is_rider(fptr))
803             return TABU;
804         if ((obj->otyp == CORPSE || obj->otyp == EGG) && touch_petrifies(fptr)
805             && !resists_ston(mon))
806             return POISON;
807         if (!carni && !herbi)
808             return obj->cursed ? UNDEF : APPORT;
809
810         /* a starving pet will eat almost anything */
811         starving = (mon->mtame && !mon->isminion
812                     && EDOG(mon)->mhpmax_penalty);
813         /* even carnivores will eat carrots if they're temporarily blind */
814         mblind = (!mon->mcansee && haseyes(mon->data));
815
816         /* ghouls prefer old corpses and unhatchable eggs, yum!
817            they'll eat fresh non-veggy corpses and hatchable eggs
818            when starving; they never eat stone-to-flesh'd meat */
819         if (mptr == &mons[PM_GHOUL]) {
820             if (obj->otyp == CORPSE)
821                 return (peek_at_iced_corpse_age(obj) + 50L <= monstermoves
822                         && fptr != &mons[PM_LIZARD]
823                         && fptr != &mons[PM_LICHEN])
824                            ? DOGFOOD
825                            : (starving && !vegan(fptr))
826                               ? ACCFOOD
827                               : POISON;
828             if (obj->otyp == EGG)
829                 return stale_egg(obj) ? CADAVER : starving ? ACCFOOD : POISON;
830             return TABU;
831         }
832
833         switch (obj->otyp) {
834         case TRIPE_RATION:
835         case MEATBALL:
836         case MEAT_RING:
837         case MEAT_STICK:
838         case HUGE_CHUNK_OF_MEAT:
839             return carni ? DOGFOOD : MANFOOD;
840         case EGG:
841             return carni ? CADAVER : MANFOOD;
842         case CORPSE:
843             if ((peek_at_iced_corpse_age(obj) + 50L <= monstermoves
844                  && obj->corpsenm != PM_LIZARD && obj->corpsenm != PM_LICHEN
845                  && mptr->mlet != S_FUNGUS)
846                 || (acidic(fptr) && !resists_acid(mon))
847                 || (poisonous(fptr) && !resists_poison(mon)))
848                 return POISON;
849             /* turning into slime is preferable to starvation */
850             else if (fptr == &mons[PM_GREEN_SLIME] && !slimeproof(mon->data))
851                 return starving ? ACCFOOD : POISON;
852             else if (vegan(fptr))
853                 return herbi ? CADAVER : MANFOOD;
854             /* most humanoids will avoid cannibalism unless starving;
855                arbitrary: elves won't eat other elves even then */
856             else if (humanoid(mptr) && same_race(mptr, fptr)
857                      && (!is_undead(mptr) && fptr->mlet != S_KOBOLD
858                          && fptr->mlet != S_ORC && fptr->mlet != S_OGRE))
859                 return (starving && carni && !is_elf(mptr)) ? ACCFOOD : TABU;
860             else
861                 return carni ? CADAVER : MANFOOD;
862         case CLOVE_OF_GARLIC:
863             return (is_undead(mptr) || is_vampshifter(mon))
864                       ? TABU
865                       : (herbi || starving)
866                          ? ACCFOOD
867                          : MANFOOD;
868         case TIN:
869             return metallivorous(mptr) ? ACCFOOD : MANFOOD;
870         case APPLE:
871             return herbi ? DOGFOOD : starving ? ACCFOOD : MANFOOD;
872         case CARROT:
873             return (herbi || mblind) ? DOGFOOD : starving ? ACCFOOD : MANFOOD;
874         case BANANA:
875             return (mptr->mlet == S_YETI && herbi)
876                       ? DOGFOOD /* for monkey and ape (tameable), sasquatch */
877                       : (herbi || starving)
878                          ? ACCFOOD
879                          : MANFOOD;
880         default:
881             if (starving)
882                 return ACCFOOD;
883             return (obj->otyp > SLIME_MOLD) ? (carni ? ACCFOOD : MANFOOD)
884                                             : (herbi ? ACCFOOD : MANFOOD);
885         }
886     default:
887         if (obj->otyp == AMULET_OF_STRANGULATION
888             || obj->otyp == RIN_SLOW_DIGESTION)
889             return TABU;
890         if (mon_hates_silver(mon) && objects[obj->otyp].oc_material == SILVER)
891             return TABU;
892         if (mptr == &mons[PM_GELATINOUS_CUBE] && is_organic(obj))
893             return ACCFOOD;
894         if (metallivorous(mptr) && is_metallic(obj)
895             && (is_rustprone(obj) || mptr != &mons[PM_RUST_MONSTER])) {
896             /* Non-rustproofed ferrous based metals are preferred. */
897             return (is_rustprone(obj) && !obj->oerodeproof) ? DOGFOOD
898                                                             : ACCFOOD;
899         }
900         if (!obj->cursed
901             && obj->oclass != BALL_CLASS
902             && obj->oclass != CHAIN_CLASS)
903             return APPORT;
904         /*FALLTHRU*/
905     case ROCK_CLASS:
906         return UNDEF;
907     }
908 }
909
910 /*
911  * With the separate mextra structure added in 3.6.x this always
912  * operates on the original mtmp. It now returns TRUE if the taming
913  * succeeded.
914  */
915 boolean
916 tamedog(mtmp, obj)
917 register struct monst *mtmp;
918 register struct obj *obj;
919 {
920     /* The Wiz, Medusa and the quest nemeses aren't even made peaceful. */
921     if (mtmp->iswiz || mtmp->data == &mons[PM_MEDUSA]
922         || (mtmp->data->mflags3 & M3_WANTSARTI))
923         return FALSE;
924
925     /* worst case, at least it'll be peaceful. */
926     mtmp->mpeaceful = 1;
927     set_malign(mtmp);
928     if (flags.moonphase == FULL_MOON && night() && rn2(6) && obj
929         && mtmp->data->mlet == S_DOG)
930         return FALSE;
931
932     /* If we cannot tame it, at least it's no longer afraid. */
933     mtmp->mflee = 0;
934     mtmp->mfleetim = 0;
935
936     /* make grabber let go now, whether it becomes tame or not */
937     if (mtmp == u.ustuck) {
938         if (u.uswallow)
939             expels(mtmp, mtmp->data, TRUE);
940         else if (!(Upolyd && sticks(youmonst.data)))
941             unstuck(mtmp);
942     }
943
944     /* feeding it treats makes it tamer */
945     if (mtmp->mtame && obj) {
946         int tasty;
947
948         if (mtmp->mcanmove && !mtmp->mconf && !mtmp->meating
949             && ((tasty = dogfood(mtmp, obj)) == DOGFOOD
950                 || (tasty <= ACCFOOD
951                     && EDOG(mtmp)->hungrytime <= monstermoves))) {
952             /* pet will "catch" and eat this thrown food */
953             if (canseemon(mtmp)) {
954                 boolean big_corpse =
955                     (obj->otyp == CORPSE && obj->corpsenm >= LOW_PM
956                      && mons[obj->corpsenm].msize > mtmp->data->msize);
957 #if 0 /*JP:T*/
958                 pline("%s catches %s%s", Monnam(mtmp), the(xname(obj)),
959                       !big_corpse ? "." : ", or vice versa!");
960 #else
961                 pline("%s\82Í%s\82ð\82Â\82©\82Ü\82¦\82½%s",
962                       Monnam(mtmp), xname(obj),
963                       !big_corpse ? "\81D" : "\81C\82Æ\8c¾\82¤\82æ\82è\82»\82Ì\8bt\82©\81I");
964 #endif
965             } else if (cansee(mtmp->mx, mtmp->my))
966 /*JP
967                 pline("%s.", Tobjnam(obj, "stop"));
968 */
969                 pline("%s\82Í\8e~\82Ü\82Á\82½\81D", xname(obj));
970             /* dog_eat expects a floor object */
971             place_object(obj, mtmp->mx, mtmp->my);
972             (void) dog_eat(mtmp, obj, mtmp->mx, mtmp->my, FALSE);
973             /* eating might have killed it, but that doesn't matter here;
974                a non-null result suppresses "miss" message for thrown
975                food and also implies that the object has been deleted */
976             return TRUE;
977         } else
978             return FALSE;
979     }
980
981     if (mtmp->mtame || !mtmp->mcanmove
982         /* monsters with conflicting structures cannot be tamed */
983         || mtmp->isshk || mtmp->isgd || mtmp->ispriest || mtmp->isminion
984         || is_covetous(mtmp->data) || is_human(mtmp->data)
985         || (is_demon(mtmp->data) && !is_demon(youmonst.data))
986         || (obj && dogfood(mtmp, obj) >= MANFOOD))
987         return FALSE;
988
989     if (mtmp->m_id == quest_status.leader_m_id)
990         return FALSE;
991
992     /* add the pet extension */
993     newedog(mtmp);
994     initedog(mtmp);
995
996     if (obj) { /* thrown food */
997         /* defer eating until the edog extension has been set up */
998         place_object(obj, mtmp->mx, mtmp->my); /* put on floor */
999         /* devour the food (might grow into larger, genocided monster) */
1000         if (dog_eat(mtmp, obj, mtmp->mx, mtmp->my, TRUE) == 2)
1001             return TRUE; /* oops, it died... */
1002         /* `obj' is now obsolete */
1003     }
1004
1005     newsym(mtmp->mx, mtmp->my);
1006     if (attacktype(mtmp->data, AT_WEAP)) {
1007         mtmp->weapon_check = NEED_HTH_WEAPON;
1008         (void) mon_wield_item(mtmp);
1009     }
1010     return TRUE;
1011 }
1012
1013 /*
1014  * Called during pet revival or pet life-saving.
1015  * If you killed the pet, it revives wild.
1016  * If you abused the pet a lot while alive, it revives wild.
1017  * If you abused the pet at all while alive, it revives untame.
1018  * If the pet wasn't abused and was very tame, it might revive tame.
1019  */
1020 void
1021 wary_dog(mtmp, was_dead)
1022 struct monst *mtmp;
1023 boolean was_dead;
1024 {
1025     struct edog *edog;
1026     boolean quietly = was_dead;
1027
1028     finish_meating(mtmp);
1029
1030     if (!mtmp->mtame)
1031         return;
1032     edog = !mtmp->isminion ? EDOG(mtmp) : 0;
1033
1034     /* if monster was starving when it died, undo that now */
1035     if (edog && edog->mhpmax_penalty) {
1036         mtmp->mhpmax += edog->mhpmax_penalty;
1037         mtmp->mhp += edog->mhpmax_penalty; /* heal it */
1038         edog->mhpmax_penalty = 0;
1039     }
1040
1041     if (edog && (edog->killed_by_u == 1 || edog->abuse > 2)) {
1042         mtmp->mpeaceful = mtmp->mtame = 0;
1043         if (edog->abuse >= 0 && edog->abuse < 10)
1044             if (!rn2(edog->abuse + 1))
1045                 mtmp->mpeaceful = 1;
1046         if (!quietly && cansee(mtmp->mx, mtmp->my)) {
1047             if (haseyes(youmonst.data)) {
1048                 if (haseyes(mtmp->data))
1049 #if 0 /*JP:T*/
1050                     pline("%s %s to look you in the %s.", Monnam(mtmp),
1051                           mtmp->mpeaceful ? "seems unable" : "refuses",
1052                           body_part(EYE));
1053 #else
1054                     pline("%s\82Í\82 \82È\82½\82Ì%s%s\81D", Monnam(mtmp),
1055                           body_part(EYE),
1056                           mtmp->mpeaceful ? "\82ð\8c©\82é\82±\82Æ\82ª\82Å\82«\82È\82¢\82æ\82¤\82¾" :
1057                           "\82©\82ç\96Ú\82ð\82»\82ç\82µ\82½");
1058 #endif
1059                 else
1060 /*JP
1061                     pline("%s avoids your gaze.", Monnam(mtmp));
1062 */
1063                     pline("%s\82Í\82 \82È\82½\82Ì\82É\82ç\82Ý\82ð\89ñ\94ð\82µ\82½\81D", Monnam(mtmp));
1064             }
1065         }
1066     } else {
1067         /* chance it goes wild anyway - Pet Sematary */
1068         mtmp->mtame = rn2(mtmp->mtame + 1);
1069         if (!mtmp->mtame)
1070             mtmp->mpeaceful = rn2(2);
1071     }
1072
1073     if (!mtmp->mtame) {
1074         if (!quietly && canspotmon(mtmp))
1075 #if 0 /*JP:T*/
1076             pline("%s %s.", Monnam(mtmp),
1077                   mtmp->mpeaceful ? "is no longer tame" : "has become feral");
1078 #else
1079             pline("%s\82Í%s\81D", Monnam(mtmp),
1080                   mtmp->mpeaceful ? "\83y\83b\83g\82Å\82È\82­\82È\82Á\82½" : "\96ì\90\89»\82µ\82½");
1081 #endif
1082         newsym(mtmp->mx, mtmp->my);
1083         /* a life-saved monster might be leashed;
1084            don't leave it that way if it's no longer tame */
1085         if (mtmp->mleashed)
1086             m_unleash(mtmp, TRUE);
1087         if (mtmp == u.usteed)
1088             dismount_steed(DISMOUNT_THROWN);
1089     } else if (edog) {
1090         /* it's still a pet; start a clean pet-slate now */
1091         edog->revivals++;
1092         edog->killed_by_u = 0;
1093         edog->abuse = 0;
1094         edog->ogoal.x = edog->ogoal.y = -1;
1095         if (was_dead || edog->hungrytime < monstermoves + 500L)
1096             edog->hungrytime = monstermoves + 500L;
1097         if (was_dead) {
1098             edog->droptime = 0L;
1099             edog->dropdist = 10000;
1100             edog->whistletime = 0L;
1101             edog->apport = 5;
1102         } /* else lifesaved, so retain current values */
1103     }
1104 }
1105
1106 void
1107 abuse_dog(mtmp)
1108 struct monst *mtmp;
1109 {
1110     if (!mtmp->mtame)
1111         return;
1112
1113     if (Aggravate_monster || Conflict)
1114         mtmp->mtame /= 2;
1115     else
1116         mtmp->mtame--;
1117
1118     if (mtmp->mtame && !mtmp->isminion)
1119         EDOG(mtmp)->abuse++;
1120
1121     if (!mtmp->mtame && mtmp->mleashed)
1122         m_unleash(mtmp, TRUE);
1123
1124     /* don't make a sound if pet is in the middle of leaving the level */
1125     /* newsym isn't necessary in this case either */
1126     if (mtmp->mx != 0) {
1127         if (mtmp->mtame && rn2(mtmp->mtame))
1128             yelp(mtmp);
1129         else
1130             growl(mtmp); /* give them a moment's worry */
1131
1132         if (!mtmp->mtame)
1133             newsym(mtmp->mx, mtmp->my);
1134     }
1135 }
1136
1137 /*dog.c*/