OSDN Git Service

update year to 2020
[jnethack/source.git] / src / eat.c
1 /* NetHack 3.6  eat.c   $NHDT-Date: 1574900825 2019/11/28 00:27:05 $  $NHDT-Branch: NetHack-3.6 $:$NHDT-Revision: 1.206 $ */
2 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
3 /*-Copyright (c) Robert Patrick Rankin, 2012. */
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-2020            */
9 /* JNetHack may be freely redistributed.  See license for details. */
10
11 #include "hack.h"
12
13 STATIC_PTR int NDECL(eatmdone);
14 STATIC_PTR int NDECL(eatfood);
15 STATIC_PTR struct obj *FDECL(costly_tin, (int));
16 STATIC_PTR int NDECL(opentin);
17 STATIC_PTR int NDECL(unfaint);
18
19 STATIC_DCL const char *FDECL(food_xname, (struct obj *, BOOLEAN_P));
20 STATIC_DCL void FDECL(choke, (struct obj *));
21 STATIC_DCL void NDECL(recalc_wt);
22 STATIC_DCL unsigned FDECL(obj_nutrition, (struct obj *));
23 STATIC_DCL struct obj *FDECL(touchfood, (struct obj *));
24 STATIC_DCL void NDECL(do_reset_eat);
25 STATIC_DCL void FDECL(done_eating, (BOOLEAN_P));
26 STATIC_DCL void FDECL(cprefx, (int));
27 STATIC_DCL int FDECL(intrinsic_possible, (int, struct permonst *));
28 STATIC_DCL void FDECL(givit, (int, struct permonst *));
29 STATIC_DCL void FDECL(cpostfx, (int));
30 STATIC_DCL void FDECL(consume_tin, (const char *));
31 STATIC_DCL void FDECL(start_tin, (struct obj *));
32 STATIC_DCL int FDECL(eatcorpse, (struct obj *));
33 STATIC_DCL void FDECL(start_eating, (struct obj *, BOOLEAN_P));
34 STATIC_DCL void FDECL(fprefx, (struct obj *));
35 STATIC_DCL void FDECL(fpostfx, (struct obj *));
36 STATIC_DCL int NDECL(bite);
37 STATIC_DCL int FDECL(edibility_prompts, (struct obj *));
38 STATIC_DCL int FDECL(rottenfood, (struct obj *));
39 STATIC_DCL void NDECL(eatspecial);
40 STATIC_DCL int FDECL(bounded_increase, (int, int, int));
41 STATIC_DCL void FDECL(accessory_has_effect, (struct obj *));
42 STATIC_DCL void FDECL(eataccessory, (struct obj *));
43 STATIC_DCL const char *FDECL(foodword, (struct obj *));
44 STATIC_DCL int FDECL(tin_variety, (struct obj *, BOOLEAN_P));
45 STATIC_DCL boolean FDECL(maybe_cannibal, (int, BOOLEAN_P));
46
47 char msgbuf[BUFSZ];
48
49 /* also used to see if you're allowed to eat cats and dogs */
50 #define CANNIBAL_ALLOWED() (Role_if(PM_CAVEMAN) || Race_if(PM_ORC))
51
52 /* monster types that cause hero to be turned into stone if eaten */
53 #define flesh_petrifies(pm) (touch_petrifies(pm) || (pm) == &mons[PM_MEDUSA])
54
55 /* Rider corpses are treated as non-rotting so that attempting to eat one
56    will be sure to reach the stage of eating where that meal is fatal */
57 #define nonrotting_corpse(mnum) \
58     ((mnum) == PM_LIZARD || (mnum) == PM_LICHEN || is_rider(&mons[mnum]))
59
60 /* non-rotting non-corpses; unlike lizard corpses, these items will behave
61    as if rotten if they are cursed (fortune cookies handled elsewhere) */
62 #define nonrotting_food(otyp) \
63     ((otyp) == LEMBAS_WAFER || (otyp) == CRAM_RATION)
64
65 STATIC_OVL NEARDATA const char comestibles[] = { FOOD_CLASS, 0 };
66 STATIC_OVL NEARDATA const char offerfodder[] = { FOOD_CLASS, AMULET_CLASS,
67                                                  0 };
68
69 /* Gold must come first for getobj(). */
70 STATIC_OVL NEARDATA const char allobj[] = {
71     COIN_CLASS,   WEAPON_CLASS, ARMOR_CLASS,  POTION_CLASS,
72     SCROLL_CLASS, WAND_CLASS,   RING_CLASS,   AMULET_CLASS,
73     FOOD_CLASS,   TOOL_CLASS,   GEM_CLASS,    ROCK_CLASS,
74     BALL_CLASS,   CHAIN_CLASS,  SPBOOK_CLASS, 0
75 };
76
77 STATIC_OVL boolean force_save_hs = FALSE;
78
79 /* see hunger states in hack.h - texts used on bottom line */
80 #if 0 /*JP:T*/
81 const char *hu_stat[] = { "Satiated", "        ", "Hungry  ", "Weak    ",
82                           "Fainting", "Fainted ", "Starved " };
83 #else
84 const char *hu_stat[] = { "\96\9e\95     ", "        ", "\82Ø\82±\82Ø\82±", "\90\8a\8eã    ",
85                           "\82Ó\82ç\82Ó\82ç", "\91²\93|    ", "\89ì\8e\80    " };
86 #endif
87
88 /*
89  * Decide whether a particular object can be eaten by the possibly
90  * polymorphed character.  Not used for monster checks.
91  */
92 boolean
93 is_edible(obj)
94 register struct obj *obj;
95 {
96     /* protect invocation tools but not Rider corpses (handled elsewhere)*/
97     /* if (obj->oclass != FOOD_CLASS && obj_resists(obj, 0, 0)) */
98     if (objects[obj->otyp].oc_unique)
99         return FALSE;
100     /* above also prevents the Amulet from being eaten, so we must never
101        allow fake amulets to be eaten either [which is already the case] */
102
103     if (metallivorous(youmonst.data) && is_metallic(obj)
104         && (youmonst.data != &mons[PM_RUST_MONSTER] || is_rustprone(obj)))
105         return TRUE;
106
107     /* Ghouls only eat non-veggy corpses or eggs (see dogfood()) */
108     if (u.umonnum == PM_GHOUL)
109         return (boolean)((obj->otyp == CORPSE
110                           && !vegan(&mons[obj->corpsenm]))
111                          || (obj->otyp == EGG));
112
113     if (u.umonnum == PM_GELATINOUS_CUBE && is_organic(obj)
114         /* [g.cubes can eat containers and retain all contents
115             as engulfed items, but poly'd player can't do that] */
116         && !Has_contents(obj))
117         return TRUE;
118
119     /* return (boolean) !!index(comestibles, obj->oclass); */
120     return (boolean) (obj->oclass == FOOD_CLASS);
121 }
122
123 /* used for hero init, life saving (if choking), and prayer results of fix
124    starving, fix weak from hunger, or golden glow boon (if u.uhunger < 900) */
125 void
126 init_uhunger()
127 {
128     context.botl = (u.uhs != NOT_HUNGRY || ATEMP(A_STR) < 0);
129     u.uhunger = 900;
130     u.uhs = NOT_HUNGRY;
131     if (ATEMP(A_STR) < 0) {
132         ATEMP(A_STR) = 0;
133         (void) encumber_msg();
134     }
135 }
136
137 /* tin types [SPINACH_TIN = -1, overrides corpsenm, nut==600] */
138 static const struct {
139     const char *txt;                      /* description */
140     int nut;                              /* nutrition */
141     Bitfield(fodder, 1);                  /* stocked by health food shops */
142     Bitfield(greasy, 1);                  /* causes slippery fingers */
143 #if 0 /*JP:T*/
144 } tintxts[] = { { "rotten", -50, 0, 0 },  /* ROTTEN_TIN = 0 */
145                 { "homemade", 50, 1, 0 }, /* HOMEMADE_TIN = 1 */
146                 { "soup made from", 20, 1, 0 },
147                 { "french fried", 40, 0, 1 },
148                 { "pickled", 40, 1, 0 },
149                 { "boiled", 50, 1, 0 },
150                 { "smoked", 50, 1, 0 },
151                 { "dried", 55, 1, 0 },
152                 { "deep fried", 60, 0, 1 },
153                 { "szechuan", 70, 1, 0 },
154                 { "broiled", 80, 0, 0 },
155                 { "stir fried", 80, 0, 1 },
156                 { "sauteed", 95, 0, 0 },
157                 { "candied", 100, 1, 0 },
158                 { "pureed", 500, 1, 0 },
159                 { "", 0, 0, 0 } };
160 #else
161 } tintxts[] = { { "\95\85\82Á\82½", -50, 0, 0 },  /* ROTTEN_TIN = 0 */
162                 { "\8e©\89Æ\90»\82Ì", 50, 1, 0 }, /* HOMEMADE_TIN = 1 */
163                 { "\82Ì\83X\81[\83v", 20, 1, 0 },
164                 { "\82Ì\83t\83\89\83C", 40, 0, 1 },
165                 { "\82Ì\92Ð\95¨", 40, 1, 0 },
166                 { "\82ä\82Å", 50, 1, 0 },
167                 { "\82Ìà\8e\90»", 50, 1, 0 },
168                 { "\8a£\91\87", 55, 1, 0 },
169                 { "\82Ì\97g\82°\95¨", 60, 0, 1 },
170                 { "\8el\90ì\95\97", 70, 1, 0 },
171                 { "\82Ì\96Ô\8fÄ\82«", 80, 0, 0 },
172                 { "àu\82ß", 80, 0, 1 },
173                 { "\82Ì\83\\83e\81[", 95, 0, 0 },
174                 { "\82Ì\8d»\93\9c\92Ð\82¯", 100, 1, 0 },
175                 { "\82Ì\83s\83\85\81[\83\8c", 500, 1, 0 },
176                 { "", 0, 0, 0 } };
177 #endif
178 #define TTSZ SIZE(tintxts)
179
180 static char *eatmbuf = 0; /* set by cpostfx() */
181
182 /* called after mimicing is over */
183 STATIC_PTR int
184 eatmdone(VOID_ARGS)
185 {
186     /* release `eatmbuf' */
187     if (eatmbuf) {
188         if (nomovemsg == eatmbuf)
189             nomovemsg = 0;
190         free((genericptr_t) eatmbuf), eatmbuf = 0;
191     }
192     /* update display */
193     if (U_AP_TYPE) {
194         youmonst.m_ap_type = M_AP_NOTHING;
195         newsym(u.ux, u.uy);
196     }
197     return 0;
198 }
199
200 /* called when hallucination is toggled */
201 void
202 eatmupdate()
203 {
204     const char *altmsg = 0;
205     int altapp = 0; /* lint suppression */
206
207     if (!eatmbuf || nomovemsg != eatmbuf)
208         return;
209
210     if (is_obj_mappear(&youmonst,ORANGE) && !Hallucination) {
211         /* revert from hallucinatory to "normal" mimicking */
212 /*JP
213         altmsg = "You now prefer mimicking yourself.";
214 */
215         altmsg = "\82 \82È\82½\82Í\8e©\95ª\8e©\90g\82Ì\82Ü\82Ë\82ð\82·\82é\82±\82Æ\82ð\91I\82ñ\82¾\81D";
216         altapp = GOLD_PIECE;
217     } else if (is_obj_mappear(&youmonst,GOLD_PIECE) && Hallucination) {
218         /* won't happen; anything which might make immobilized
219            hero begin hallucinating (black light attack, theft
220            of Grayswandir) will terminate the mimicry first */
221 /*JP
222         altmsg = "Your rind escaped intact.";
223 */
224         altmsg = "\82 \82È\82½\82Ì\94ç\82ª\82»\82Ì\82Ü\82Ü\82Ì\8c`\82Å\93¦\82°\82Ä\82¢\82Á\82½\81D";
225         altapp = ORANGE;
226     }
227
228     if (altmsg) {
229         /* replace end-of-mimicking message */
230         if (strlen(altmsg) > strlen(eatmbuf)) {
231             free((genericptr_t) eatmbuf);
232             eatmbuf = (char *) alloc(strlen(altmsg) + 1);
233         }
234         nomovemsg = strcpy(eatmbuf, altmsg);
235         /* update current image */
236         youmonst.mappearance = altapp;
237         newsym(u.ux, u.uy);
238     }
239 }
240
241 /* ``[the(] singular(food, xname) [)]'' */
242 STATIC_OVL const char *
243 food_xname(food, the_pfx)
244 struct obj *food;
245 boolean the_pfx;
246 {
247     const char *result;
248
249     if (food->otyp == CORPSE) {
250         result = corpse_xname(food, (const char *) 0,
251                               CXN_SINGULAR | (the_pfx ? CXN_PFX_THE : 0));
252         /* not strictly needed since pname values are capitalized
253            and the() is a no-op for them */
254         if (type_is_pname(&mons[food->corpsenm]))
255             the_pfx = FALSE;
256     } else {
257         /* the ordinary case */
258         result = singular(food, xname);
259     }
260     if (the_pfx)
261         result = the(result);
262     return result;
263 }
264
265 /* Created by GAN 01/28/87
266  * Amended by AKP 09/22/87: if not hard, don't choke, just vomit.
267  * Amended by 3.  06/12/89: if not hard, sometimes choke anyway, to keep risk.
268  *                11/10/89: if hard, rarely vomit anyway, for slim chance.
269  *
270  * To a full belly all food is bad. (It.)
271  */
272 STATIC_OVL void
273 choke(food)
274 struct obj *food;
275 {
276     /* only happens if you were satiated */
277     if (u.uhs != SATIATED) {
278         if (!food || food->otyp != AMULET_OF_STRANGULATION)
279             return;
280     } else if (Role_if(PM_KNIGHT) && u.ualign.type == A_LAWFUL) {
281         adjalign(-1); /* gluttony is unchivalrous */
282 /*JP
283         You_feel("like a glutton!");
284 */
285         You("\91å\90H\8a¿\82Ì\82æ\82¤\82È\8bC\82ª\82µ\82½\81I");
286     }
287
288     exercise(A_CON, FALSE);
289
290     if (Breathless || (!Strangled && !rn2(20))) {
291         /* choking by eating AoS doesn't involve stuffing yourself */
292         if (food && food->otyp == AMULET_OF_STRANGULATION) {
293 /*JP
294             You("choke, but recover your composure.");
295 */
296             You("\8eñ\82ð\8di\82ß\82ç\82ê\82½\81D\82µ\82©\82µ\82È\82ñ\82Æ\82à\82È\82©\82Á\82½\81D");
297             return;
298         }
299 /*JP
300         You("stuff yourself and then vomit voluminously.");
301 */
302         pline("\82ª\82Â\82ª\82Â\82Æ\8cû\82É\8bl\82ß\8d\9e\82ñ\82¾\82ª\81C\83h\83o\82Á\82Æ\93f\82«\8fo\82µ\82Ä\82µ\82Ü\82Á\82½\81D");
303         morehungry(1000); /* you just got *very* sick! */
304         vomit();
305     } else {
306         killer.format = KILLED_BY_AN;
307         /*
308          * Note all "killer"s below read "Choked on %s" on the
309          * high score list & tombstone.  So plan accordingly.
310          */
311         if (food) {
312 /*JP
313             You("choke over your %s.", foodword(food));
314 */
315             You("%s\82ð\8dA\82É\8bl\82Ü\82ç\82¹\82Ä\82µ\82Ü\82Á\82½\81D", foodword(food));
316             if (food->oclass == COIN_CLASS) {
317 /*JP
318                 Strcpy(killer.name, "very rich meal");
319 */
320                 Strcpy(killer.name, "\82Æ\82Ä\82à\8d\82\89¿\82È\97¿\97\9d");
321             } else {
322                 killer.format = KILLED_BY;
323                 Strcpy(killer.name, killer_xname(food));
324             }
325         } else {
326 /*JP
327             You("choke over it.");
328 */
329             pline("\8dA\82É\8bl\82Ü\82ç\82¹\82Ä\82µ\82Ü\82Á\82½\81D");
330 /*JP
331             Strcpy(killer.name, "quick snack");
332 */
333             Strcpy(killer.name, "\91\81\90H\82¢");
334         }
335 /*JP
336         You("die...");
337 */
338         pline("\82 \82È\82½\82Í\8e\80\82É\82Ü\82µ\82½\81D\81D\81D");
339         done(CHOKING);
340     }
341 }
342
343 /* modify object wt. depending on time spent consuming it */
344 STATIC_OVL void
345 recalc_wt()
346 {
347     struct obj *piece = context.victual.piece;
348     if (!piece) {
349         impossible("recalc_wt without piece");
350         return;
351     }
352     debugpline1("Old weight = %d", piece->owt);
353     debugpline2("Used time = %d, Req'd time = %d", context.victual.usedtime,
354                 context.victual.reqtime);
355     piece->owt = weight(piece);
356     debugpline1("New weight = %d", piece->owt);
357 }
358
359 /* called when eating interrupted by an event */
360 void
361 reset_eat()
362 {
363     /* we only set a flag here - the actual reset process is done after
364      * the round is spent eating.
365      */
366     if (context.victual.eating && !context.victual.doreset) {
367         debugpline0("reset_eat...");
368         context.victual.doreset = TRUE;
369     }
370     return;
371 }
372
373 /* base nutrition of a food-class object */
374 STATIC_OVL unsigned
375 obj_nutrition(otmp)
376 struct obj *otmp;
377 {
378     unsigned nut = (otmp->otyp == CORPSE) ? mons[otmp->corpsenm].cnutrit
379                       : otmp->globby ? otmp->owt
380                          : (unsigned) objects[otmp->otyp].oc_nutrition;
381
382     if (otmp->otyp == LEMBAS_WAFER) {
383         if (maybe_polyd(is_elf(youmonst.data), Race_if(PM_ELF)))
384             nut += nut / 4; /* 800 -> 1000 */
385         else if (maybe_polyd(is_orc(youmonst.data), Race_if(PM_ORC)))
386             nut -= nut / 4; /* 800 -> 600 */
387         /* prevent polymorph making a partly eaten wafer
388            become more nutritious than an untouched one */
389         if (otmp->oeaten >= nut)
390             otmp->oeaten = (otmp->oeaten < objects[LEMBAS_WAFER].oc_nutrition)
391                               ? (nut - 1) : nut;
392     } else if (otmp->otyp == CRAM_RATION) {
393         if (maybe_polyd(is_dwarf(youmonst.data), Race_if(PM_DWARF)))
394             nut += nut / 6; /* 600 -> 700 */
395     }
396     return nut;
397 }
398
399 STATIC_OVL struct obj *
400 touchfood(otmp)
401 struct obj *otmp;
402 {
403     if (otmp->quan > 1L) {
404         if (!carried(otmp))
405             (void) splitobj(otmp, otmp->quan - 1L);
406         else
407             otmp = splitobj(otmp, 1L);
408         debugpline0("split object,");
409     }
410
411     if (!otmp->oeaten) {
412         costly_alteration(otmp, COST_BITE);
413         otmp->oeaten = obj_nutrition(otmp);
414     }
415
416     if (carried(otmp)) {
417         freeinv(otmp);
418         if (inv_cnt(FALSE) >= 52) {
419             sellobj_state(SELL_DONTSELL);
420             dropy(otmp);
421             sellobj_state(SELL_NORMAL);
422         } else {
423             otmp->nomerge = 1; /* used to prevent merge */
424             otmp = addinv(otmp);
425             otmp->nomerge = 0;
426         }
427     }
428     return otmp;
429 }
430
431 /* When food decays, in the middle of your meal, we don't want to dereference
432  * any dangling pointers, so set it to null (which should still trigger
433  * do_reset_eat() at the beginning of eatfood()) and check for null pointers
434  * in do_reset_eat().
435  */
436 void
437 food_disappears(obj)
438 struct obj *obj;
439 {
440     if (obj == context.victual.piece) {
441         context.victual.piece = (struct obj *) 0;
442         context.victual.o_id = 0;
443     }
444     if (obj->timed)
445         obj_stop_timers(obj);
446 }
447
448 /* renaming an object used to result in it having a different address,
449    so the sequence start eating/opening, get interrupted, name the food,
450    resume eating/opening would restart from scratch */
451 void
452 food_substitution(old_obj, new_obj)
453 struct obj *old_obj, *new_obj;
454 {
455     if (old_obj == context.victual.piece) {
456         context.victual.piece = new_obj;
457         context.victual.o_id = new_obj->o_id;
458     }
459     if (old_obj == context.tin.tin) {
460         context.tin.tin = new_obj;
461         context.tin.o_id = new_obj->o_id;
462     }
463 }
464
465 STATIC_OVL void
466 do_reset_eat()
467 {
468     debugpline0("do_reset_eat...");
469     if (context.victual.piece) {
470         context.victual.o_id = 0;
471         context.victual.piece = touchfood(context.victual.piece);
472         if (context.victual.piece)
473             context.victual.o_id = context.victual.piece->o_id;
474         recalc_wt();
475     }
476     context.victual.fullwarn = context.victual.eating =
477         context.victual.doreset = FALSE;
478     /* Do not set canchoke to FALSE; if we continue eating the same object
479      * we need to know if canchoke was set when they started eating it the
480      * previous time.  And if we don't continue eating the same object
481      * canchoke always gets recalculated anyway.
482      */
483     stop_occupation();
484     newuhs(FALSE);
485 }
486
487 /* called each move during eating process */
488 STATIC_PTR int
489 eatfood(VOID_ARGS)
490 {
491     if (!context.victual.piece
492         || (!carried(context.victual.piece)
493             && !obj_here(context.victual.piece, u.ux, u.uy))) {
494         /* maybe it was stolen? */
495         do_reset_eat();
496         return 0;
497     }
498     if (!context.victual.eating)
499         return 0;
500
501     if (++context.victual.usedtime <= context.victual.reqtime) {
502         if (bite())
503             return 0;
504         return 1; /* still busy */
505     } else {        /* done */
506         done_eating(TRUE);
507         return 0;
508     }
509 }
510
511 STATIC_OVL void
512 done_eating(message)
513 boolean message;
514 {
515     struct obj *piece = context.victual.piece;
516
517     piece->in_use = TRUE;
518     occupation = 0; /* do this early, so newuhs() knows we're done */
519     newuhs(FALSE);
520     if (nomovemsg) {
521         if (message)
522             pline1(nomovemsg);
523         nomovemsg = 0;
524     } else if (message)
525 /*JP
526         You("finish eating %s.", food_xname(piece, TRUE));
527 */
528         You("%s\82ð\90H\82×\8fI\82¦\82½\81D",  food_xname(piece, TRUE));
529
530     if (piece->otyp == CORPSE || piece->globby)
531         cpostfx(piece->corpsenm);
532     else
533         fpostfx(piece);
534
535     if (carried(piece))
536         useup(piece);
537     else
538         useupf(piece, 1L);
539     context.victual.piece = (struct obj *) 0;
540     context.victual.o_id = 0;
541     context.victual.fullwarn = context.victual.eating =
542         context.victual.doreset = FALSE;
543 }
544
545 void
546 eating_conducts(pd)
547 struct permonst *pd;
548 {
549     u.uconduct.food++;
550     if (!vegan(pd))
551         u.uconduct.unvegan++;
552     if (!vegetarian(pd))
553         violated_vegetarian();
554 }
555
556 /* handle side-effects of mind flayer's tentacle attack */
557 int
558 eat_brains(magr, mdef, visflag, dmg_p)
559 struct monst *magr, *mdef;
560 boolean visflag;
561 int *dmg_p; /* for dishing out extra damage in lieu of Int loss */
562 {
563     struct permonst *pd = mdef->data;
564     boolean give_nutrit = FALSE;
565     int result = MM_HIT, xtra_dmg = rnd(10);
566
567     if (noncorporeal(pd)) {
568         if (visflag)
569 #if 0 /*JP:T*/
570             pline("%s brain is unharmed.",
571                   (mdef == &youmonst) ? "Your" : s_suffix(Monnam(mdef)));
572 #else
573             pline("%s\82Ì\94]\82Í\96³\8e\96\82¾\82Á\82½\81D",
574                   (mdef == &youmonst) ? "\82 \82È\82½" : Monnam(mdef));
575 #endif
576         return MM_MISS; /* side-effects can't occur */
577     } else if (magr == &youmonst) {
578 /*JP
579         You("eat %s brain!", s_suffix(mon_nam(mdef)));
580 */
581         You("%s\82Ì\94]\82ð\90H\82×\82½\81I", mon_nam(mdef));
582     } else if (mdef == &youmonst) {
583 /*JP
584         Your("brain is eaten!");
585 */
586         Your("\94]\82Í\90H\82×\82ç\82ê\82½\81I");
587     } else { /* monster against monster */
588         if (visflag && canspotmon(mdef))
589 /*JP
590             pline("%s brain is eaten!", s_suffix(Monnam(mdef)));
591 */
592             pline("%s\82Ì\94]\82Í\90H\82×\82ç\82ê\82½\81I", Monnam(mdef));
593     }
594
595     if (flesh_petrifies(pd)) {
596         /* mind flayer has attempted to eat the brains of a petrification
597            inducing critter (most likely Medusa; attacking a cockatrice via
598            tentacle-touch should have been caught before reaching this far) */
599         if (magr == &youmonst) {
600             if (!Stone_resistance && !Stoned)
601                 make_stoned(5L, (char *) 0, KILLED_BY_AN, pd->mname);
602         } else {
603             /* no need to check for poly_when_stoned or Stone_resistance;
604                mind flayers don't have those capabilities */
605             if (visflag && canseemon(magr))
606 /*JP
607                 pline("%s turns to stone!", Monnam(magr));
608 */
609                 pline("%s\82Í\90Î\82É\82È\82Á\82½\81I", Monnam(magr));
610             monstone(magr);
611             if (!DEADMONSTER(magr)) {
612                 /* life-saved; don't continue eating the brains */
613                 return MM_MISS;
614             } else {
615                 if (magr->mtame && !visflag)
616                     /* parallels mhitm.c's brief_feeling */
617 /*JP
618                     You("have a sad thought for a moment, then it passes.");
619 */
620                     You("\94ß\82µ\82¢\8dl\82¦\82É\82¨\82»\82í\82ê\82½\82ª\81A\82·\82®\82É\89ß\82¬\82³\82Á\82½\81D");
621                 return MM_AGR_DIED;
622             }
623         }
624     }
625
626     if (magr == &youmonst) {
627         /*
628          * player mind flayer is eating something's brain
629          */
630         eating_conducts(pd);
631         if (mindless(pd)) { /* (cannibalism not possible here) */
632 /*JP
633             pline("%s doesn't notice.", Monnam(mdef));
634 */
635             pline("%s\82Í\8bC\82Ã\82¢\82Ä\82¢\82È\82¢\81D", Monnam(mdef));
636             /* all done; no extra harm inflicted upon target */
637             return MM_MISS;
638         } else if (is_rider(pd)) {
639 /*JP
640             pline("Ingesting that is fatal.");
641 */
642             pline("\8eæ\82è\8d\9e\82ñ\82¾\82ç\82·\82®\82É\8e\80\82ñ\82Å\82µ\82Ü\82Á\82½\81D");
643 #if 0 /*JP:T*/
644             Sprintf(killer.name, "unwisely ate the brain of %s", pd->mname);
645             killer.format = NO_KILLER_PREFIX;
646 #else
647             Sprintf(killer.name, "\8bð\82©\82É\82à%s\82Ì\91Ì\82ð\90H\82×\82Ä", pd->mname);
648             killer.format = KILLED_BY;
649 #endif
650             done(DIED);
651             /* life-saving needed to reach here */
652             exercise(A_WIS, FALSE);
653             *dmg_p += xtra_dmg; /* Rider takes extra damage */
654         } else {
655             morehungry(-rnd(30)); /* cannot choke */
656             if (ABASE(A_INT) < AMAX(A_INT)) {
657                 /* recover lost Int; won't increase current max */
658                 ABASE(A_INT) += rnd(4);
659                 if (ABASE(A_INT) > AMAX(A_INT))
660                     ABASE(A_INT) = AMAX(A_INT);
661                 context.botl = 1;
662             }
663             exercise(A_WIS, TRUE);
664             *dmg_p += xtra_dmg;
665         }
666         /* targetting another mind flayer or your own underlying species
667            is cannibalism */
668         (void) maybe_cannibal(monsndx(pd), TRUE);
669
670     } else if (mdef == &youmonst) {
671         /*
672          * monster mind flayer is eating hero's brain
673          */
674         /* no such thing as mindless players */
675         if (ABASE(A_INT) <= ATTRMIN(A_INT)) {
676 /*JP
677             static NEARDATA const char brainlessness[] = "brainlessness";
678 */
679             static NEARDATA const char brainlessness[] = "\94]\82ð\8e¸\82Á\82Ä";
680
681             if (Lifesaved) {
682                 Strcpy(killer.name, brainlessness);
683                 killer.format = KILLED_BY;
684                 done(DIED);
685                 /* amulet of life saving has now been used up */
686 /*JP
687                 pline("Unfortunately your brain is still gone.");
688 */
689                 pline("\8ec\94O\82È\82ª\82ç\82 \82È\82½\82É\82Í\94]\82ª\82È\82¢\81D");
690                 /* sanity check against adding other forms of life-saving */
691                 u.uprops[LIFESAVED].extrinsic =
692                     u.uprops[LIFESAVED].intrinsic = 0L;
693             } else {
694 /*JP
695                 Your("last thought fades away.");
696 */
697                 Your("\8dÅ\8cã\82Ì\8ev\82¢\82ª\91\96\94n\93\95\82Ì\82æ\82¤\82É\89¡\82¬\82Á\82½\81D");
698             }
699             Strcpy(killer.name, brainlessness);
700             killer.format = KILLED_BY;
701             done(DIED);
702             /* can only get here when in wizard or explore mode and user has
703                explicitly chosen not to die; arbitrarily boost intelligence */
704             ABASE(A_INT) = ATTRMIN(A_INT) + 2;
705 /*JP
706             You_feel("like a scarecrow.");
707 */
708             You("\82©\82©\82µ\82Ì\82æ\82¤\82È\8bC\8e\9d\82ª\82µ\82½\81D");
709         }
710         give_nutrit = TRUE; /* in case a conflicted pet is doing this */
711         exercise(A_WIS, FALSE);
712         /* caller handles Int and memory loss */
713
714     } else { /* mhitm */
715         /*
716          * monster mind flayer is eating another monster's brain
717          */
718         if (mindless(pd)) {
719             if (visflag && canspotmon(mdef))
720 /*JP
721                 pline("%s doesn't notice.", Monnam(mdef));
722 */
723                 pline("%s\82Í\8bC\82Ã\82¢\82Ä\82¢\82È\82¢\81D", Monnam(mdef));
724             return MM_MISS;
725         } else if (is_rider(pd)) {
726             mondied(magr);
727             if (DEADMONSTER(magr))
728                 result = MM_AGR_DIED;
729             /* Rider takes extra damage regardless of whether attacker dies */
730             *dmg_p += xtra_dmg;
731         } else {
732             *dmg_p += xtra_dmg;
733             give_nutrit = TRUE;
734             if (*dmg_p >= mdef->mhp && visflag && canspotmon(mdef))
735 #if 0 /*JP:T*/
736                 pline("%s last thought fades away...",
737                       s_suffix(Monnam(mdef)));
738 #else
739                 pline("%s\82Ì\8dÅ\8cã\82Ì\8ev\82¢\82ª\82æ\82¬\82é\81D\81D\81D",
740                       Monnam(mdef));
741 #endif
742         }
743     }
744
745     if (give_nutrit && magr->mtame && !magr->isminion) {
746         EDOG(magr)->hungrytime += rnd(60);
747         magr->mconf = 0;
748     }
749
750     return result;
751 }
752
753 /* eating a corpse or egg of one's own species is usually naughty */
754 STATIC_OVL boolean
755 maybe_cannibal(pm, allowmsg)
756 int pm;
757 boolean allowmsg;
758 {
759     static NEARDATA long ate_brains = 0L;
760     struct permonst *fptr = &mons[pm]; /* food type */
761
762     /* when poly'd into a mind flayer, multiple tentacle hits in one
763        turn cause multiple digestion checks to occur; avoid giving
764        multiple luck penalties for the same attack */
765     if (moves == ate_brains)
766         return FALSE;
767     ate_brains = moves; /* ate_anything, not just brains... */
768
769     if (!CANNIBAL_ALLOWED()
770         /* non-cannibalistic heroes shouldn't eat own species ever
771            and also shouldn't eat current species when polymorphed
772            (even if having the form of something which doesn't care
773            about cannibalism--hero's innate traits aren't altered) */
774         && (your_race(fptr)
775             || (Upolyd && same_race(youmonst.data, fptr))
776             || (u.ulycn >= LOW_PM && were_beastie(pm) == u.ulycn))) {
777         if (allowmsg) {
778             if (Upolyd && your_race(fptr))
779 /*JP
780                 You("have a bad feeling deep inside.");
781 */
782                 You("\8c\99\88«\8a´\82É\82¨\82»\82í\82ê\82½\81D");
783 /*JP
784             You("cannibal!  You will regret this!");
785 */
786             pline("\8b¤\8bò\82¢\82¾\81I\8cã\89÷\82·\82é\82¼\81I");
787         }
788         HAggravate_monster |= FROMOUTSIDE;
789         change_luck(-rn1(4, 2)); /* -5..-2 */
790         return TRUE;
791     }
792     return FALSE;
793 }
794
795 STATIC_OVL void
796 cprefx(pm)
797 register int pm;
798 {
799     (void) maybe_cannibal(pm, TRUE);
800     if (flesh_petrifies(&mons[pm])) {
801         if (!Stone_resistance
802             && !(poly_when_stoned(youmonst.data)
803                  && polymon(PM_STONE_GOLEM))) {
804 /*JP
805             Sprintf(killer.name, "tasting %s meat", mons[pm].mname);
806 */
807             Sprintf(killer.name, "%s\82Ì\93÷\82ð\90H\82×", mons[pm].mname);
808             killer.format = KILLED_BY;
809 /*JP
810             You("turn to stone.");
811 */
812             You("\90Î\82É\82È\82Á\82½\81D");
813             done(STONING);
814             if (context.victual.piece)
815                 context.victual.eating = FALSE;
816             return; /* lifesaved */
817         }
818     }
819
820     switch (pm) {
821     case PM_LITTLE_DOG:
822     case PM_DOG:
823     case PM_LARGE_DOG:
824     case PM_KITTEN:
825     case PM_HOUSECAT:
826     case PM_LARGE_CAT:
827         /* cannibals are allowed to eat domestic animals without penalty */
828         if (!CANNIBAL_ALLOWED()) {
829 /*JP
830             You_feel("that eating the %s was a bad idea.", mons[pm].mname);
831 */
832             pline("%s\82ð\90H\82×\82é\82Ì\82Í\82æ\82­\82È\82¢\8bC\82ª\82µ\82½\81D", mons[pm].mname);
833             HAggravate_monster |= FROMOUTSIDE;
834         }
835         break;
836     case PM_LIZARD:
837         if (Stoned)
838             fix_petrification();
839         break;
840     case PM_DEATH:
841     case PM_PESTILENCE:
842     case PM_FAMINE: {
843 /*JP
844         pline("Eating that is instantly fatal.");
845 */
846         pline("\90H\82×\82½\82ç\82·\82®\82É\8e\80\82ñ\82Å\82µ\82Ü\82Á\82½\81D");
847 #if 0 /*JP:T*/
848         Sprintf(killer.name, "unwisely ate the body of %s", mons[pm].mname);
849         killer.format = NO_KILLER_PREFIX;
850 #else
851         Sprintf(killer.name, "\8bð\82©\82É\82à%s\82Ì\91Ì\82ð\90H\82×\82Ä", mons[pm].mname);
852         killer.format = KILLED_BY;
853 #endif
854         done(DIED);
855         /* life-saving needed to reach here */
856         exercise(A_WIS, FALSE);
857         /* It so happens that since we know these monsters */
858         /* cannot appear in tins, context.victual.piece will always */
859         /* be what we want, which is not generally true. */
860         if (revive_corpse(context.victual.piece)) {
861             context.victual.piece = (struct obj *) 0;
862             context.victual.o_id = 0;
863         }
864         return;
865     }
866     case PM_GREEN_SLIME:
867         if (!Slimed && !Unchanging && !slimeproof(youmonst.data)) {
868 /*JP
869             You("don't feel very well.");
870 */
871             You("\82·\82²\82­\8bC\95ª\82ª\88«\82¢\81D");
872             make_slimed(10L, (char *) 0);
873             delayed_killer(SLIMED, KILLED_BY_AN, "");
874         }
875     /* Fall through */
876     default:
877         if (acidic(&mons[pm]) && Stoned)
878             fix_petrification();
879         break;
880     }
881 }
882
883 void
884 fix_petrification()
885 {
886     char buf[BUFSZ];
887
888     if (Hallucination)
889 #if 0 /*JP:T*/
890         Sprintf(buf, "What a pity--you just ruined a future piece of %sart!",
891                 ACURR(A_CHA) > 15 ? "fine " : "");
892 #else
893         Sprintf(buf, "\82È\82ñ\82Ä\82±\82Æ\82¾\81I%s\8c|\8fp\8dì\95i\82É\82È\82ê\82½\82©\82à\82µ\82ê\82È\82¢\82Ì\82É\81I",
894                 ACURR(A_CHA) > 15 ? "\8bM\8fd\82È" : "");
895 #endif
896     else
897 /*JP
898         Strcpy(buf, "You feel limber!");
899 */
900         Strcpy(buf, "\91Ì\82ª\93î\82ç\82©\82­\82È\82Á\82½\82æ\82¤\82È\8bC\82ª\82µ\82½\81I");
901     make_stoned(0L, buf, 0, (char *) 0);
902 }
903
904 /*
905  * If you add an intrinsic that can be gotten by eating a monster, add it
906  * to intrinsic_possible() and givit().  (It must already be in prop.h to
907  * be an intrinsic property.)
908  * It would be very easy to make the intrinsics not try to give you one
909  * that you already had by checking to see if you have it in
910  * intrinsic_possible() instead of givit(), but we're not that nice.
911  */
912
913 /* intrinsic_possible() returns TRUE iff a monster can give an intrinsic. */
914 STATIC_OVL int
915 intrinsic_possible(type, ptr)
916 int type;
917 register struct permonst *ptr;
918 {
919     int res = 0;
920
921 #ifdef DEBUG
922 #define ifdebugresist(Msg)      \
923     do {                        \
924         if (res)                \
925             debugpline0(Msg);   \
926     } while (0)
927 #else
928 #define ifdebugresist(Msg) /*empty*/
929 #endif
930     switch (type) {
931     case FIRE_RES:
932         res = (ptr->mconveys & MR_FIRE) != 0;
933         ifdebugresist("can get fire resistance");
934         break;
935     case SLEEP_RES:
936         res = (ptr->mconveys & MR_SLEEP) != 0;
937         ifdebugresist("can get sleep resistance");
938         break;
939     case COLD_RES:
940         res = (ptr->mconveys & MR_COLD) != 0;
941         ifdebugresist("can get cold resistance");
942         break;
943     case DISINT_RES:
944         res = (ptr->mconveys & MR_DISINT) != 0;
945         ifdebugresist("can get disintegration resistance");
946         break;
947     case SHOCK_RES: /* shock (electricity) resistance */
948         res = (ptr->mconveys & MR_ELEC) != 0;
949         ifdebugresist("can get shock resistance");
950         break;
951     case POISON_RES:
952         res = (ptr->mconveys & MR_POISON) != 0;
953         ifdebugresist("can get poison resistance");
954         break;
955     case TELEPORT:
956         res = can_teleport(ptr);
957         ifdebugresist("can get teleport");
958         break;
959     case TELEPORT_CONTROL:
960         res = control_teleport(ptr);
961         ifdebugresist("can get teleport control");
962         break;
963     case TELEPAT:
964         res = telepathic(ptr);
965         ifdebugresist("can get telepathy");
966         break;
967     default:
968         /* res stays 0 */
969         break;
970     }
971 #undef ifdebugresist
972     return res;
973 }
974
975 /* givit() tries to give you an intrinsic based on the monster's level
976  * and what type of intrinsic it is trying to give you.
977  */
978 STATIC_OVL void
979 givit(type, ptr)
980 int type;
981 register struct permonst *ptr;
982 {
983     register int chance;
984
985     debugpline1("Attempting to give intrinsic %d", type);
986     /* some intrinsics are easier to get than others */
987     switch (type) {
988     case POISON_RES:
989         if ((ptr == &mons[PM_KILLER_BEE] || ptr == &mons[PM_SCORPION])
990             && !rn2(4))
991             chance = 1;
992         else
993             chance = 15;
994         break;
995     case TELEPORT:
996         chance = 10;
997         break;
998     case TELEPORT_CONTROL:
999         chance = 12;
1000         break;
1001     case TELEPAT:
1002         chance = 1;
1003         break;
1004     default:
1005         chance = 15;
1006         break;
1007     }
1008
1009     if (ptr->mlevel <= rn2(chance))
1010         return; /* failed die roll */
1011
1012     switch (type) {
1013     case FIRE_RES:
1014         debugpline0("Trying to give fire resistance");
1015         if (!(HFire_resistance & FROMOUTSIDE)) {
1016 /*JP
1017             You(Hallucination ? "be chillin'." : "feel a momentary chill.");
1018 */
1019             You(Hallucination ? "\81u\83N\81[\83\8b\91î\94z\95Ö\81v\82³\82ê\82Ä\82¢\82é\82æ\82¤\82¾\81D" : "\88ê\8fu\8a¦\82¯\82ª\82µ\82½\81D");
1020             HFire_resistance |= FROMOUTSIDE;
1021         }
1022         break;
1023     case SLEEP_RES:
1024         debugpline0("Trying to give sleep resistance");
1025         if (!(HSleep_resistance & FROMOUTSIDE)) {
1026 /*JP
1027             You_feel("wide awake.");
1028 */
1029             You("\82Ï\82Á\82¿\82è\96Ú\82ª\82³\82ß\82½\81D");
1030             HSleep_resistance |= FROMOUTSIDE;
1031         }
1032         break;
1033     case COLD_RES:
1034         debugpline0("Trying to give cold resistance");
1035         if (!(HCold_resistance & FROMOUTSIDE)) {
1036 /*JP
1037             You_feel("full of hot air.");
1038 */
1039             You("\94M\95\97\82ð\91S\90g\82É\8a´\82\82½\81D");
1040             HCold_resistance |= FROMOUTSIDE;
1041         }
1042         break;
1043     case DISINT_RES:
1044         debugpline0("Trying to give disintegration resistance");
1045         if (!(HDisint_resistance & FROMOUTSIDE)) {
1046 /*JP
1047             You_feel(Hallucination ? "totally together, man." : "very firm.");
1048 */
1049             You_feel(Hallucination ? "\90¢\8aE\90l\97Þ\82Æ\8cZ\92í\82É\82È\82Á\82½\82æ\82¤\82È\8bC\82ª\82µ\82½\81D" : "\82Æ\82Ä\82à\8aæ\8fä\82É\82È\82Á\82½\82æ\82¤\82È\8bC\82ª\82µ\82½\81D");
1050             HDisint_resistance |= FROMOUTSIDE;
1051         }
1052         break;
1053     case SHOCK_RES: /* shock (electricity) resistance */
1054         debugpline0("Trying to give shock resistance");
1055         if (!(HShock_resistance & FROMOUTSIDE)) {
1056             if (Hallucination)
1057 /*JP
1058                 You_feel("grounded in reality.");
1059 */
1060                 You("\8eÀ\82Í\83A\81[\83X\82³\82ê\82Ä\82¢\82é\82æ\82¤\82È\8bC\82ª\82µ\82½\81D");
1061             else
1062 /*JP
1063                 Your("health currently feels amplified!");
1064 */
1065                 pline("\8c\92\8dN\82ª\91\9d\95\9d\82³\82ê\82½\82æ\82¤\82È\8bC\82ª\82µ\82½\81I");
1066             HShock_resistance |= FROMOUTSIDE;
1067         }
1068         break;
1069     case POISON_RES:
1070         debugpline0("Trying to give poison resistance");
1071         if (!(HPoison_resistance & FROMOUTSIDE)) {
1072 /*JP
1073             You_feel(Poison_resistance ? "especially healthy." : "healthy.");
1074 */
1075             You_feel(Poison_resistance ? "\93Á\82É\8c\92\8dN\82É\82È\82Á\82½\8bC\82ª\82µ\82½\81D" : "\8c\92\8dN\82É\82È\82Á\82½\8bC\82ª\82µ\82½\81D");
1076             HPoison_resistance |= FROMOUTSIDE;
1077         }
1078         break;
1079     case TELEPORT:
1080         debugpline0("Trying to give teleport");
1081         if (!(HTeleportation & FROMOUTSIDE)) {
1082 /*JP
1083             You_feel(Hallucination ? "diffuse." : "very jumpy.");
1084 */
1085             pline(Hallucination ? "\91Ì\82ª\94ò\82Ñ\8eU\82Á\82½\82æ\82¤\82È\8bC\82ª\82µ\82½\81D" : "\92µ\96ô\97Í\82ª\8d\82\82Ü\82Á\82½\82æ\82¤\82È\8bC\82ª\82µ\82½\81D");
1086             HTeleportation |= FROMOUTSIDE;
1087         }
1088         break;
1089     case TELEPORT_CONTROL:
1090         debugpline0("Trying to give teleport control");
1091         if (!(HTeleport_control & FROMOUTSIDE)) {
1092 #if 0 /*JP:T*/
1093             You_feel(Hallucination ? "centered in your personal space."
1094                                    : "in control of yourself.");
1095 #else
1096             You_feel(Hallucination ? "\8e©\8cÈ\92\86\90S\93I\82É\82È\82Á\82½\82æ\82¤\82È\8bC\82ª\82µ\82½\81D"
1097                                    : "\8e©\95ª\8e©\90g\82ð\90§\8cä\82Å\82«\82é\82æ\82¤\82È\8bC\82ª\82µ\82½\81D");
1098 #endif
1099             HTeleport_control |= FROMOUTSIDE;
1100         }
1101         break;
1102     case TELEPAT:
1103         debugpline0("Trying to give telepathy");
1104         if (!(HTelepat & FROMOUTSIDE)) {
1105 #if 0 /*JP:T*/
1106             You_feel(Hallucination ? "in touch with the cosmos."
1107                                    : "a strange mental acuity.");
1108 #else
1109             You_feel(Hallucination ? "\89F\92\88\82Ì\90_\94é\82É\90G\82ê\82½\82æ\82¤\82È\8bC\82ª\82µ\82½\81D"
1110                                    : "\8aï\96­\82È\90¸\90_\93I\89s\82³\82ð\8a´\82\82½\81D");
1111 #endif
1112             HTelepat |= FROMOUTSIDE;
1113             /* If blind, make sure monsters show up. */
1114             if (Blind)
1115                 see_monsters();
1116         }
1117         break;
1118     default:
1119         debugpline0("Tried to give an impossible intrinsic");
1120         break;
1121     }
1122 }
1123
1124 /* called after completely consuming a corpse */
1125 STATIC_OVL void
1126 cpostfx(pm)
1127 int pm;
1128 {
1129     int tmp = 0;
1130     int catch_lycanthropy = NON_PM;
1131     boolean check_intrinsics = FALSE;
1132
1133     /* in case `afternmv' didn't get called for previously mimicking
1134        gold, clean up now to avoid `eatmbuf' memory leak */
1135     if (eatmbuf)
1136         (void) eatmdone();
1137
1138     switch (pm) {
1139     case PM_NEWT:
1140         /* MRKR: "eye of newt" may give small magical energy boost */
1141         if (rn2(3) || 3 * u.uen <= 2 * u.uenmax) {
1142             int old_uen = u.uen;
1143
1144             u.uen += rnd(3);
1145             if (u.uen > u.uenmax) {
1146                 if (!rn2(3))
1147                     u.uenmax++;
1148                 u.uen = u.uenmax;
1149             }
1150             if (old_uen != u.uen) {
1151 /*JP
1152                 You_feel("a mild buzz.");
1153 */
1154                 You("\82·\82±\82µ\82Ó\82ç\82Ó\82ç\82µ\82½\81D");
1155                 context.botl = 1;
1156             }
1157         }
1158         break;
1159     case PM_WRAITH:
1160         pluslvl(FALSE);
1161         break;
1162     case PM_HUMAN_WERERAT:
1163         catch_lycanthropy = PM_WERERAT;
1164         break;
1165     case PM_HUMAN_WEREJACKAL:
1166         catch_lycanthropy = PM_WEREJACKAL;
1167         break;
1168     case PM_HUMAN_WEREWOLF:
1169         catch_lycanthropy = PM_WEREWOLF;
1170         break;
1171     case PM_NURSE:
1172         if (Upolyd)
1173             u.mh = u.mhmax;
1174         else
1175             u.uhp = u.uhpmax;
1176         make_blinded(0L, !u.ucreamed);
1177         context.botl = 1;
1178         check_intrinsics = TRUE; /* might also convey poison resistance */
1179         break;
1180     case PM_STALKER:
1181         if (!Invis) {
1182             set_itimeout(&HInvis, (long) rn1(100, 50));
1183             if (!Blind && !BInvis)
1184                 self_invis_message();
1185         } else {
1186             if (!(HInvis & INTRINSIC))
1187 /*JP
1188                 You_feel("hidden!");
1189 */
1190                 Your("\8ep\82Í\89B\82³\82ê\82½\81I");
1191             HInvis |= FROMOUTSIDE;
1192             HSee_invisible |= FROMOUTSIDE;
1193         }
1194         newsym(u.ux, u.uy);
1195         /*FALLTHRU*/
1196     case PM_YELLOW_LIGHT:
1197     case PM_GIANT_BAT:
1198         make_stunned((HStun & TIMEOUT) + 30L, FALSE);
1199         /*FALLTHRU*/
1200     case PM_BAT:
1201         make_stunned((HStun & TIMEOUT) + 30L, FALSE);
1202         break;
1203     case PM_GIANT_MIMIC:
1204         tmp += 10;
1205         /*FALLTHRU*/
1206     case PM_LARGE_MIMIC:
1207         tmp += 20;
1208         /*FALLTHRU*/
1209     case PM_SMALL_MIMIC:
1210         tmp += 20;
1211         if (youmonst.data->mlet != S_MIMIC && !Unchanging) {
1212             char buf[BUFSZ];
1213
1214             u.uconduct.polyselfs++; /* you're changing form */
1215 #if 0 /*JP:T*/
1216             You_cant("resist the temptation to mimic %s.",
1217                      Hallucination ? "an orange" : "a pile of gold");
1218 #else
1219             You("%s\82ð\90^\8e\97\82µ\82½\82¢\97U\98f\82É\82©\82ç\82ê\82½\81D",
1220                      Hallucination ? "\83I\83\8c\83\93\83W" : "\8bà\89Ý\82Ì\8eR");
1221 #endif
1222             /* A pile of gold can't ride. */
1223             if (u.usteed)
1224                 dismount_steed(DISMOUNT_FELL);
1225             nomul(-tmp);
1226 /*JP
1227             multi_reason = "pretending to be a pile of gold";
1228 */
1229             multi_reason = "\8bà\89Ý\82Ì\8eR\82Ì\90^\8e\97\82ð\82µ\82Ä\82¢\82é\8e\9e\82É";
1230             Sprintf(buf,
1231                     Hallucination
1232 /*JP
1233                        ? "You suddenly dread being peeled and mimic %s again!"
1234 */
1235                        ? "\93Ë\91R\8aÛ\97\87\82É\82³\82ê\82é\82Ì\82ª\8b°\82ë\82µ\82­\82È\82Á\82Ä\82Ü\82½%s\82Ì\90^\8e\97\82ð\82µ\82½\81I"
1236 /*JP
1237                        : "You now prefer mimicking %s again.",
1238 */
1239                        : "\82±\82ñ\82Ç\82Í\82Ü\82½%s\82Ì\90^\8e\97\82ª\82µ\82½\82­\82È\82Á\82½\81D",
1240                     an(Upolyd ? youmonst.data->mname : urace.noun));
1241             eatmbuf = dupstr(buf);
1242             nomovemsg = eatmbuf;
1243             afternmv = eatmdone;
1244             /* ??? what if this was set before? */
1245             youmonst.m_ap_type = M_AP_OBJECT;
1246             youmonst.mappearance = Hallucination ? ORANGE : GOLD_PIECE;
1247             newsym(u.ux, u.uy);
1248             curs_on_u();
1249             /* make gold symbol show up now */
1250             display_nhwindow(WIN_MAP, TRUE);
1251         }
1252         break;
1253     case PM_QUANTUM_MECHANIC:
1254 /*JP
1255         Your("velocity suddenly seems very uncertain!");
1256 */
1257         Your("\91¬\93x\82ª\93Ë\91R\81C\95s\8am\92è\82É\82È\82Á\82½\81I");
1258         if (HFast & INTRINSIC) {
1259             HFast &= ~INTRINSIC;
1260 /*JP
1261             You("seem slower.");
1262 */
1263             You("\92x\82­\82È\82Á\82½\82æ\82¤\82¾\81D");
1264         } else {
1265             HFast |= FROMOUTSIDE;
1266 /*JP
1267             You("seem faster.");
1268 */
1269             You("\91¬\82­\82È\82Á\82½\82æ\82¤\82¾\81D");
1270         }
1271         break;
1272     case PM_LIZARD:
1273         if ((HStun & TIMEOUT) > 2)
1274             make_stunned(2L, FALSE);
1275         if ((HConfusion & TIMEOUT) > 2)
1276             make_confused(2L, FALSE);
1277         break;
1278     case PM_CHAMELEON:
1279     case PM_DOPPELGANGER:
1280     case PM_SANDESTIN: /* moot--they don't leave corpses */
1281         if (Unchanging) {
1282 #if 0 /*JP:T*/
1283             You_feel("momentarily different."); /* same as poly trap */
1284 #else
1285             You_feel("\88ê\8fu\88á\82Á\82½\8a´\82\82ª\82µ\82½\81D"); /* same as poly trap */
1286 #endif
1287         } else {
1288 /*JP
1289             You_feel("a change coming over you.");
1290 */
1291             pline("\95Ï\89»\82ª\96K\82ê\82½\81D");
1292             polyself(0);
1293         }
1294         break;
1295     case PM_DISENCHANTER:
1296         /* picks an intrinsic at random and removes it; there's
1297            no feedback if hero already lacks the chosen ability */
1298         debugpline0("using attrcurse to strip an intrinsic");
1299         attrcurse();
1300         break;
1301     case PM_MIND_FLAYER:
1302     case PM_MASTER_MIND_FLAYER:
1303         if (ABASE(A_INT) < ATTRMAX(A_INT)) {
1304             if (!rn2(2)) {
1305 /*JP
1306                 pline("Yum!  That was real brain food!");
1307 */
1308                 pline("\82¤\82Ü\82¢\81I\82±\82ê\82±\82»\96{\93\96\82Ì\81u\93ª\82Ì\97Ç\82­\82È\82é\90H\8e\96\81v\82¾\81I");
1309                 (void) adjattrib(A_INT, 1, FALSE);
1310                 break; /* don't give them telepathy, too */
1311             }
1312         } else {
1313 /*JP
1314             pline("For some reason, that tasted bland.");
1315 */
1316             pline("\82Ç\82¤\82µ\82½\82í\82¯\82©\81C\92W\94\92\82È\96¡\82¾\81D");
1317         }
1318     /*FALLTHRU*/
1319     default:
1320         check_intrinsics = TRUE;
1321         break;
1322     }
1323
1324     /* possibly convey an intrinsic */
1325     if (check_intrinsics) {
1326         struct permonst *ptr = &mons[pm];
1327         boolean conveys_STR = is_giant(ptr);
1328         int i, count;
1329
1330         if (dmgtype(ptr, AD_STUN) || dmgtype(ptr, AD_HALU)
1331             || pm == PM_VIOLET_FUNGUS) {
1332 /*JP
1333             pline("Oh wow!  Great stuff!");
1334 */
1335             pline("\83\8f\81[\83H\81I\82±\82è\82á\82·\82²\82¢\81I");
1336             (void) make_hallucinated((HHallucination & TIMEOUT) + 200L, FALSE,
1337                                      0L);
1338         }
1339
1340         /* Check the monster for all of the intrinsics.  If this
1341          * monster can give more than one, pick one to try to give
1342          * from among all it can give.
1343          *
1344          * Strength from giants is now treated like an intrinsic
1345          * rather than being given unconditionally.
1346          */
1347         count = 0; /* number of possible intrinsics */
1348         tmp = 0;   /* which one we will try to give */
1349         if (conveys_STR) {
1350             count = 1;
1351             tmp = -1; /* use -1 as fake prop index for STR */
1352             debugpline1("\"Intrinsic\" strength, %d", tmp);
1353         }
1354         for (i = 1; i <= LAST_PROP; i++) {
1355             if (!intrinsic_possible(i, ptr))
1356                 continue;
1357             ++count;
1358             /* a 1 in count chance of replacing the old choice
1359                with this one, and a count-1 in count chance
1360                of keeping the old choice (note that 1 in 1 and
1361                0 in 1 are what we want for the first candidate) */
1362             if (!rn2(count)) {
1363                 debugpline2("Intrinsic %d replacing %d", i, tmp);
1364                 tmp = i;
1365             }
1366         }
1367         /* if strength is the only candidate, give it 50% chance */
1368         if (conveys_STR && count == 1 && !rn2(2))
1369             tmp = 0;
1370         /* if something was chosen, give it now (givit() might fail) */
1371         if (tmp == -1)
1372             gainstr((struct obj *) 0, 0, TRUE);
1373         else if (tmp > 0)
1374             givit(tmp, ptr);
1375     } /* check_intrinsics */
1376
1377     if (catch_lycanthropy >= LOW_PM) {
1378         set_ulycn(catch_lycanthropy);
1379         retouch_equipment(2);
1380     }
1381     return;
1382 }
1383
1384 void
1385 violated_vegetarian()
1386 {
1387     u.uconduct.unvegetarian++;
1388     if (Role_if(PM_MONK)) {
1389 /*JP
1390         You_feel("guilty.");
1391 */
1392         pline("\8dß\82ð\8a´\82\82½\81D");
1393         adjalign(-1);
1394     }
1395     return;
1396 }
1397
1398 /* common code to check and possibly charge for 1 context.tin.tin,
1399  * will split() context.tin.tin if necessary */
1400 STATIC_PTR struct obj *
1401 costly_tin(alter_type)
1402 int alter_type; /* COST_xxx */
1403 {
1404     struct obj *tin = context.tin.tin;
1405
1406     if (carried(tin) ? tin->unpaid
1407                      : (costly_spot(tin->ox, tin->oy) && !tin->no_charge)) {
1408         if (tin->quan > 1L) {
1409             tin = context.tin.tin = splitobj(tin, 1L);
1410             context.tin.o_id = tin->o_id;
1411         }
1412         costly_alteration(tin, alter_type);
1413     }
1414     return tin;
1415 }
1416
1417 int
1418 tin_variety_txt(s, tinvariety)
1419 char *s;
1420 int *tinvariety;
1421 {
1422     int k, l;
1423
1424     if (s && tinvariety) {
1425         *tinvariety = -1;
1426         for (k = 0; k < TTSZ - 1; ++k) {
1427             l = (int) strlen(tintxts[k].txt);
1428             if (!strncmpi(s, tintxts[k].txt, l) && ((int) strlen(s) > l)
1429                 && s[l] == ' ') {
1430                 *tinvariety = k;
1431                 return (l + 1);
1432             }
1433         }
1434     }
1435     return 0;
1436 }
1437
1438 /*
1439  * This assumes that buf already contains the word "tin",
1440  * as is the case with caller xname().
1441  */
1442 /*JP:\81u\8aÊ\8bl\81v\82Í\8cã\82Å\95t\82¯\82é */
1443 void
1444 tin_details(obj, mnum, buf)
1445 struct obj *obj;
1446 int mnum;
1447 char *buf;
1448 {
1449 #if 0 /*JP*/
1450     char buf2[BUFSZ];
1451 #endif
1452     int r = tin_variety(obj, TRUE);
1453
1454     if (obj && buf) {
1455         if (r == SPINACH_TIN)
1456 /*JP
1457             Strcat(buf, " of spinach");
1458 */
1459             Strcat(buf, "\83z\83E\83\8c\83\93\91\90\82Ì");
1460         else if (mnum == NON_PM)
1461 /*JP
1462             Strcpy(buf, "empty tin");
1463 */
1464             Strcat(buf, "\8bó\82Á\82Û\82Ì");
1465         else {
1466 #if 0 /*JP*//*\93ú\96{\8cê\82Í\8cã\82Å*/
1467             if ((obj->cknown || iflags.override_ID) && obj->spe < 0) {
1468                 if (r == ROTTEN_TIN || r == HOMEMADE_TIN) {
1469                     /* put these before the word tin */
1470                     Sprintf(buf2, "%s %s of ", tintxts[r].txt, buf);
1471                     Strcpy(buf, buf2);
1472                 } else {
1473                     Sprintf(eos(buf), " of %s ", tintxts[r].txt);
1474                 }
1475                 Sprintf(eos(buf), "%s", tintxts[r].txt);
1476             } else {
1477                 Strcpy(eos(buf), " of ");
1478             }
1479 #endif
1480 #if 1 /*JP*//*\81u\82Ì\81v\82Å\8en\82Ü\82é\82È\82ç\8cã\92u\81A\82»\82ê\88È\8aO\82È\82ç\91O\92u*/
1481             if (strstr(tintxts[r].txt, "\82Ì") != tintxts[r].txt) {
1482                 Strcpy(eos(buf), tintxts[r].txt);
1483             }
1484 #endif
1485             if (vegetarian(&mons[mnum]))
1486 /*JP
1487                 Sprintf(eos(buf), "%s", mons[mnum].mname);
1488 */
1489                 Sprintf(eos(buf), "%s", mons[mnum].mname);
1490             else
1491 /*JP
1492                 Sprintf(eos(buf), "%s meat", mons[mnum].mname);
1493 */
1494                 Sprintf(eos(buf), "%s\82Ì\93÷", mons[mnum].mname);
1495 #if 1 /*JP*//*\81u\82Ì\81v\82Å\8en\82Ü\82é\82È\82ç\8cã\92u\81A\82»\82ê\88È\8aO\82È\82ç\91O\92u*/
1496             if (strstr(tintxts[r].txt, "\82Ì") == tintxts[r].txt) {
1497                 Strcpy(eos(buf), tintxts[r].txt);
1498             }
1499             Strcpy(eos(buf), "\82Ì");
1500 #endif
1501         }
1502     }
1503 }
1504
1505 void
1506 set_tin_variety(obj, forcetype)
1507 struct obj *obj;
1508 int forcetype;
1509 {
1510     register int r;
1511
1512     if (forcetype == SPINACH_TIN
1513         || (forcetype == HEALTHY_TIN
1514             && (obj->corpsenm == NON_PM /* empty or already spinach */
1515                 || !vegetarian(&mons[obj->corpsenm])))) { /* replace meat */
1516         obj->corpsenm = NON_PM; /* not based on any monster */
1517         obj->spe = 1;           /* spinach */
1518         return;
1519     } else if (forcetype == HEALTHY_TIN) {
1520         r = tin_variety(obj, FALSE);
1521         if (r < 0 || r >= TTSZ)
1522             r = ROTTEN_TIN; /* shouldn't happen */
1523         while ((r == ROTTEN_TIN && !obj->cursed) || !tintxts[r].fodder)
1524             r = rn2(TTSZ - 1);
1525     } else if (forcetype >= 0 && forcetype < TTSZ - 1) {
1526         r = forcetype;
1527     } else {               /* RANDOM_TIN */
1528         r = rn2(TTSZ - 1); /* take your pick */
1529         if (r == ROTTEN_TIN && nonrotting_corpse(obj->corpsenm))
1530             r = HOMEMADE_TIN; /* lizards don't rot */
1531     }
1532     obj->spe = -(r + 1); /* offset by 1 to allow index 0 */
1533 }
1534
1535 STATIC_OVL int
1536 tin_variety(obj, disp)
1537 struct obj *obj;
1538 boolean disp; /* we're just displaying so leave things alone */
1539 {
1540     register int r;
1541
1542     if (obj->spe == 1) {
1543         r = SPINACH_TIN;
1544     } else if (obj->cursed) {
1545         r = ROTTEN_TIN; /* always rotten if cursed */
1546     } else if (obj->spe < 0) {
1547         r = -(obj->spe);
1548         --r; /* get rid of the offset */
1549     } else
1550         r = rn2(TTSZ - 1);
1551
1552     if (!disp && r == HOMEMADE_TIN && !obj->blessed && !rn2(7))
1553         r = ROTTEN_TIN; /* some homemade tins go bad */
1554
1555     if (r == ROTTEN_TIN && nonrotting_corpse(obj->corpsenm))
1556         r = HOMEMADE_TIN; /* lizards don't rot */
1557     return r;
1558 }
1559
1560 STATIC_OVL void
1561 consume_tin(mesg)
1562 const char *mesg;
1563 {
1564     const char *what;
1565     int which, mnum, r;
1566     struct obj *tin = context.tin.tin;
1567
1568     r = tin_variety(tin, FALSE);
1569     if (tin->otrapped || (tin->cursed && r != HOMEMADE_TIN && !rn2(8))) {
1570 /*JP
1571         b_trapped("tin", 0);
1572 */
1573         b_trapped("\8aÊ", 0);
1574         tin = costly_tin(COST_DSTROY);
1575         goto use_up_tin;
1576     }
1577
1578     pline1(mesg); /* "You succeed in opening the tin." */
1579
1580     if (r != SPINACH_TIN) {
1581         mnum = tin->corpsenm;
1582         if (mnum == NON_PM) {
1583 /*JP
1584             pline("It turns out to be empty.");
1585 */
1586             pline("\8aÊ\82Í\8bó\82Á\82Û\82¾\82Á\82½\81D");
1587             tin->dknown = tin->known = 1;
1588             tin = costly_tin(COST_OPEN);
1589             goto use_up_tin;
1590         }
1591
1592         which = 0; /* 0=>plural, 1=>as-is, 2=>"the" prefix */
1593         if ((mnum == PM_COCKATRICE || mnum == PM_CHICKATRICE)
1594             && (Stone_resistance || Hallucination)) {
1595 /*JP
1596             what = "chicken";
1597 */
1598             what = "\8c{\93÷";
1599             which = 1; /* suppress pluralization */
1600         } else if (Hallucination) {
1601             what = rndmonnam(NULL);
1602         } else {
1603             what = mons[mnum].mname;
1604             if (the_unique_pm(&mons[mnum]))
1605                 which = 2;
1606             else if (type_is_pname(&mons[mnum]))
1607                 which = 1;
1608         }
1609         if (which == 0)
1610             what = makeplural(what);
1611         else if (which == 2)
1612             what = the(what);
1613
1614 /*JP
1615         pline("It smells like %s.", what);
1616 */
1617         pline("%s\82Ì\82æ\82¤\82È\93õ\82¢\82ª\82µ\82½\81D", what);
1618 /*JP
1619         if (yn("Eat it?") == 'n') {
1620 */
1621         if (yn("\90H\82×\82Ü\82·\82©\81H") == 'n') {
1622             if (flags.verbose)
1623 /*JP
1624                 You("discard the open tin.");
1625 */
1626                 You("\8aJ\82¯\82½\8aÊ\82ð\8eÌ\82Ä\82½\81D");
1627             if (!Hallucination)
1628                 tin->dknown = tin->known = 1;
1629             tin = costly_tin(COST_OPEN);
1630             goto use_up_tin;
1631         }
1632
1633         /* in case stop_occupation() was called on previous meal */
1634         context.victual.piece = (struct obj *) 0;
1635         context.victual.o_id = 0;
1636         context.victual.fullwarn = context.victual.eating =
1637             context.victual.doreset = FALSE;
1638
1639 #if 0 /*JP*/
1640         You("consume %s %s.", tintxts[r].txt, mons[mnum].mname);
1641 #else /*JP: \81u\82Ì\81v\82Å\8en\82Ü\82é\82È\82ç\8cã\92u\81A\82»\82ê\88È\8aO\82È\82ç\91O\92u */
1642         if (strstr(tintxts[r].txt, "\82Ì") == tintxts[r].txt) {
1643             You("%s%s\82Ì\8aÊ\8bl\82ð\82½\82¢\82ç\82°\82½\81D", mons[mnum].mname, tintxts[r].txt);
1644         } else {
1645             You("%s%s\82Ì\8aÊ\8bl\82ð\82½\82¢\82ç\82°\82½\81D", tintxts[r].txt, mons[mnum].mname);
1646         }
1647 #endif
1648
1649         eating_conducts(&mons[mnum]);
1650
1651         tin->dknown = tin->known = 1;
1652         cprefx(mnum);
1653         cpostfx(mnum);
1654
1655         /* charge for one at pre-eating cost */
1656         tin = costly_tin(COST_OPEN);
1657
1658         if (tintxts[r].nut < 0) /* rotten */
1659             make_vomiting((long) rn1(15, 10), FALSE);
1660         else
1661             lesshungry(tintxts[r].nut);
1662
1663         if (tintxts[r].greasy) {
1664             /* Assume !Glib, because you can't open tins when Glib. */
1665             make_glib(rn1(11, 5)); /* 5..15 */
1666 #if 0 /*JP*/
1667             pline("Eating %s food made your %s very slippery.",
1668                   tintxts[r].txt, fingers_or_gloves(TRUE));
1669 #else
1670             pline("\96û\82Á\82Û\82¢\95¨\82ð\90H\82×\82½\82Ì\82Å\82 \82È\82½\82Ì%s\82Í\8a\8a\82è\82â\82·\82­\82È\82Á\82½\81D",
1671                   fingers_or_gloves(TRUE));
1672 #endif
1673         }
1674
1675     } else { /* spinach... */
1676         if (tin->cursed) {
1677 #if 0 /*JP:T*/
1678             pline("It contains some decaying%s%s substance.",
1679                   Blind ? "" : " ", Blind ? "" : hcolor(NH_GREEN));
1680 #else
1681             pline("%s\95\85\82Á\82½\95¨\91Ì\82ª\93ü\82Á\82Ä\82¢\82é\81D",
1682                   Blind ? "" : hcolor(NH_GREEN));
1683 #endif
1684         } else {
1685 /*JP
1686             pline("It contains spinach.");
1687 */
1688             pline("\83z\83E\83\8c\83\93\91\90\82ª\93ü\82Á\82Ä\82¢\82é\81D");
1689             tin->dknown = tin->known = 1;
1690         }
1691
1692 /*JP
1693         if (yn("Eat it?") == 'n') {
1694 */
1695         if (yn("\90H\82×\82Ü\82·\82©\81H") == 'n') {
1696             if (flags.verbose)
1697 /*JP
1698                 You("discard the open tin.");
1699 */
1700                 You("\8aJ\82¯\82½\8aÊ\82ð\8eÌ\82Ä\82½\81D");
1701             tin = costly_tin(COST_OPEN);
1702             goto use_up_tin;
1703         }
1704
1705         /*
1706          * Same order as with non-spinach above:
1707          * conduct update, side-effects, shop handling, and nutrition.
1708          */
1709         u.uconduct.food++; /* don't need vegetarian checks for spinach */
1710         if (!tin->cursed)
1711 #if 0 /*JP:T*/
1712             pline("This makes you feel like %s!",
1713                   /* "Swee'pea" is a character from the Popeye cartoons */
1714                   Hallucination ? "Swee'pea"
1715                   /* "feel like Popeye" unless sustain ability suppresses
1716                      any attribute change; this slightly oversimplifies
1717                      things:  we want "Popeye" if no strength increase
1718                      occurs due to already being at maximum, but we won't
1719                      get it if at-maximum and fixed-abil both apply */
1720                   : !Fixed_abil ? "Popeye"
1721                   /* no gain, feel like another character from Popeye */
1722                   : (flags.female ? "Olive Oyl" : "Bluto"));
1723 #else
1724             pline("%s\82Ì\82æ\82¤\82È\8bC\95ª\82É\82È\82Á\82½\81I",
1725                   /* "Swee'pea" is a character from the Popeye cartoons */
1726                   Hallucination ? "\83X\83C\81[\83s\81["
1727                   /* "feel like Popeye" unless sustain ability suppresses
1728                      any attribute change; this slightly oversimplifies
1729                      things:  we want "Popeye" if no strength increase
1730                      occurs due to already being at maximum, but we won't
1731                      get it if at-maximum and fixed-abil both apply */
1732                   : !Fixed_abil ? "\83|\83p\83C"
1733                   /* no gain, feel like another character from Popeye */
1734                   : (flags.female ? "\83I\83\8a\81[\83u" : "\83u\83\8b\81[\83g"));
1735 #endif
1736         gainstr(tin, 0, FALSE);
1737
1738         tin = costly_tin(COST_OPEN);
1739         lesshungry(tin->blessed ? 600                   /* blessed */
1740                    : !tin->cursed ? (400 + rnd(200))    /* uncursed */
1741                      : (200 + rnd(400)));               /* cursed */
1742     }
1743
1744  use_up_tin:
1745     if (carried(tin))
1746         useup(tin);
1747     else
1748         useupf(tin, 1L);
1749     context.tin.tin = (struct obj *) 0;
1750     context.tin.o_id = 0;
1751 }
1752
1753 /* called during each move whilst opening a tin */
1754 STATIC_PTR int
1755 opentin(VOID_ARGS)
1756 {
1757     /* perhaps it was stolen (although that should cause interruption) */
1758     if (!carried(context.tin.tin)
1759         && (!obj_here(context.tin.tin, u.ux, u.uy) || !can_reach_floor(TRUE)))
1760         return 0; /* %% probably we should use tinoid */
1761     if (context.tin.usedtime++ >= 50) {
1762 /*JP
1763         You("give up your attempt to open the tin.");
1764 */
1765         You("\8aÊ\82ð\8aJ\82¯\82é\82Ì\82ð\82 \82«\82ç\82ß\82½\81D");
1766         return 0;
1767     }
1768     if (context.tin.usedtime < context.tin.reqtime)
1769         return 1; /* still busy */
1770
1771 /*JP
1772     consume_tin("You succeed in opening the tin.");
1773 */
1774     consume_tin("\8aÊ\82ð\8aJ\82¯\82é\82Ì\82É\90¬\8c÷\82µ\82½\81D");
1775     return 0;
1776 }
1777
1778 /* called when starting to open a tin */
1779 STATIC_OVL void
1780 start_tin(otmp)
1781 struct obj *otmp;
1782 {
1783     const char *mesg = 0;
1784     register int tmp;
1785
1786     if (metallivorous(youmonst.data)) {
1787 /*JP
1788         mesg = "You bite right into the metal tin...";
1789 */
1790         mesg = "\8bà\91®\82Ì\8aÊ\82ð\8a\9a\82Ý\82Í\82\82ß\82½\81D\81D\81D";
1791         tmp = 0;
1792     } else if (cantwield(youmonst.data)) { /* nohands || verysmall */
1793 /*JP
1794         You("cannot handle the tin properly to open it.");
1795 */
1796         You("\8aÊ\82ð\82¤\82Ü\82­\8aJ\82¯\82ç\82ê\82È\82¢\81D");
1797         return;
1798     } else if (otmp->blessed) {
1799         /* 50/50 chance for immediate access vs 1 turn delay (unless
1800            wielding blessed tin opener which always yields immediate
1801            access); 1 turn delay case is non-deterministic:  getting
1802            interrupted and retrying might yield another 1 turn delay
1803            or might open immediately on 2nd (or 3rd, 4th, ...) try */
1804         tmp = (uwep && uwep->blessed && uwep->otyp == TIN_OPENER) ? 0 : rn2(2);
1805         if (!tmp)
1806 /*JP
1807             mesg = "The tin opens like magic!";
1808 */
1809             mesg = "\8aÊ\82Í\96\82\96@\82Ì\82æ\82¤\82É\8aJ\82¢\82½\81I";
1810         else
1811 /*JP
1812             pline_The("tin seems easy to open.");
1813 */
1814             pline_The("\8aÊ\82Í\8aÈ\92P\82É\8aJ\82¯\82ç\82ê\82»\82¤\82¾\81D");
1815     } else if (uwep) {
1816         switch (uwep->otyp) {
1817         case TIN_OPENER:
1818 #if 0 /*JP:T*/
1819             mesg = "You easily open the tin."; /* iff tmp==0 */
1820 #else
1821             mesg = "\82 \82È\82½\82Í\8aÈ\92P\82É\8aÊ\82ð\8aJ\82¯\82½\81D"; /* iff tmp==0 */
1822 #endif
1823             tmp = rn2(uwep->cursed ? 3 : !uwep->blessed ? 2 : 1);
1824             break;
1825         case DAGGER:
1826         case SILVER_DAGGER:
1827         case ELVEN_DAGGER:
1828         case ORCISH_DAGGER:
1829         case ATHAME:
1830         case KNIFE:
1831         case STILETTO:
1832         case CRYSKNIFE:
1833             tmp = 3;
1834             break;
1835         case PICK_AXE:
1836         case AXE:
1837             tmp = 6;
1838             break;
1839         default:
1840             goto no_opener;
1841         }
1842 /*JP
1843         pline("Using %s you try to open the tin.", yobjnam(uwep, (char *) 0));
1844 */
1845         You("%s\82ð\8eg\82Á\82Ä\8aÊ\82ð\8aJ\82¯\82æ\82¤\82Æ\82µ\82½\81D", xname(uwep));
1846     } else {
1847  no_opener:
1848 /*JP
1849         pline("It is not so easy to open this tin.");
1850 */
1851         pline("\82±\82Ì\8aÊ\82ð\8aJ\82¯\82é\82Ì\82Í\97e\88Õ\82È\82±\82Æ\82Å\82Í\82È\82¢\81D");
1852         if (Glib) {
1853 /*JP
1854             pline_The("tin slips from your %s.", fingers_or_gloves(FALSE));
1855 */
1856             pline_The("\8aÊ\82Í\82 \82È\82½\82Ì%s\82©\82ç\8a\8a\82è\97\8e\82¿\82½\81D", fingers_or_gloves(FALSE));
1857             if (otmp->quan > 1L) {
1858                 otmp = splitobj(otmp, 1L);
1859             }
1860             if (carried(otmp))
1861                 dropx(otmp);
1862             else
1863                 stackobj(otmp);
1864             return;
1865         }
1866         tmp = rn1(1 + 500 / ((int) (ACURR(A_DEX) + ACURRSTR)), 10);
1867     }
1868
1869     context.tin.tin = otmp;
1870     context.tin.o_id = otmp->o_id;
1871     if (!tmp) {
1872         consume_tin(mesg); /* begin immediately */
1873     } else {
1874         context.tin.reqtime = tmp;
1875         context.tin.usedtime = 0;
1876 /*JP
1877         set_occupation(opentin, "opening the tin", 0);
1878 */
1879         set_occupation(opentin, "\8aÊ\82ð\8aJ\82¯\82é", 0);
1880     }
1881     return;
1882 }
1883
1884 /* called when waking up after fainting */
1885 int
1886 Hear_again(VOID_ARGS)
1887 {
1888     /* Chance of deafness going away while fainted/sleeping/etc. */
1889     if (!rn2(2)) {
1890         make_deaf(0L, FALSE);
1891         context.botl = TRUE;
1892     }
1893     return 0;
1894 }
1895
1896 /* called on the "first bite" of rotten food */
1897 STATIC_OVL int
1898 rottenfood(obj)
1899 struct obj *obj;
1900 {
1901 /*JP
1902     pline("Blecch!  Rotten %s!", foodword(obj));
1903 */
1904     pline("\83Q\83F\81I\95\85\82Á\82½%s\82¾\81I", foodword(obj));
1905     if (!rn2(4)) {
1906         if (Hallucination)
1907 /*JP
1908             You_feel("rather trippy.");
1909 */
1910             You("\82Ö\82ë\82Ö\82ë\82µ\82½\81D");
1911         else
1912 /*JP
1913             You_feel("rather %s.", body_part(LIGHT_HEADED));
1914 */
1915             You("%s\81D", body_part(LIGHT_HEADED));
1916         make_confused(HConfusion + d(2, 4), FALSE);
1917     } else if (!rn2(4) && !Blind) {
1918 /*JP
1919         pline("Everything suddenly goes dark.");
1920 */
1921         pline("\93Ë\91R\91S\82Ä\82ª\88Ã\82­\82È\82Á\82½\81D");
1922         /* hero is not Blind, but Blinded timer might be nonzero if
1923            blindness is being overridden by the Eyes of the Overworld */
1924         make_blinded((Blinded & TIMEOUT) + (long) d(2, 10), FALSE);
1925         if (!Blind)
1926             Your1(vision_clears);
1927     } else if (!rn2(3)) {
1928         const char *what, *where;
1929         int duration = rnd(10);
1930
1931         if (!Blind)
1932 /*JP
1933             what = "goes", where = "dark";
1934 */
1935             what = "\82È\82Á\82½", where = "\88Ã\88Å\82É";
1936         else if (Levitation || Is_airlevel(&u.uz) || Is_waterlevel(&u.uz))
1937 /*JP
1938             what = "you lose control of", where = "yourself";
1939 */
1940             what = "\90§\8cä\82Å\82«\82È\82­\82È\82Á\82½", where = "\8e©\95ª\82ð";
1941         else
1942 /*JP
1943             what = "you slap against the",
1944 */
1945             what = "\82É\82Ô\82Â\82©\82Á\82½",
1946 /*JP
1947             where = (u.usteed) ? "saddle" : surface(u.ux, u.uy);
1948 */
1949             where = (u.usteed) ? "\88Æ" : surface(u.ux, u.uy);
1950 /*JP
1951         pline_The("world spins and %s %s.", what, where);
1952 */
1953         pline("\90¢\8aE\82ª\89ñ\93]\82µ\81C%s%s\81D", where, what);
1954         incr_itimeout(&HDeaf, duration);
1955         context.botl = TRUE;
1956         nomul(-duration);
1957 /*JP
1958         multi_reason = "unconscious from rotten food";
1959 */
1960         multi_reason = "\95\85\82Á\82½\90H\82×\95¨\82Å\88Ó\8e¯\82ð\8e¸\82Á\82Ä\82¢\82é\8aÔ\82É";
1961 /*JP
1962         nomovemsg = "You are conscious again.";
1963 */
1964         nomovemsg = "\82 \82È\82½\82Í\82Ü\82½\90³\8bC\82Ã\82¢\82½\81D";
1965         afternmv = Hear_again;
1966         return 1;
1967     }
1968     return 0;
1969 }
1970
1971 /* called when a corpse is selected as food */
1972 STATIC_OVL int
1973 eatcorpse(otmp)
1974 struct obj *otmp;
1975 {
1976     int retcode = 0, tp = 0, mnum = otmp->corpsenm;
1977     long rotted = 0L;
1978     boolean stoneable = (flesh_petrifies(&mons[mnum]) && !Stone_resistance
1979                          && !poly_when_stoned(youmonst.data)),
1980             slimeable = (mnum == PM_GREEN_SLIME && !Slimed && !Unchanging
1981                          && !slimeproof(youmonst.data)),
1982             glob = otmp->globby ? TRUE : FALSE;
1983
1984     /* KMH, conduct */
1985     if (!vegan(&mons[mnum]))
1986         u.uconduct.unvegan++;
1987     if (!vegetarian(&mons[mnum]))
1988         violated_vegetarian();
1989
1990     if (!nonrotting_corpse(mnum)) {
1991         long age = peek_at_iced_corpse_age(otmp);
1992
1993         rotted = (monstermoves - age) / (10L + rn2(20));
1994         if (otmp->cursed)
1995             rotted += 2L;
1996         else if (otmp->blessed)
1997             rotted -= 2L;
1998     }
1999
2000     if (mnum != PM_ACID_BLOB && !stoneable && !slimeable && rotted > 5L) {
2001         boolean cannibal = maybe_cannibal(mnum, FALSE);
2002
2003 #if 0 /*JP*/
2004         pline("Ulch - that %s was tainted%s!",
2005               (mons[mnum].mlet == S_FUNGUS) ? "fungoid vegetation"
2006                   : glob ? "glob"
2007                       : vegetarian(&mons[mnum]) ? "protoplasm"
2008                           : "meat",
2009               cannibal ? ", you cannibal" : "");
2010 #else /* \93ú\96{\8cê\82Å\82Í\92P\8f\83\82É */
2011         pline("\83I\83F\81I\82±\82ê\82Í\95\85\82Á\82Ä\82¢\82é\81I%s", 
2012               cannibal ? "\82µ\82©\82à\8b¤\90H\82¢\82¾\81I" : "");
2013 #endif
2014         if (Sick_resistance) {
2015 /*JP
2016             pline("It doesn't seem at all sickening, though...");
2017 */
2018             pline("\82µ\82©\82µ\81C\82¢\82½\82Á\82Ä\8c³\8bC\82¾\81D\81D\81D");
2019         } else {
2020             long sick_time;
2021
2022             sick_time = (long) rn1(10, 10);
2023             /* make sure new ill doesn't result in improvement */
2024             if (Sick && (sick_time > Sick))
2025                 sick_time = (Sick > 1L) ? Sick - 1L : 1L;
2026 #if 0 /*JP:T*/
2027             make_sick(sick_time, corpse_xname(otmp, "rotted", CXN_NORMAL),
2028                       TRUE, SICK_VOMITABLE);
2029 #else
2030             make_sick(sick_time, corpse_xname(otmp, "\95\85\82Á\82½", CXN_NORMAL),
2031                       TRUE, SICK_VOMITABLE);
2032 #endif
2033
2034 /*JP
2035             pline("(It must have died too long ago to be safe to eat.)");
2036 */
2037             pline("(\82±\82Ì\93÷\82Í\88À\91S\82É\90H\82×\82ç\82ê\82é\8e\9e\8aÔ\82ð\89ß\82¬\82Ä\82µ\82Ü\82Á\82Ä\82¢\82½\82æ\82¤\82¾\81D)");
2038         }
2039         if (carried(otmp))
2040             useup(otmp);
2041         else
2042             useupf(otmp, 1L);
2043         return 2;
2044     } else if (acidic(&mons[mnum]) && !Acid_resistance) {
2045         tp++;
2046 #if 0 /*JP:T*/
2047         You("have a very bad case of stomach acid.");   /* not body_part() */
2048 #else
2049         pline("\88Ý\8e_\82Ì\92²\8eq\82ª\82Æ\82Ä\82à\88«\82¢\81D");
2050 #endif
2051 #if 0 /*JP:T*/
2052         losehp(rnd(15), !glob ? "acidic corpse" : "acidic glob",
2053                KILLED_BY_AN); /* acid damage */
2054 #else
2055         /* \93ú\96{\8cê\82Å\82Í\8bæ\95Ê\82µ\82È\82¢ */
2056         losehp(rnd(15), "\8e_\82Ì\8e\80\91Ì\82Å", KILLED_BY_AN);
2057 #endif
2058     } else if (poisonous(&mons[mnum]) && rn2(5)) {
2059         tp++;
2060 /*JP
2061         pline("Ecch - that must have been poisonous!");
2062 */
2063         pline("\83E\83Q\83F\81[\81C\97L\93Å\82¾\82Á\82½\82É\82¿\82ª\82¢\82È\82¢\81I");  
2064         if (!Poison_resistance) {
2065             losestr(rnd(4));
2066 #if 0 /*JP:T*/
2067             losehp(rnd(15), !glob ? "poisonous corpse" : "poisonous glob",
2068                    KILLED_BY_AN);
2069 #else
2070             losehp(rnd(15), "\93Å\82Ì\8e\80\91Ì\82Å", KILLED_BY_AN);
2071 #endif
2072         } else
2073 /*JP
2074             You("seem unaffected by the poison.");
2075 */
2076             You("\93Å\82Ì\89e\8b¿\82ð\8eó\82¯\82È\82¢\82æ\82¤\82¾\81D");
2077     /* now any corpse left too long will make you mildly ill */
2078     } else if ((rotted > 5L || (rotted > 3L && rn2(5))) && !Sick_resistance) {
2079         tp++;
2080 /*JP
2081         You_feel("%ssick.", (Sick) ? "very " : "");
2082 */
2083         You("%s\8bC\95ª\82ª\88«\82¢\81D", (Sick) ? "\82Æ\82Ä\82à" : "");
2084 /*JP
2085         losehp(rnd(8), !glob ? "cadaver" : "rotted glob", KILLED_BY_AN);
2086 */
2087         losehp(rnd(8), "\95\85\97\90\8e\80\91Ì\82Å", KILLED_BY_AN);
2088     }
2089
2090     /* delay is weight dependent */
2091     context.victual.reqtime = 3 + ((!glob ? mons[mnum].cwt : otmp->owt) >> 6);
2092
2093     if (!tp && !nonrotting_corpse(mnum) && (otmp->orotten || !rn2(7))) {
2094         if (rottenfood(otmp)) {
2095             otmp->orotten = TRUE;
2096             (void) touchfood(otmp);
2097             retcode = 1;
2098         }
2099
2100         if (!mons[otmp->corpsenm].cnutrit) {
2101             /* no nutrition: rots away, no message if you passed out */
2102             if (!retcode)
2103 /*JP
2104                 pline_The("corpse rots away completely.");
2105 */
2106                 pline("\8e\80\91Ì\82Í\8a®\91S\82É\95\85\82Á\82Ä\82µ\82Ü\82Á\82½\81D");
2107             if (carried(otmp))
2108                 useup(otmp);
2109             else
2110                 useupf(otmp, 1L);
2111             retcode = 2;
2112         }
2113
2114         if (!retcode)
2115             consume_oeaten(otmp, 2); /* oeaten >>= 2 */
2116     } else if ((mnum == PM_COCKATRICE || mnum == PM_CHICKATRICE)
2117                && (Stone_resistance || Hallucination)) {
2118 /*JP
2119         pline("This tastes just like chicken!");
2120 */
2121         pline("\82±\82ê\82Í\8c{\93÷\82Ì\96¡\82¾\81I");
2122     } else if (mnum == PM_FLOATING_EYE && u.umonnum == PM_RAVEN) {
2123 /*JP
2124         You("peck the eyeball with delight.");
2125 */
2126         You("\96Ú\8bÊ\82ð\82Â\82ñ\82Â\82ñ\82Â\82Â\82¢\82½\81D");
2127     } else {
2128         /* yummy is always False for omnivores, palatable always True */
2129         boolean yummy = (vegan(&mons[mnum])
2130                             ? (!carnivorous(youmonst.data)
2131                                && herbivorous(youmonst.data))
2132                             : (carnivorous(youmonst.data)
2133                                && !herbivorous(youmonst.data))),
2134             palatable = ((vegetarian(&mons[mnum])
2135                           ? herbivorous(youmonst.data)
2136                           : carnivorous(youmonst.data))
2137                          && rn2(10)
2138                          && ((rotted < 1) ? TRUE : !rn2(rotted+1)));
2139         const char *pmxnam = food_xname(otmp, FALSE);
2140
2141 #if 0 /*JP*/
2142         if (!strncmpi(pmxnam, "the ", 4))
2143             pmxnam += 4;
2144         pline("%s%s %s %s%c",
2145               type_is_pname(&mons[mnum])
2146                  ? "" : the_unique_pm(&mons[mnum]) ? "The " : "This ",
2147               pmxnam,
2148               Hallucination ? "is" : "tastes",
2149                   /* tiger reference is to TV ads for "Frosted Flakes",
2150                      breakfast cereal targeted at kids by "Tony the tiger" */
2151               Hallucination
2152                  ? (yummy ? ((u.umonnum == PM_TIGER) ? "gr-r-reat" : "gnarly")
2153                           : palatable ? "copacetic" : "grody")
2154                  : (yummy ? "delicious" : palatable ? "okay" : "terrible"),
2155               (yummy || !palatable) ? '!' : '.');
2156 #else
2157         pline("\82±\82Ì%s\82Í%s%s",
2158               pmxnam,
2159               Hallucination
2160                  ? (yummy ? ((u.umonnum == PM_TIGER) ? "\83O\83D\83\8c\83C\83g\83D"
2161                                                      : "\83C\83P\82Ä\82é")
2162                           : palatable ? "\82Ü\82 \82 \82è\82¾" : "\83C\83P\82Ä\82È\82¢")
2163                  : (yummy ? "\82Æ\82Ä\82à\8e|\82¢" : palatable ? "\82Ü\82 \82Ü\82 \82¾"
2164                                                      : "\82Ð\82Ç\82¢\96¡\82¾"),
2165               (yummy || !palatable) ? "\81I" : "\81D");
2166 #endif
2167     }
2168
2169     return retcode;
2170 }
2171
2172 /* called as you start to eat */
2173 STATIC_OVL void
2174 start_eating(otmp, already_partly_eaten)
2175 struct obj *otmp;
2176 boolean already_partly_eaten;
2177 {
2178     const char *old_nomovemsg, *save_nomovemsg;
2179
2180     debugpline2("start_eating: %s (victual = %s)",
2181                 /* note: fmt_ptr() returns a static buffer but supports
2182                    several such so we don't need to copy the first result
2183                    before calling it a second time */
2184                 fmt_ptr((genericptr_t) otmp),
2185                 fmt_ptr((genericptr_t) context.victual.piece));
2186     debugpline1("reqtime = %d", context.victual.reqtime);
2187     debugpline1("(original reqtime = %d)", objects[otmp->otyp].oc_delay);
2188     debugpline1("nmod = %d", context.victual.nmod);
2189     debugpline1("oeaten = %d", otmp->oeaten);
2190     context.victual.fullwarn = context.victual.doreset = FALSE;
2191     context.victual.eating = TRUE;
2192
2193     if (otmp->otyp == CORPSE || otmp->globby) {
2194         cprefx(context.victual.piece->corpsenm);
2195         if (!context.victual.piece || !context.victual.eating) {
2196             /* rider revived, or died and lifesaved */
2197             return;
2198         }
2199     }
2200
2201     old_nomovemsg = nomovemsg;
2202     if (bite()) {
2203         /* survived choking, finish off food that's nearly done;
2204            need this to handle cockatrice eggs, fortune cookies, etc */
2205         if (++context.victual.usedtime >= context.victual.reqtime) {
2206             /* don't want done_eating() to issue nomovemsg if it
2207                is due to vomit() called by bite() */
2208             save_nomovemsg = nomovemsg;
2209             if (!old_nomovemsg)
2210                 nomovemsg = 0;
2211             done_eating(FALSE);
2212             if (!old_nomovemsg)
2213                 nomovemsg = save_nomovemsg;
2214         }
2215         return;
2216     }
2217
2218     if (++context.victual.usedtime >= context.victual.reqtime) {
2219         /* print "finish eating" message if they just resumed -dlc */
2220         done_eating((context.victual.reqtime > 1
2221                      || already_partly_eaten) ? TRUE : FALSE);
2222         return;
2223     }
2224
2225 /*JP
2226     Sprintf(msgbuf, "eating %s", food_xname(otmp, TRUE));
2227 */
2228     Sprintf(msgbuf, "%s\82ð\90H\82×\82é", food_xname(otmp, TRUE));
2229     set_occupation(eatfood, msgbuf, 0);
2230 }
2231
2232 /*
2233  * Called on "first bite" of (non-corpse) food, after touchfood() has
2234  * marked it 'partly eaten'.  Used for non-rotten non-tin non-corpse food.
2235  * Messages should use present tense since multi-turn food won't be
2236  * finishing at the time they're issued.
2237  */
2238 STATIC_OVL void
2239 fprefx(otmp)
2240 struct obj *otmp;
2241 {
2242     switch (otmp->otyp) {
2243     case FOOD_RATION: /* nutrition 800 */
2244         /* 200+800 remains below 1000+1, the satiation threshold */
2245         if (u.uhunger <= 200)
2246 #if 0 /*JP:T*/
2247             pline("%s!", Hallucination ? "Oh wow, like, superior, man"
2248                                        : "This food really hits the spot");
2249 #else
2250             pline("%s\81I", Hallucination ? "\82Ü\82Á\82½\82è\82Æ\82µ\82Ä\81C\82»\82ê\82Å\82¢\82Ä\82µ\82Â\82±\82­\82È\82¢\81I\82±\82ê\82¼\8b\86\8bÉ\82Ì\83\81\83j\83\85\81[\82¾"
2251                                         : "\82±\82Ì\90H\82×\95¨\82Í\96{\93\96\82É\90\\82µ\95ª\82È\82¢");
2252 #endif
2253
2254         /* 700-1+800 remains below 1500, the choking threshold which
2255            triggers "you're having a hard time getting it down" feedback */
2256         else if (u.uhunger < 700)
2257 /*JP
2258             pline("This satiates your %s!", body_part(STOMACH));
2259 */
2260             pline("\96\9e\95 \82É\82È\82Á\82½\81I");
2261         /* [satiation message may be inaccurate if eating gets interrupted] */
2262         break;
2263     case TRIPE_RATION:
2264         if (carnivorous(youmonst.data) && !humanoid(youmonst.data)) {
2265 /*JP
2266             pline("This tripe ration is surprisingly good!");
2267 */
2268             pline("\82±\82Ì\83\82\83c\93÷\82Í\82¨\82Ç\82ë\82­\82Ù\82Ç\8e|\82¢\81I");
2269         } else if (maybe_polyd(is_orc(youmonst.data), Race_if(PM_ORC))) {
2270 /*JP
2271             pline(Hallucination ? "Tastes great!  Less filling!"
2272 */
2273             pline(Hallucination ? "\82¤\82Ü\82¢\81I\82à\82Á\82Æ\82Ù\82µ\82­\82È\82é\82Ë\81I"
2274 /*JP
2275                                 : "Mmm, tripe... not bad!");
2276 */
2277                                 : "\82ñ\81[\81C\83\82\83c\82©\81D\81D\81D\88«\82­\82È\82¢\81I");
2278         } else {
2279 /*JP
2280             pline("Yak - dog food!");
2281 */
2282             pline("\82¤\82°\81C\83h\83b\83O\83t\81[\83h\82¾\81I");
2283             more_experienced(1, 0);
2284             newexplevel();
2285             /* not cannibalism, but we use similar criteria
2286                for deciding whether to be sickened by this meal */
2287             if (rn2(2) && !CANNIBAL_ALLOWED())
2288                 make_vomiting((long) rn1(context.victual.reqtime, 14), FALSE);
2289         }
2290         break;
2291     case LEMBAS_WAFER:
2292         if (maybe_polyd(is_orc(youmonst.data), Race_if(PM_ORC))) {
2293 /*JP
2294             pline("%s", "!#?&* elf kibble!");
2295 */
2296             pline("%s", "\81I\81\94\81H\81\95\81\96 \83G\83\8b\83N\82Ì\90H\82¢\95¨\81I");
2297             break;
2298         } else if (maybe_polyd(is_elf(youmonst.data), Race_if(PM_ELF))) {
2299 /*JP
2300             pline("A little goes a long way.");
2301 */
2302             pline("\8f­\82µ\82Å\8f\\95ª\82¾\81D");
2303             break;
2304         }
2305         goto give_feedback;
2306     case MEATBALL:
2307     case MEAT_STICK:
2308     case HUGE_CHUNK_OF_MEAT:
2309     case MEAT_RING:
2310         goto give_feedback;
2311     case CLOVE_OF_GARLIC:
2312         if (is_undead(youmonst.data)) {
2313             make_vomiting((long) rn1(context.victual.reqtime, 5), FALSE);
2314             break;
2315         }
2316         /*FALLTHRU*/
2317     default:
2318         if (otmp->otyp == SLIME_MOLD && !otmp->cursed
2319             && otmp->spe == context.current_fruit) {
2320 #if 0 /*JP:T*/
2321             pline("My, this is a %s %s!",
2322                   Hallucination ? "primo" : "yummy",
2323                   singular(otmp, xname));
2324 #else
2325             pline("\82¨\82â\81C\82È\82ñ\82Ä%s%s\82¾\81I",
2326                   Hallucination ? "\8fã\95i\82È" : "\82¨\82¢\82µ\82¢",
2327                   singular(otmp, xname));
2328 #endif
2329         } else if (otmp->otyp == APPLE && otmp->cursed && !Sleep_resistance) {
2330             ; /* skip core joke; feedback deferred til fpostfx() */
2331
2332 #if defined(MAC) || defined(MACOSX)
2333         /* KMH -- Why should Unix have all the fun?
2334            We check MACOSX before UNIX to get the Apple-specific apple
2335            message; the '#if UNIX' code will still kick in for pear. */
2336         } else if (otmp->otyp == APPLE) {
2337 /*JP
2338             pline("Delicious!  Must be a Macintosh!");
2339 */
2340             pline("\82·\82Î\82ç\82µ\82¢\81I\83}\83b\83L\83\93\83g\83b\83V\83\85\82É\88á\82¢\82È\82¢\81I");
2341 #endif
2342
2343 #ifdef UNIX
2344         } else if (otmp->otyp == APPLE || otmp->otyp == PEAR) {
2345             if (!Hallucination) {
2346                 pline("Core dumped.");
2347             } else {
2348                 /* based on an old Usenet joke, a fake a.out manual page */
2349                 int x = rnd(100);
2350
2351                 pline("%s -- core dumped.",
2352                       (x <= 75)
2353                          ? "Segmentation fault"
2354                          : (x <= 99)
2355                             ? "Bus error"
2356                             : "Yo' mama");
2357             }
2358 #endif
2359         } else if (otmp->otyp == EGG && stale_egg(otmp)) {
2360 #if 0 /*JP:T*/
2361             pline("Ugh.  Rotten egg."); /* perhaps others like it */
2362 #else
2363             pline("\83E\83Q\83F\81[\95\85\82Á\82½\97\91\82¾\81D");
2364 #endif
2365             /* increasing existing nausea means that it will take longer
2366                before eventual vomit, but also means that constitution
2367                will be abused more times before illness completes */
2368             make_vomiting((Vomiting & TIMEOUT) + (long) d(10, 4), TRUE);
2369         } else {
2370  give_feedback:
2371 #if 0 /*JP:T*/
2372             pline("This %s is %s", singular(otmp, xname),
2373                   otmp->cursed
2374                      ? (Hallucination ? "grody!" : "terrible!")
2375                      : (otmp->otyp == CRAM_RATION
2376                         || otmp->otyp == K_RATION
2377                         || otmp->otyp == C_RATION)
2378                         ? "bland."
2379                         : Hallucination ? "gnarly!" : "delicious!");
2380 #else
2381             pline("\82±\82Ì%s\82Í%s", singular(otmp, xname),
2382                   otmp->cursed
2383                     ? (Hallucination ? "\83C\83P\82Ä\82È\82¢\81I" : "\82Ð\82Ç\82¢\96¡\82¾\81I")
2384                     : (otmp->otyp == CRAM_RATION
2385                         || otmp->otyp == K_RATION
2386                         || otmp->otyp == C_RATION)
2387                         ? "\96¡\8bC\82È\82¢\81D"
2388                         : Hallucination ? "\83C\83P\82Ä\82é\81I" : "\82¤\82Ü\82¢\81I");
2389 #endif
2390         }
2391         break; /* default */
2392     } /* switch */
2393 }
2394
2395 /* increment a combat intrinsic with limits on its growth */
2396 STATIC_OVL int
2397 bounded_increase(old, inc, typ)
2398 int old, inc, typ;
2399 {
2400     int absold, absinc, sgnold, sgninc;
2401
2402     /* don't include any amount coming from worn rings (caller handles
2403        'protection' differently) */
2404     if (uright && uright->otyp == typ && typ != RIN_PROTECTION)
2405         old -= uright->spe;
2406     if (uleft && uleft->otyp == typ && typ != RIN_PROTECTION)
2407         old -= uleft->spe;
2408     absold = abs(old), absinc = abs(inc);
2409     sgnold = sgn(old), sgninc = sgn(inc);
2410
2411     if (absinc == 0 || sgnold != sgninc || absold + absinc < 10) {
2412         ; /* use inc as-is */
2413     } else if (absold + absinc < 20) {
2414         absinc = rnd(absinc); /* 1..n */
2415         if (absold + absinc < 10)
2416             absinc = 10 - absold;
2417         inc = sgninc * absinc;
2418     } else if (absold + absinc < 40) {
2419         absinc = rn2(absinc) ? 1 : 0;
2420         if (absold + absinc < 20)
2421             absinc = rnd(20 - absold);
2422         inc = sgninc * absinc;
2423     } else {
2424         inc = 0; /* no further increase allowed via this method */
2425     }
2426     /* put amount from worn rings back */
2427     if (uright && uright->otyp == typ && typ != RIN_PROTECTION)
2428         old += uright->spe;
2429     if (uleft && uleft->otyp == typ && typ != RIN_PROTECTION)
2430         old += uleft->spe;
2431     return old + inc;
2432 }
2433
2434 STATIC_OVL void
2435 accessory_has_effect(otmp)
2436 struct obj *otmp;
2437 {
2438 #if 0 /*JP:T*/
2439     pline("Magic spreads through your body as you digest the %s.",
2440           (otmp->oclass == RING_CLASS) ? "ring" : "amulet");
2441 #else
2442     pline("\82 \82È\82½\82ª%s\82ð\8fÁ\89»\82·\82é\82Æ\81C\82»\82Ì\96\82\97Í\82ª\91Ì\82É\82µ\82Ý\82±\82ñ\82¾\81D",
2443           otmp->oclass == RING_CLASS ? "\8ew\97Ö" : "\96\82\8f\9c\82¯");
2444 #endif
2445 }
2446
2447 STATIC_OVL void
2448 eataccessory(otmp)
2449 struct obj *otmp;
2450 {
2451     int typ = otmp->otyp;
2452     long oldprop;
2453
2454     /* Note: rings are not so common that this is unbalancing. */
2455     /* (How often do you even _find_ 3 rings of polymorph in a game?) */
2456     oldprop = u.uprops[objects[typ].oc_oprop].intrinsic;
2457     if (otmp == uleft || otmp == uright) {
2458         Ring_gone(otmp);
2459         if (u.uhp <= 0)
2460             return; /* died from sink fall */
2461     }
2462     otmp->known = otmp->dknown = 1; /* by taste */
2463     if (!rn2(otmp->oclass == RING_CLASS ? 3 : 5)) {
2464         switch (otmp->otyp) {
2465         default:
2466             if (!objects[typ].oc_oprop)
2467                 break; /* should never happen */
2468
2469             if (!(u.uprops[objects[typ].oc_oprop].intrinsic & FROMOUTSIDE))
2470                 accessory_has_effect(otmp);
2471
2472             u.uprops[objects[typ].oc_oprop].intrinsic |= FROMOUTSIDE;
2473
2474             switch (typ) {
2475             case RIN_SEE_INVISIBLE:
2476                 set_mimic_blocking();
2477                 see_monsters();
2478                 if (Invis && !oldprop && !ESee_invisible
2479                     && !perceives(youmonst.data) && !Blind) {
2480                     newsym(u.ux, u.uy);
2481 /*JP
2482                     pline("Suddenly you can see yourself.");
2483 */
2484                     pline("\93Ë\91R\8e©\95ª\8e©\90g\82ª\8c©\82¦\82é\82æ\82¤\82É\82È\82Á\82½\81D");
2485                     makeknown(typ);
2486                 }
2487                 break;
2488             case RIN_INVISIBILITY:
2489                 if (!oldprop && !EInvis && !BInvis && !See_invisible
2490                     && !Blind) {
2491                     newsym(u.ux, u.uy);
2492 #if 0 /*JP:T*/
2493                     Your("body takes on a %s transparency...",
2494                          Hallucination ? "normal" : "strange");
2495 #else
2496                     pline("%s\82 \82È\82½\82Ì\91Ì\82Í\93§\89ß\90«\82ð\82à\82Á\82½\81D\81D\81D",
2497                           Hallucination ? "\82 \82½\82è\82Ü\82¦\82È\82±\82Æ\82¾\82ª" : "\8aï\96­\82È\82±\82Æ\82É");
2498 #endif
2499                     makeknown(typ);
2500                 }
2501                 break;
2502             case RIN_PROTECTION_FROM_SHAPE_CHAN:
2503                 rescham();
2504                 break;
2505             case RIN_LEVITATION:
2506                 /* undo the `.intrinsic |= FROMOUTSIDE' done above */
2507                 u.uprops[LEVITATION].intrinsic = oldprop;
2508                 if (!Levitation) {
2509                     float_up();
2510                     incr_itimeout(&HLevitation, d(10, 20));
2511                     makeknown(typ);
2512                 }
2513                 break;
2514             } /* inner switch */
2515             break; /* default case of outer switch */
2516
2517         case RIN_ADORNMENT:
2518             accessory_has_effect(otmp);
2519             if (adjattrib(A_CHA, otmp->spe, -1))
2520                 makeknown(typ);
2521             break;
2522         case RIN_GAIN_STRENGTH:
2523             accessory_has_effect(otmp);
2524             if (adjattrib(A_STR, otmp->spe, -1))
2525                 makeknown(typ);
2526             break;
2527         case RIN_GAIN_CONSTITUTION:
2528             accessory_has_effect(otmp);
2529             if (adjattrib(A_CON, otmp->spe, -1))
2530                 makeknown(typ);
2531             break;
2532         case RIN_INCREASE_ACCURACY:
2533             accessory_has_effect(otmp);
2534             u.uhitinc = (schar) bounded_increase((int) u.uhitinc, otmp->spe,
2535                                                  RIN_INCREASE_ACCURACY);
2536             break;
2537         case RIN_INCREASE_DAMAGE:
2538             accessory_has_effect(otmp);
2539             u.udaminc = (schar) bounded_increase((int) u.udaminc, otmp->spe,
2540                                                  RIN_INCREASE_DAMAGE);
2541             break;
2542         case RIN_PROTECTION:
2543             accessory_has_effect(otmp);
2544             HProtection |= FROMOUTSIDE;
2545             u.ublessed = bounded_increase(u.ublessed, otmp->spe,
2546                                           RIN_PROTECTION);
2547             context.botl = 1;
2548             break;
2549         case RIN_FREE_ACTION:
2550             /* Give sleep resistance instead */
2551             if (!(HSleep_resistance & FROMOUTSIDE))
2552                 accessory_has_effect(otmp);
2553             if (!Sleep_resistance)
2554 /*JP
2555                 You_feel("wide awake.");
2556 */
2557                 You("\82Ï\82Á\82¿\82è\96Ú\82ª\82³\82ß\82½\81D");
2558             HSleep_resistance |= FROMOUTSIDE;
2559             break;
2560         case AMULET_OF_CHANGE:
2561             accessory_has_effect(otmp);
2562             makeknown(typ);
2563             change_sex();
2564 #if 0 /*JP:T*/
2565             You("are suddenly very %s!",
2566                 flags.female ? "feminine" : "masculine");
2567 #else
2568             You("\93Ë\91R\82Æ\82Ä\82à%s\82Á\82Û\82­\82È\82Á\82½\81I", 
2569                 flags.female ? "\8f\97" : "\92j");
2570 #endif
2571             context.botl = 1;
2572             break;
2573         case AMULET_OF_UNCHANGING:
2574             /* un-change: it's a pun */
2575             if (!Unchanging && Upolyd) {
2576                 accessory_has_effect(otmp);
2577                 makeknown(typ);
2578                 rehumanize();
2579             }
2580             break;
2581         case AMULET_OF_STRANGULATION: /* bad idea! */
2582             /* no message--this gives no permanent effect */
2583             choke(otmp);
2584             break;
2585         case AMULET_OF_RESTFUL_SLEEP: { /* another bad idea! */
2586             long newnap = (long) rnd(100), oldnap = (HSleepy & TIMEOUT);
2587
2588             if (!(HSleepy & FROMOUTSIDE))
2589                 accessory_has_effect(otmp);
2590             HSleepy |= FROMOUTSIDE;
2591             /* might also be wearing one; use shorter of two timeouts */
2592             if (newnap < oldnap || oldnap == 0L)
2593                 HSleepy = (HSleepy & ~TIMEOUT) | newnap;
2594             break;
2595         }
2596         case RIN_SUSTAIN_ABILITY:
2597         case AMULET_OF_LIFE_SAVING:
2598         case AMULET_OF_REFLECTION: /* nice try */
2599             /* can't eat Amulet of Yendor or fakes,
2600              * and no oc_prop even if you could -3.
2601              */
2602             break;
2603         }
2604     }
2605 }
2606
2607 /* called after eating non-food */
2608 STATIC_OVL void
2609 eatspecial()
2610 {
2611     struct obj *otmp = context.victual.piece;
2612
2613     /* lesshungry wants an occupation to handle choke messages correctly */
2614 /*JP
2615     set_occupation(eatfood, "eating non-food", 0);
2616 */
2617     set_occupation(eatfood, "\90H\82×\82é", 0);
2618     lesshungry(context.victual.nmod);
2619     occupation = 0;
2620     context.victual.piece = (struct obj *) 0;
2621     context.victual.o_id = 0;
2622     context.victual.eating = 0;
2623     if (otmp->oclass == COIN_CLASS) {
2624         if (carried(otmp))
2625             useupall(otmp);
2626         else
2627             useupf(otmp, otmp->quan);
2628         vault_gd_watching(GD_EATGOLD);
2629         return;
2630     }
2631     if (objects[otmp->otyp].oc_material == PAPER) {
2632 #ifdef MAIL
2633         if (otmp->otyp == SCR_MAIL)
2634             /* no nutrition */
2635 /*JP
2636             pline("This junk mail is less than satisfying.");
2637 */
2638             pline("\82±\82Ì\83S\83~\83\81\81[\83\8b\82Í\96\9e\91«\82É\82Í\82Ù\82Ç\89\93\82¢\81D");
2639         else
2640 #endif
2641         if (otmp->otyp == SCR_SCARE_MONSTER)
2642             /* to eat scroll, hero is currently polymorphed into a monster */
2643 /*JP
2644             pline("Yuck%c", otmp->blessed ? '!' : '.');
2645 */
2646             pline("\82¨\82¦\82Á%s", otmp->blessed ? "\81I" : "\81D");
2647         else if (otmp->oclass == SCROLL_CLASS
2648                  /* check description after checking for specific scrolls */
2649                  && !strcmpi(OBJ_DESCR(objects[otmp->otyp]), "YUM YUM"))
2650 /*JP
2651             pline("Yum%c", otmp->blessed ? '!' : '.');
2652 */
2653             pline("\82¤\82Ü\82¢%s", otmp->blessed ? "\81I" : "\81D");
2654         else
2655 /*JP
2656             pline("Needs salt...");
2657 */
2658             pline("\96¡\82ª\82¤\82·\82¢\81D\81D\81D");
2659     }
2660     if (otmp->oclass == POTION_CLASS) {
2661         otmp->quan++; /* dopotion() does a useup() */
2662         (void) dopotion(otmp);
2663     } else if (otmp->oclass == RING_CLASS || otmp->oclass == AMULET_CLASS) {
2664         eataccessory(otmp);
2665     } else if (otmp->otyp == LEASH && otmp->leashmon) {
2666         o_unleash(otmp);
2667     }
2668
2669     /* KMH -- idea by "Tommy the Terrorist" */
2670     if (otmp->otyp == TRIDENT && !otmp->cursed) {
2671         /* sugarless chewing gum which used to be heavily advertised on TV */
2672 #if 0 /*JP:T*/
2673         pline(Hallucination ? "Four out of five dentists agree."
2674                             : "That was pure chewing satisfaction!");
2675 #else
2676         pline(Hallucination ? "\8cÜ\90l\82É\8el\90l\82Ì\8e\95\88ã\8eÒ\82ª\83g\83\89\83C\83f\83\93\83g\82ð\82¨\91E\82ß\82µ\82Ä\82¢\82Ü\82·\81D"
2677                             : "\8f\83\90\88\82É\8a\9a\82Ý\82½\82¢\8bC\8e\9d\82ð\96\9e\82½\82µ\82½\81I");
2678 #endif
2679         exercise(A_WIS, TRUE);
2680     }
2681     if (otmp->otyp == FLINT && !otmp->cursed) {
2682         /* chewable vitamin for kids based on "The Flintstones" TV cartoon */
2683 /*JP
2684         pline("Yabba-dabba delicious!");
2685 */
2686         pline("\83\84\83b\83o\83_\83b\83o\82¤\82Ü\82¢\81I");
2687         exercise(A_CON, TRUE);
2688     }
2689
2690     if (otmp == uwep && otmp->quan == 1L)
2691         uwepgone();
2692     if (otmp == uquiver && otmp->quan == 1L)
2693         uqwepgone();
2694     if (otmp == uswapwep && otmp->quan == 1L)
2695         uswapwepgone();
2696
2697     if (otmp == uball)
2698         unpunish();
2699     if (otmp == uchain)
2700         unpunish(); /* but no useup() */
2701     else if (carried(otmp))
2702         useup(otmp);
2703     else
2704         useupf(otmp, 1L);
2705 }
2706
2707 /* NOTE: the order of these words exactly corresponds to the
2708    order of oc_material values #define'd in objclass.h. */
2709 static const char *foodwords[] = {
2710 #if 0 /*JP:T*/
2711     "meal",    "liquid",  "wax",       "food", "meat",     "paper",
2712     "cloth",   "leather", "wood",      "bone", "scale",    "metal",
2713     "metal",   "metal",   "silver",    "gold", "platinum", "mithril",
2714     "plastic", "glass",   "rich food", "stone"
2715 #else
2716     "\93÷",           "\89t\91Ì",   "\96û",       "\90H\97¿", "\93÷",       "\8e\86",
2717     "\95\9e",           "\94ç",     "\96Ø",       "\8d\9c",   "\97Ø",       "\8bà\91®",
2718     "\8bà\91®",         "\8bà\91®",   "\8bâ",       "\8bà",   "\83v\83\89\83`\83i", "\83~\83X\83\8a\83\8b",
2719     "\83v\83\89\83X\83`\83b\83N", "\83K\83\89\83X", "\8d\82\8b\89\97¿\97\9d", "\90Î"
2720 #endif
2721 };
2722
2723 STATIC_OVL const char *
2724 foodword(otmp)
2725 struct obj *otmp;
2726 {
2727     if (otmp->oclass == FOOD_CLASS)
2728 /*JP
2729         return "food";
2730 */
2731         return "\90H\97¿";
2732     if (otmp->oclass == GEM_CLASS && objects[otmp->otyp].oc_material == GLASS
2733         && otmp->dknown)
2734         makeknown(otmp->otyp);
2735     return foodwords[objects[otmp->otyp].oc_material];
2736 }
2737
2738 /* called after consuming (non-corpse) food */
2739 STATIC_OVL void
2740 fpostfx(otmp)
2741 struct obj *otmp;
2742 {
2743     switch (otmp->otyp) {
2744     case SPRIG_OF_WOLFSBANE:
2745         if (u.ulycn >= LOW_PM || is_were(youmonst.data))
2746             you_unwere(TRUE);
2747         break;
2748     case CARROT:
2749         if (!u.uswallow
2750             || !attacktype_fordmg(u.ustuck->data, AT_ENGL, AD_BLND))
2751             make_blinded((long) u.ucreamed, TRUE);
2752         break;
2753     case FORTUNE_COOKIE:
2754         outrumor(bcsign(otmp), BY_COOKIE);
2755         if (!Blind)
2756             u.uconduct.literate++;
2757         break;
2758     case LUMP_OF_ROYAL_JELLY:
2759         /* This stuff seems to be VERY healthy! */
2760         gainstr(otmp, 1, TRUE);
2761         if (Upolyd) {
2762             u.mh += otmp->cursed ? -rnd(20) : rnd(20);
2763             if (u.mh > u.mhmax) {
2764                 if (!rn2(17))
2765                     u.mhmax++;
2766                 u.mh = u.mhmax;
2767             } else if (u.mh <= 0) {
2768                 rehumanize();
2769             }
2770         } else {
2771             u.uhp += otmp->cursed ? -rnd(20) : rnd(20);
2772             if (u.uhp > u.uhpmax) {
2773                 if (!rn2(17))
2774                     u.uhpmax++;
2775                 u.uhp = u.uhpmax;
2776             } else if (u.uhp <= 0) {
2777                 killer.format = KILLED_BY_AN;
2778 #if 0 /*JP*/
2779                 Strcpy(killer.name, "rotten lump of royal jelly");
2780                 done(POISONING);
2781 #else
2782                 Strcpy(killer.name, "\95\85\82Á\82½\83\8d\83C\83\84\83\8b\83[\83\8a\81[\82ð\90H\82×\90H\92\86\93Å\82Å");
2783                 done(DIED);
2784 #endif
2785             }
2786         }
2787         if (!otmp->cursed)
2788             heal_legs(0);
2789         break;
2790     case EGG:
2791         if (flesh_petrifies(&mons[otmp->corpsenm])) {
2792             if (!Stone_resistance
2793                 && !(poly_when_stoned(youmonst.data)
2794                      && polymon(PM_STONE_GOLEM))) {
2795                 if (!Stoned) {
2796 /*JP
2797                     Sprintf(killer.name, "%s egg",
2798 */
2799                     Sprintf(killer.name, "%s\82Ì\97\91\82Å",
2800                             mons[otmp->corpsenm].mname);
2801                     make_stoned(5L, (char *) 0, KILLED_BY_AN, killer.name);
2802                 }
2803             }
2804             /* note: no "tastes like chicken" message for eggs */
2805         }
2806         break;
2807     case EUCALYPTUS_LEAF:
2808         if (Sick && !otmp->cursed)
2809             make_sick(0L, (char *) 0, TRUE, SICK_ALL);
2810         if (Vomiting && !otmp->cursed)
2811             make_vomiting(0L, TRUE);
2812         break;
2813     case APPLE:
2814         if (otmp->cursed && !Sleep_resistance) {
2815             /* Snow White; 'poisoned' applies to [a subset of] weapons,
2816                not food, so we substitute cursed; fortunately our hero
2817                won't have to wait for a prince to be rescued/revived */
2818             if (Race_if(PM_DWARF) && Hallucination)
2819 /*JP
2820                 verbalize("Heigh-ho, ho-hum, I think I'll skip work today.");
2821 */
2822                 verbalize("\83n\83C\83z\81[\81C\83n\83C\83z\81[\81C\8d¡\93ú\82Í\8bx\82Ý\81D");
2823             else if (Deaf || !flags.acoustics)
2824 /*JP
2825                 You("fall asleep.");
2826 */
2827                 You("\96°\82è\82É\97\8e\82¿\82½\81D");
2828             else
2829 /*JP
2830                 You_hear("sinister laughter as you fall asleep...");
2831 */
2832                 You_hear("\96°\82è\82É\97\8e\82¿\82é\82Æ\82«\82É\8e×\88«\82È\8fÎ\82¢\90º\82ð\95·\82¢\82½\81D\81D\81D");
2833             fall_asleep(-rn1(11, 20), TRUE);
2834         }
2835         break;
2836     }
2837     return;
2838 }
2839
2840 #if 0
2841 /* intended for eating a spellbook while polymorphed, but not used;
2842    "leather" applied to appearance, not composition, and has been
2843    changed to "leathery" to reflect that */
2844 STATIC_DCL boolean FDECL(leather_cover, (struct obj *));
2845
2846 STATIC_OVL boolean
2847 leather_cover(otmp)
2848 struct obj *otmp;
2849 {
2850     const char *odesc = OBJ_DESCR(objects[otmp->otyp]);
2851
2852     if (odesc && (otmp->oclass == SPBOOK_CLASS)) {
2853         if (!strcmp(odesc, "leather"))
2854             return TRUE;
2855     }
2856     return FALSE;
2857 }
2858 #endif
2859
2860 /*
2861  * return 0 if the food was not dangerous.
2862  * return 1 if the food was dangerous and you chose to stop.
2863  * return 2 if the food was dangerous and you chose to eat it anyway.
2864  */
2865 STATIC_OVL int
2866 edibility_prompts(otmp)
2867 struct obj *otmp;
2868 {
2869     /* Blessed food detection grants hero a one-use
2870      * ability to detect food that is unfit for consumption
2871      * or dangerous and avoid it.
2872      */
2873 #if 0 /*JP*/
2874     char buf[BUFSZ], foodsmell[BUFSZ],
2875          it_or_they[QBUFSZ], eat_it_anyway[QBUFSZ];
2876 #else
2877     char buf[BUFSZ], foodsmell[BUFSZ],
2878          eat_it_anyway[QBUFSZ];
2879 #endif
2880     boolean cadaver = (otmp->otyp == CORPSE || otmp->globby),
2881             stoneorslime = FALSE;
2882     int material = objects[otmp->otyp].oc_material, mnum = otmp->corpsenm;
2883     long rotted = 0L;
2884
2885 #if 0 /*JP*/
2886     Strcpy(foodsmell, Tobjnam(otmp, "smell"));
2887 #else
2888     Strcpy(foodsmell, xname(otmp));
2889 #endif
2890 #if 0 /*JP*/
2891     Strcpy(it_or_they, (otmp->quan == 1L) ? "it" : "they");
2892 #endif
2893 #if 0 /*JP*/
2894     Sprintf(eat_it_anyway, "Eat %s anyway?",
2895             (otmp->quan == 1L) ? "it" : "one");
2896 #else
2897     Strcpy(eat_it_anyway, "\82»\82ê\82Å\82à\90H\82×\82é\81H");
2898 #endif
2899
2900     if (cadaver || otmp->otyp == EGG || otmp->otyp == TIN) {
2901         /* These checks must match those in eatcorpse() */
2902         stoneorslime = (flesh_petrifies(&mons[mnum]) && !Stone_resistance
2903                         && !poly_when_stoned(youmonst.data));
2904
2905         if (mnum == PM_GREEN_SLIME || otmp->otyp == GLOB_OF_GREEN_SLIME)
2906             stoneorslime = (!Unchanging && !slimeproof(youmonst.data));
2907
2908         if (cadaver && !nonrotting_corpse(mnum)) {
2909             long age = peek_at_iced_corpse_age(otmp);
2910
2911             /* worst case rather than random
2912                in this calculation to force prompt */
2913             rotted = (monstermoves - age) / (10L + 0 /* was rn2(20) */);
2914             if (otmp->cursed)
2915                 rotted += 2L;
2916             else if (otmp->blessed)
2917                 rotted -= 2L;
2918         }
2919     }
2920
2921     /*
2922      * These problems with food should be checked in
2923      * order from most detrimental to least detrimental.
2924      */
2925     if (cadaver && mnum != PM_ACID_BLOB && rotted > 5L && !Sick_resistance) {
2926         /* Tainted meat */
2927 #if 0 /*JP:T*/
2928         Sprintf(buf, "%s like %s could be tainted!  %s", foodsmell, it_or_they,
2929                 eat_it_anyway);
2930 #else
2931         Sprintf(buf, "%s\82Í\89\98\90õ\82³\82ê\82Ä\82¢\82é\82æ\82¤\82È\82É\82¨\82¢\82ª\82·\82é\81I%s",
2932                 foodsmell, eat_it_anyway);
2933 #endif
2934         if (yn_function(buf, ynchars, 'n') == 'n')
2935             return 1;
2936         else
2937             return 2;
2938     }
2939     if (stoneorslime) {
2940 #if 0 /*JP:T*/
2941         Sprintf(buf, "%s like %s could be something very dangerous!  %s",
2942                 foodsmell, it_or_they, eat_it_anyway);
2943 #else
2944         Sprintf(buf, "%s\82Í\82È\82ñ\82¾\82©\82·\82²\82­\8aë\8c¯\82»\82¤\82È\82É\82¨\82¢\82ª\82·\82é\81I%s",
2945                 foodsmell, eat_it_anyway);
2946 #endif
2947         if (yn_function(buf, ynchars, 'n') == 'n')
2948             return 1;
2949         else
2950             return 2;
2951     }
2952     if (otmp->orotten || (cadaver && rotted > 3L)) {
2953         /* Rotten */
2954 #if 0 /*JP:T*/
2955         Sprintf(buf, "%s like %s could be rotten! %s",  foodsmell, it_or_they,
2956                 eat_it_anyway);
2957 #else
2958         Sprintf(buf, "%s\82Í\95\85\82Á\82½\82æ\82¤\82È\82É\82¨\82¢\82ª\82·\82é\81I%s", foodsmell,
2959                 eat_it_anyway);
2960 #endif
2961         if (yn_function(buf, ynchars, 'n') == 'n')
2962             return 1;
2963         else
2964             return 2;
2965     }
2966     if (cadaver && poisonous(&mons[mnum]) && !Poison_resistance) {
2967         /* poisonous */
2968 #if 0 /*JP:T*/
2969         Sprintf(buf, "%s like %s might be poisonous!  %s", foodsmell,
2970                 it_or_they, eat_it_anyway);
2971 #else
2972         Sprintf(buf, "%s\82Í\93Å\82ð\82à\82Á\82Ä\82¢\82»\82¤\82È\82É\82¨\82¢\82ª\82·\82é\81I%s", foodsmell,
2973                 eat_it_anyway);
2974 #endif
2975         if (yn_function(buf, ynchars, 'n') == 'n')
2976             return 1;
2977         else
2978             return 2;
2979     }
2980     if (otmp->otyp == APPLE && otmp->cursed && !Sleep_resistance) {
2981         /* causes sleep, for long enough to be dangerous */
2982 #if 0 /*JP:T*/
2983         Sprintf(buf, "%s like %s might have been poisoned.  %s", foodsmell,
2984                 it_or_they, eat_it_anyway);
2985 #else
2986         Sprintf(buf, "%s\82Í\93Å\82ª\93ü\82ê\82ç\82ê\82Ä\82¢\82»\82¤\82È\82É\82¨\82¢\82ª\82·\82é\81I%s", foodsmell,
2987                 eat_it_anyway);
2988 #endif
2989         return (yn_function(buf, ynchars, 'n') == 'n') ? 1 : 2;
2990     }
2991     if (cadaver && !vegetarian(&mons[mnum]) && !u.uconduct.unvegetarian
2992         && Role_if(PM_MONK)) {
2993 /*JP
2994         Sprintf(buf, "%s unhealthy.  %s", foodsmell, eat_it_anyway);
2995 */
2996         Sprintf(buf, "%s\82Í\8c\92\8dN\82É\88«\82»\82¤\82È\82É\82¨\82¢\82ª\82·\82é\81D%s", foodsmell, eat_it_anyway);
2997         if (yn_function(buf, ynchars, 'n') == 'n')
2998             return 1;
2999         else
3000             return 2;
3001     }
3002     if (cadaver && acidic(&mons[mnum]) && !Acid_resistance) {
3003 /*JP
3004         Sprintf(buf, "%s rather acidic.  %s", foodsmell, eat_it_anyway);
3005 */
3006         Sprintf(buf, "%s\82Í\8f­\82µ\8e_\82Á\82Ï\82»\82¤\82È\82É\82¨\82¢\82ª\82·\82é\81D%s", foodsmell, eat_it_anyway);
3007         if (yn_function(buf, ynchars, 'n') == 'n')
3008             return 1;
3009         else
3010             return 2;
3011     }
3012     if (Upolyd && u.umonnum == PM_RUST_MONSTER && is_metallic(otmp)
3013         && otmp->oerodeproof) {
3014 #if 0 /*JP:T*/
3015         Sprintf(buf, "%s disgusting to you right now.  %s", foodsmell,
3016                 eat_it_anyway);
3017 #else
3018         Sprintf(buf, "%s\82Í\8bC\95ª\82ª\88«\82­\82È\82é\82É\82¨\82¢\82ª\82·\82é\81D%s", foodsmell,
3019                 eat_it_anyway);
3020 #endif
3021         if (yn_function(buf, ynchars, 'n') == 'n')
3022             return 1;
3023         else
3024             return 2;
3025     }
3026
3027     /*
3028      * Breaks conduct, but otherwise safe.
3029      */
3030     if (!u.uconduct.unvegan
3031         && ((material == LEATHER || material == BONE
3032              || material == DRAGON_HIDE || material == WAX)
3033             || (cadaver && !vegan(&mons[mnum])))) {
3034 #if 0 /*JP:T*/
3035         Sprintf(buf, "%s foul and unfamiliar to you.  %s", foodsmell,
3036                 eat_it_anyway);
3037 #else
3038         Sprintf(buf, "%s\82Í\89\98\82ê\82Ä\82¢\82Ä\81C\82 \82È\82½\82É\82È\82\82Ü\82È\82¢\82æ\82¤\82È\82É\82¨\82¢\82ª\82·\82é\81D%s", foodsmell,
3039                 eat_it_anyway);
3040 #endif
3041         if (yn_function(buf, ynchars, 'n') == 'n')
3042             return 1;
3043         else
3044             return 2;
3045     }
3046     if (!u.uconduct.unvegetarian
3047         && ((material == LEATHER || material == BONE
3048              || material == DRAGON_HIDE)
3049             || (cadaver && !vegetarian(&mons[mnum])))) {
3050 /*JP
3051         Sprintf(buf, "%s unfamiliar to you.  %s", foodsmell, eat_it_anyway);
3052 */
3053         Sprintf(buf, "%s\82Í\82 \82È\82½\82É\82È\82\82Ü\82È\82¢\82æ\82¤\82È\82É\82¨\82¢\82ª\82·\82é\81D%s", foodsmell, eat_it_anyway);
3054         if (yn_function(buf, ynchars, 'n') == 'n')
3055             return 1;
3056         else
3057             return 2;
3058     }
3059
3060     if (cadaver && mnum != PM_ACID_BLOB && rotted > 5L && Sick_resistance) {
3061         /* Tainted meat with Sick_resistance */
3062 #if 0 /*JP:T*/
3063         Sprintf(buf, "%s like %s could be tainted!  %s",
3064                 foodsmell, it_or_they, eat_it_anyway);
3065 #else
3066         Sprintf(buf, "%s\82Í\89\98\90õ\82³\82ê\82Ä\82¢\82é\82æ\82¤\82È\82É\82¨\82¢\82ª\82·\82é\81I%s",
3067                 foodsmell, eat_it_anyway);
3068 #endif
3069         if (yn_function(buf, ynchars, 'n') == 'n')
3070             return 1;
3071         else
3072             return 2;
3073     }
3074     return 0;
3075 }
3076
3077 /* 'e' command */
3078 int
3079 doeat()
3080 {
3081     struct obj *otmp;
3082     int basenutrit; /* nutrition of full item */
3083     boolean dont_start = FALSE, nodelicious = FALSE,
3084             already_partly_eaten;
3085
3086     if (Strangled) {
3087 /*JP
3088         pline("If you can't breathe air, how can you consume solids?");
3089 */
3090         pline("\91§\82à\82Å\82«\82È\82¢\82Ì\82É\81C\82Ç\82¤\82â\82Á\82Ä\90H\82×\82½\82ç\82¢\82¢\82ñ\82¾\82¢\81H");
3091         return 0;
3092     }
3093     if (!(otmp = floorfood("eat", 0)))
3094         return 0;
3095     if (check_capacity((char *) 0))
3096         return 0;
3097
3098     if (u.uedibility) {
3099         int res = edibility_prompts(otmp);
3100
3101         if (res) {
3102 #if 0 /*JP*/
3103             Your(
3104                "%s stops tingling and your sense of smell returns to normal.",
3105                  body_part(NOSE));
3106 #else
3107             Your("%s\82ª\82¤\82¸\82¤\82¸\82·\82é\82Ì\82Í\8e~\82Ü\82è\81C\9ak\8ao\82Í\95\81\92Ê\82É\96ß\82Á\82½\81D",
3108                  body_part(NOSE));
3109 #endif
3110             u.uedibility = 0;
3111             if (res == 1)
3112                 return 0;
3113         }
3114     }
3115
3116     /* We have to make non-foods take 1 move to eat, unless we want to
3117      * do ridiculous amounts of coding to deal with partly eaten plate
3118      * mails, players who polymorph back to human in the middle of their
3119      * metallic meal, etc....
3120      */
3121     if (!is_edible(otmp)) {
3122 /*JP
3123         You("cannot eat that!");
3124 */
3125         You("\82»\82ê\82ð\90H\82×\82ç\82ê\82È\82¢\81I");
3126         return 0;
3127     } else if ((otmp->owornmask & (W_ARMOR | W_TOOL | W_AMUL | W_SADDLE))
3128                != 0) {
3129         /* let them eat rings */
3130 /*JP
3131         You_cant("eat %s you're wearing.", something);
3132 */
3133         You("\90g\82É\82Â\82¯\82Ä\82¢\82é\8aÔ\82Í\90H\82×\82ê\82È\82¢\81D");
3134         return 0;
3135     } else if (!(carried(otmp) ? retouch_object(&otmp, FALSE)
3136                                : touch_artifact(otmp, &youmonst))) {
3137         return 1; /* got blasted so use a turn */
3138     }
3139     if (is_metallic(otmp) && u.umonnum == PM_RUST_MONSTER
3140         && otmp->oerodeproof) {
3141         otmp->rknown = TRUE;
3142         if (otmp->quan > 1L) {
3143             if (!carried(otmp))
3144                 (void) splitobj(otmp, otmp->quan - 1L);
3145             else
3146                 otmp = splitobj(otmp, 1L);
3147         }
3148 /*JP
3149         pline("Ulch - that %s was rustproofed!", xname(otmp));
3150 */
3151         pline("\83E\83Q\83F\81[\81I%s\82Í\96h\8eK\82³\82ê\82Ä\82¢\82é\81I", xname(otmp));
3152         /* The regurgitated object's rustproofing is gone now */
3153         otmp->oerodeproof = 0;
3154         make_stunned((HStun & TIMEOUT) + (long) rn2(10), TRUE);
3155         /*
3156          * We don't expect rust monsters to be wielding welded weapons
3157          * or wearing cursed rings which were rustproofed, but guard
3158          * against the possibility just in case.
3159          */
3160         if (welded(otmp) || (otmp->cursed && (otmp->owornmask & W_RING))) {
3161             set_bknown(otmp, 1); /* for ring; welded() does this for weapon */
3162 /*JP
3163             You("spit out %s.", the(xname(otmp)));
3164 */
3165             You("%s\82ð\93f\82«\8fo\82µ\82½\81D", xname(otmp));
3166         } else {
3167 #if 0 /*JP:T*/
3168             You("spit %s out onto the %s.", the(xname(otmp)),
3169                 surface(u.ux, u.uy));
3170 #else
3171             You("%s\82ð%s\82É\93f\82«\8fo\82µ\82½\81D", the(xname(otmp)),
3172                 surface(u.ux, u.uy));
3173 #endif
3174             if (carried(otmp)) {
3175                 /* no need to check for leash in use; it's not metallic */
3176                 if (otmp->owornmask)
3177                     remove_worn_item(otmp, FALSE);
3178                 freeinv(otmp);
3179                 dropy(otmp);
3180             }
3181             stackobj(otmp);
3182         }
3183         return 1;
3184     }
3185     /* KMH -- Slow digestion is... indigestible */
3186     if (otmp->otyp == RIN_SLOW_DIGESTION) {
3187 /*JP
3188         pline("This ring is indigestible!");
3189 */
3190         pline("\82±\82Ì\8ew\97Ö\82Í\8fÁ\89»\82µ\82É\82­\82¢\81I");
3191         (void) rottenfood(otmp);
3192         if (otmp->dknown && !objects[otmp->otyp].oc_name_known
3193             && !objects[otmp->otyp].oc_uname)
3194             docall(otmp);
3195         return 1;
3196     }
3197     if (otmp->oclass != FOOD_CLASS) {
3198         int material;
3199
3200         context.victual.reqtime = 1;
3201         context.victual.piece = otmp;
3202         context.victual.o_id = otmp->o_id;
3203         /* Don't split it, we don't need to if it's 1 move */
3204         context.victual.usedtime = 0;
3205         context.victual.canchoke = (u.uhs == SATIATED);
3206         /* Note: gold weighs 1 pt. for each 1000 pieces (see
3207            pickup.c) so gold and non-gold is consistent. */
3208         if (otmp->oclass == COIN_CLASS)
3209             basenutrit = ((otmp->quan > 200000L)
3210                              ? 2000
3211                              : (int) (otmp->quan / 100L));
3212         else if (otmp->oclass == BALL_CLASS || otmp->oclass == CHAIN_CLASS)
3213             basenutrit = weight(otmp);
3214         /* oc_nutrition is usually weight anyway */
3215         else
3216             basenutrit = objects[otmp->otyp].oc_nutrition;
3217 #ifdef MAIL
3218         if (otmp->otyp == SCR_MAIL) {
3219             basenutrit = 0;
3220             nodelicious = TRUE;
3221         }
3222 #endif
3223         context.victual.nmod = basenutrit;
3224         context.victual.eating = TRUE; /* needed for lesshungry() */
3225
3226         material = objects[otmp->otyp].oc_material;
3227         if (material == LEATHER || material == BONE
3228             || material == DRAGON_HIDE) {
3229             u.uconduct.unvegan++;
3230             violated_vegetarian();
3231         } else if (material == WAX)
3232             u.uconduct.unvegan++;
3233         u.uconduct.food++;
3234
3235         if (otmp->cursed) {
3236             (void) rottenfood(otmp);
3237             nodelicious = TRUE;
3238         } else if (objects[otmp->otyp].oc_material == PAPER)
3239             nodelicious = TRUE;
3240
3241         if (otmp->oclass == WEAPON_CLASS && otmp->opoisoned) {
3242 /*JP
3243             pline("Ecch - that must have been poisonous!");
3244 */
3245             pline("\83E\83Q\83F\81[\81C\97L\93Å\82¾\82Á\82½\82É\88á\82¢\82È\82¢\81I");  
3246             if (!Poison_resistance) {
3247                 losestr(rnd(4));
3248 #if 0 /*JP*/
3249                 losehp(rnd(15), xname(otmp), KILLED_BY_AN);
3250 #else
3251                 {
3252                     char jbuf[BUFSZ];
3253                     Sprintf(jbuf, "%s\82Å", xname(otmp));
3254                     losehp(rnd(15), jbuf, KILLED_BY_AN);
3255                 }
3256 #endif
3257             } else
3258 /*JP
3259                 You("seem unaffected by the poison.");
3260 */
3261                 You("\93Å\82Ì\89e\8b¿\82ð\8eó\82¯\82È\82¢\82æ\82¤\82¾\81D");
3262         } else if (!nodelicious) {
3263 #if 0 /*JP*/
3264             pline("%s%s is delicious!",
3265                   (obj_is_pname(otmp)
3266                    && otmp->oartifact < ART_ORB_OF_DETECTION)
3267                       ? ""
3268                       : "This ",
3269                   (otmp->oclass == COIN_CLASS)
3270                       ? foodword(otmp)
3271                       : singular(otmp, xname));
3272 #else
3273             pline("%s%s\82Í\8e|\82¢\81I",
3274                   (obj_is_pname(otmp)
3275                    && otmp->oartifact < ART_ORB_OF_DETECTION)
3276                       ? ""
3277                       : "\82±\82Ì",
3278                   (otmp->oclass == COIN_CLASS)
3279                       ? foodword(otmp)
3280                       : singular(otmp, xname));
3281 #endif
3282         }
3283         eatspecial();
3284         return 1;
3285     }
3286
3287     if (otmp == context.victual.piece) {
3288         /* If they weren't able to choke, they don't suddenly become able to
3289          * choke just because they were interrupted.  On the other hand, if
3290          * they were able to choke before, if they lost food it's possible
3291          * they shouldn't be able to choke now.
3292          */
3293         if (u.uhs != SATIATED)
3294             context.victual.canchoke = FALSE;
3295         context.victual.o_id = 0;
3296         context.victual.piece = touchfood(otmp);
3297         if (context.victual.piece)
3298             context.victual.o_id = context.victual.piece->o_id;
3299 #if 0 /*JP:T*/
3300         You("resume %syour meal.",
3301             (context.victual.usedtime + 1 >= context.victual.reqtime)
3302             ? "the last bite of " : "");
3303 #else
3304         You("\90H\8e\96%s\82ð\8dÄ\8aJ\82µ\82½\81D",
3305             (context.victual.usedtime + 1 >= context.victual.reqtime)
3306             ? "\82Ì\8dÅ\8cã\82Ì\88ê\8cû" : "");
3307 #endif
3308         start_eating(context.victual.piece, FALSE);
3309         return 1;
3310     }
3311
3312     /* nothing in progress - so try to find something. */
3313     /* tins are a special case */
3314     /* tins must also check conduct separately in case they're discarded */
3315     if (otmp->otyp == TIN) {
3316         start_tin(otmp);
3317         return 1;
3318     }
3319
3320     /* KMH, conduct */
3321     u.uconduct.food++;
3322
3323     already_partly_eaten = otmp->oeaten ? TRUE : FALSE;
3324     context.victual.o_id = 0;
3325     context.victual.piece = otmp = touchfood(otmp);
3326     if (context.victual.piece)
3327         context.victual.o_id = context.victual.piece->o_id;
3328     context.victual.usedtime = 0;
3329
3330     /* Now we need to calculate delay and nutritional info.
3331      * The base nutrition calculated here and in eatcorpse() accounts
3332      * for normal vs. rotten food.  The reqtime and nutrit values are
3333      * then adjusted in accordance with the amount of food left.
3334      */
3335     if (otmp->otyp == CORPSE || otmp->globby) {
3336         int tmp = eatcorpse(otmp);
3337
3338         if (tmp == 2) {
3339             /* used up */
3340             context.victual.piece = (struct obj *) 0;
3341             context.victual.o_id = 0;
3342             return 1;
3343         } else if (tmp)
3344             dont_start = TRUE;
3345         /* if not used up, eatcorpse sets up reqtime and may modify oeaten */
3346     } else {
3347         /* No checks for WAX, LEATHER, BONE, DRAGON_HIDE.  These are
3348          * all handled in the != FOOD_CLASS case, above.
3349          */
3350         switch (objects[otmp->otyp].oc_material) {
3351         case FLESH:
3352             u.uconduct.unvegan++;
3353             if (otmp->otyp != EGG) {
3354                 violated_vegetarian();
3355             }
3356             break;
3357
3358         default:
3359             if (otmp->otyp == PANCAKE || otmp->otyp == FORTUNE_COOKIE /*eggs*/
3360                 || otmp->otyp == CREAM_PIE || otmp->otyp == CANDY_BAR /*milk*/
3361                 || otmp->otyp == LUMP_OF_ROYAL_JELLY)
3362                 u.uconduct.unvegan++;
3363             break;
3364         }
3365
3366         context.victual.reqtime = objects[otmp->otyp].oc_delay;
3367         if (otmp->otyp != FORTUNE_COOKIE
3368             && (otmp->cursed || (!nonrotting_food(otmp->otyp)
3369                                  && (monstermoves - otmp->age)
3370                                         > (otmp->blessed ? 50L : 30L)
3371                                  && (otmp->orotten || !rn2(7))))) {
3372             if (rottenfood(otmp)) {
3373                 otmp->orotten = TRUE;
3374                 dont_start = TRUE;
3375             }
3376             consume_oeaten(otmp, 1); /* oeaten >>= 1 */
3377         } else if (!already_partly_eaten) {
3378             fprefx(otmp);
3379         } else {
3380 #if 0 /*JP:T*/
3381             You("%s %s.",
3382                 (context.victual.reqtime == 1) ? "eat" : "begin eating",
3383                 doname(otmp));
3384 #else
3385             You("%s\82ð\90H\82×%s\82½\81D",
3386                 doname(otmp),
3387                 (context.victual.reqtime == 1) ? "" : "\82Í\82\82ß");
3388 #endif
3389         }
3390     }
3391
3392     /* re-calc the nutrition */
3393     basenutrit = (int) obj_nutrition(otmp);
3394
3395     debugpline3(
3396      "before rounddiv: victual.reqtime == %d, oeaten == %d, basenutrit == %d",
3397                 context.victual.reqtime, otmp->oeaten, basenutrit);
3398
3399     context.victual.reqtime = (basenutrit == 0) ? 0
3400         : rounddiv(context.victual.reqtime * (long) otmp->oeaten, basenutrit);
3401
3402     debugpline1("after rounddiv: victual.reqtime == %d",
3403                 context.victual.reqtime);
3404     /*
3405      * calculate the modulo value (nutrit. units per round eating)
3406      * note: this isn't exact - you actually lose a little nutrition due
3407      *       to this method.
3408      * TODO: add in a "remainder" value to be given at the end of the meal.
3409      */
3410     if (context.victual.reqtime == 0 || otmp->oeaten == 0)
3411         /* possible if most has been eaten before */
3412         context.victual.nmod = 0;
3413     else if ((int) otmp->oeaten >= context.victual.reqtime)
3414         context.victual.nmod = -((int) otmp->oeaten
3415                                  / context.victual.reqtime);
3416     else
3417         context.victual.nmod = context.victual.reqtime % otmp->oeaten;
3418     context.victual.canchoke = (u.uhs == SATIATED);
3419
3420     if (!dont_start)
3421         start_eating(otmp, already_partly_eaten);
3422     return 1;
3423 }
3424
3425 int
3426 use_tin_opener(obj)
3427 struct obj *obj;
3428 {
3429     struct obj *otmp;
3430     int res = 0;
3431
3432     if (!carrying(TIN)) {
3433 /*JP
3434         You("have no tin to open.");
3435 */
3436         You("\8aÊ\82ð\8e\9d\82Á\82Ä\82¢\82È\82¢\81D");
3437         return 0;
3438     }
3439
3440     if (obj != uwep) {
3441         if (obj->cursed && obj->bknown) {
3442             char qbuf[QBUFSZ];
3443
3444 #if 0 /*JP:T*/
3445             if (ynq(safe_qbuf(qbuf, "Really wield ", "?",
3446                               obj, doname, thesimpleoname, "that")) != 'y')
3447 #else
3448             if (ynq(safe_qbuf(qbuf, "\96{\93\96\82É", "\82ð\91\95\94õ\82·\82é\81H",
3449                               obj, doname, thesimpleoname, "\82»\82ê")) != 'y')
3450 #endif
3451                 return 0;
3452         }
3453         if (!wield_tool(obj, "use"))
3454             return 0;
3455         res = 1;
3456     }
3457
3458     otmp = getobj(comestibles, "open");
3459     if (!otmp)
3460         return res;
3461
3462     start_tin(otmp);
3463     return 1;
3464 }
3465
3466 /* Take a single bite from a piece of food, checking for choking and
3467  * modifying usedtime.  Returns 1 if they choked and survived, 0 otherwise.
3468  */
3469 STATIC_OVL int
3470 bite()
3471 {
3472     if (context.victual.canchoke && u.uhunger >= 2000) {
3473         choke(context.victual.piece);
3474         return 1;
3475     }
3476     if (context.victual.doreset) {
3477         do_reset_eat();
3478         return 0;
3479     }
3480     force_save_hs = TRUE;
3481     if (context.victual.nmod < 0) {
3482         lesshungry(-context.victual.nmod);
3483         consume_oeaten(context.victual.piece,
3484                        context.victual.nmod); /* -= -nmod */
3485     } else if (context.victual.nmod > 0
3486                && (context.victual.usedtime % context.victual.nmod)) {
3487         lesshungry(1);
3488         consume_oeaten(context.victual.piece, -1); /* -= 1 */
3489     }
3490     force_save_hs = FALSE;
3491     recalc_wt();
3492     return 0;
3493 }
3494
3495 /* as time goes by - called by moveloop(every move) & domove(melee attack) */
3496 void
3497 gethungry()
3498 {
3499     if (u.uinvulnerable)
3500         return; /* you don't feel hungrier */
3501
3502     /* being polymorphed into a creature which doesn't eat prevents
3503        this first uhunger decrement, but to stay in such form the hero
3504        will need to wear an Amulet of Unchanging so still burn a small
3505        amount of nutrition in the 'moves % 20' ring/amulet check below */
3506     if ((!Unaware || !rn2(10)) /* slow metabolic rate while asleep */
3507         && (carnivorous(youmonst.data)
3508             || herbivorous(youmonst.data)
3509             || metallivorous(youmonst.data))
3510         && !Slow_digestion)
3511         u.uhunger--; /* ordinary food consumption */
3512
3513     if (moves % 2) { /* odd turns */
3514         /* Regeneration uses up food, unless due to an artifact */
3515         if ((HRegeneration & ~FROMFORM)
3516             || (ERegeneration & ~(W_ARTI | W_WEP)))
3517             u.uhunger--;
3518         if (near_capacity() > SLT_ENCUMBER)
3519             u.uhunger--;
3520     } else { /* even turns */
3521         if (Hunger)
3522             u.uhunger--;
3523         /* Conflict uses up food too */
3524         if (HConflict || (EConflict & (~W_ARTI)))
3525             u.uhunger--;
3526         /* +0 charged rings don't do anything, so don't affect hunger.
3527            Slow digestion cancels move hunger but still causes ring hunger. */
3528         switch ((int) (moves % 20)) { /* note: use even cases only */
3529         case 4:
3530             if (uleft && (uleft->spe || !objects[uleft->otyp].oc_charged))
3531                 u.uhunger--;
3532             break;
3533         case 8:
3534             if (uamul)
3535                 u.uhunger--;
3536             break;
3537         case 12:
3538             if (uright && (uright->spe || !objects[uright->otyp].oc_charged))
3539                 u.uhunger--;
3540             break;
3541         case 16:
3542             if (u.uhave.amulet)
3543                 u.uhunger--;
3544             break;
3545         default:
3546             break;
3547         }
3548     }
3549     newuhs(TRUE);
3550 }
3551
3552 /* called after vomiting and after performing feats of magic */
3553 void
3554 morehungry(num)
3555 int num;
3556 {
3557     u.uhunger -= num;
3558     newuhs(TRUE);
3559 }
3560
3561 /* called after eating (and after drinking fruit juice) */
3562 void
3563 lesshungry(num)
3564 int num;
3565 {
3566     /* See comments in newuhs() for discussion on force_save_hs */
3567     boolean iseating = (occupation == eatfood) || force_save_hs;
3568
3569     debugpline1("lesshungry(%d)", num);
3570     u.uhunger += num;
3571     if (u.uhunger >= 2000) {
3572         if (!iseating || context.victual.canchoke) {
3573             if (iseating) {
3574                 choke(context.victual.piece);
3575                 reset_eat();
3576             } else
3577                 choke(occupation == opentin ? context.tin.tin
3578                                             : (struct obj *) 0);
3579             /* no reset_eat() */
3580         }
3581     } else {
3582         /* Have lesshungry() report when you're nearly full so all eating
3583          * warns when you're about to choke.
3584          */
3585         if (u.uhunger >= 1500
3586             && (!context.victual.eating
3587                 || (context.victual.eating && !context.victual.fullwarn))) {
3588 /*JP
3589             pline("You're having a hard time getting all of it down.");
3590 */
3591             pline("\91S\82Ä\82ð\88ù\82Ý\82±\82Þ\82É\82Í\8e\9e\8aÔ\82ª\82©\82©\82é\81D");
3592 /*JP
3593             nomovemsg = "You're finally finished.";
3594 */
3595             nomovemsg = "\82â\82Á\82Æ\90H\82×\8fI\82¦\82½\81D";
3596             if (!context.victual.eating) {
3597                 multi = -2;
3598             } else {
3599                 context.victual.fullwarn = TRUE;
3600                 if (context.victual.canchoke && context.victual.reqtime > 1) {
3601                     /* a one-gulp food will not survive a stop */
3602 /*JP
3603                     if (!paranoid_query(ParanoidEating, "Continue eating?")) {
3604 */
3605                     if (!paranoid_query(ParanoidEating, "\90H\82×\91±\82¯\82Ü\82·\82©\81H")) {
3606                         reset_eat();
3607                         nomovemsg = (char *) 0;
3608                     }
3609                 }
3610             }
3611         }
3612     }
3613     newuhs(FALSE);
3614 }
3615
3616 STATIC_PTR
3617 int
3618 unfaint(VOID_ARGS)
3619 {
3620     (void) Hear_again();
3621     if (u.uhs > FAINTING)
3622         u.uhs = FAINTING;
3623     stop_occupation();
3624     context.botl = 1;
3625     return 0;
3626 }
3627
3628 boolean
3629 is_fainted()
3630 {
3631     return (boolean) (u.uhs == FAINTED);
3632 }
3633
3634 /* call when a faint must be prematurely terminated */
3635 void
3636 reset_faint()
3637 {
3638     if (afternmv == unfaint)
3639 /*JP
3640         unmul("You revive.");
3641 */
3642         unmul("\82 \82È\82½\82Í\8bC\82ª\82Â\82¢\82½\81D");
3643 }
3644
3645 /* compute and comment on your (new?) hunger status */
3646 void
3647 newuhs(incr)
3648 boolean incr;
3649 {
3650     unsigned newhs;
3651     static unsigned save_hs;
3652     static boolean saved_hs = FALSE;
3653     int h = u.uhunger;
3654
3655     newhs = (h > 1000)
3656                 ? SATIATED
3657                 : (h > 150) ? NOT_HUNGRY
3658                             : (h > 50) ? HUNGRY : (h > 0) ? WEAK : FAINTING;
3659
3660     /* While you're eating, you may pass from WEAK to HUNGRY to NOT_HUNGRY.
3661      * This should not produce the message "you only feel hungry now";
3662      * that message should only appear if HUNGRY is an endpoint.  Therefore
3663      * we check to see if we're in the middle of eating.  If so, we save
3664      * the first hunger status, and at the end of eating we decide what
3665      * message to print based on the _entire_ meal, not on each little bit.
3666      */
3667     /* It is normally possible to check if you are in the middle of a meal
3668      * by checking occupation == eatfood, but there is one special case:
3669      * start_eating() can call bite() for your first bite before it
3670      * sets the occupation.
3671      * Anyone who wants to get that case to work _without_ an ugly static
3672      * force_save_hs variable, feel free.
3673      */
3674     /* Note: If you become a certain hunger status in the middle of the
3675      * meal, and still have that same status at the end of the meal,
3676      * this will incorrectly print the associated message at the end of
3677      * the meal instead of the middle.  Such a case is currently
3678      * impossible, but could become possible if a message for SATIATED
3679      * were added or if HUNGRY and WEAK were separated by a big enough
3680      * gap to fit two bites.
3681      */
3682     if (occupation == eatfood || force_save_hs) {
3683         if (!saved_hs) {
3684             save_hs = u.uhs;
3685             saved_hs = TRUE;
3686         }
3687         u.uhs = newhs;
3688         return;
3689     } else {
3690         if (saved_hs) {
3691             u.uhs = save_hs;
3692             saved_hs = FALSE;
3693         }
3694     }
3695
3696     if (newhs == FAINTING) {
3697         /* u,uhunger is likely to be negative at this point */
3698         int uhunger_div_by_10 = sgn(u.uhunger) * ((abs(u.uhunger) + 5) / 10);
3699
3700         if (is_fainted())
3701             newhs = FAINTED;
3702         if (u.uhs <= WEAK || rn2(20 - uhunger_div_by_10) >= 19) {
3703             if (!is_fainted() && multi >= 0 /* %% */) {
3704                 int duration = 10 - uhunger_div_by_10;
3705
3706                 /* stop what you're doing, then faint */
3707                 stop_occupation();
3708 /*JP
3709                 You("faint from lack of food.");
3710 */
3711                 You("\95 \82ª\8c¸\82Á\82Ä\93|\82ê\82½\81D");
3712                 incr_itimeout(&HDeaf, duration);
3713                 context.botl = TRUE;
3714                 nomul(-duration);
3715 /*JP
3716                 multi_reason = "fainted from lack of food";
3717 */
3718                 multi_reason = "\8bó\95 \82Å\91²\93|\82µ\82Ä\82¢\82é\8aÔ\82É";
3719 /*JP
3720                 nomovemsg = "You regain consciousness.";
3721 */
3722                 nomovemsg = "\82 \82È\82½\82Í\90³\8bC\82Ã\82¢\82½\81D";
3723                 afternmv = unfaint;
3724                 newhs = FAINTED;
3725                 if (!Levitation)
3726 /*JP
3727                     selftouch("Falling, you");
3728 */
3729                     selftouch("\97\8e\82¿\82È\82ª\82ç\81C\82 \82È\82½\82Í");
3730             }
3731
3732         /* this used to be -(200 + 20 * Con) but that was when being asleep
3733            suppressed per-turn uhunger decrement but being fainted didn't;
3734            now uhunger becomes more negative at a slower rate */
3735         } else if (u.uhunger < -(100 + 10 * (int) ACURR(A_CON))) {
3736             u.uhs = STARVED;
3737             context.botl = 1;
3738             bot();
3739 /*JP
3740             You("die from starvation.");
3741 */
3742             You("\89ì\8e\80\82µ\82½\81D");
3743             killer.format = KILLED_BY;
3744 /*JP
3745             Strcpy(killer.name, "starvation");
3746 */
3747             Strcpy(killer.name, "\90H\97¿\95s\91«\82Å\89ì\8e\80\82µ\82½");
3748             done(STARVING);
3749             /* if we return, we lifesaved, and that calls newuhs */
3750             return;
3751         }
3752     }
3753
3754     if (newhs != u.uhs) {
3755         if (newhs >= WEAK && u.uhs < WEAK) {
3756             /* this used to be losestr(1) which had the potential to
3757                be fatal (still handled below) by reducing HP if it
3758                tried to take base strength below minimum of 3 */
3759             ATEMP(A_STR) = -1; /* temporary loss overrides Fixed_abil */
3760             /* defer context.botl status update until after hunger message */
3761         } else if (newhs < WEAK && u.uhs >= WEAK) {
3762             /* this used to be losestr(-1) which could be abused by
3763                becoming weak while wearing ring of sustain ability,
3764                removing ring, eating to 'restore' strength which boosted
3765                strength by a point each time the cycle was performed;
3766                substituting "while polymorphed" for sustain ability and
3767                "rehumanize" for ring removal might have done that too */
3768             ATEMP(A_STR) = 0; /* repair of loss also overrides Fixed_abil */
3769             /* defer context.botl status update until after hunger message */
3770         }
3771
3772         switch (newhs) {
3773         case HUNGRY:
3774             if (Hallucination) {
3775 #if 0 /*JP:T*/
3776                 You((!incr) ? "now have a lesser case of the munchies."
3777                             : "are getting the munchies.");
3778 #else
3779                 if (!incr) {
3780                     You("\83n\83\89\83w\83\8a\82ª\8c¸\82Á\82½\81D");
3781                 } else {
3782                     pline("\83n\83\89\83w\83\8a\83w\83\8a\83n\83\89\81D");
3783                 }
3784 #endif
3785             } else
3786 /*JP
3787                 You((!incr) ? "only feel hungry now."
3788 */
3789                 You((!incr) ? "\92P\82É\95 \83y\83R\8fó\91Ô\82É\82È\82Á\82½\81D"
3790                             : (u.uhunger < 145)
3791 /*JP
3792                                   ? "feel hungry."
3793 */
3794                                   ? "\8bó\95 \8a´\82ð\8a´\82\82½\81D"
3795 /*JP
3796                                   : "are beginning to feel hungry.");
3797 */
3798                                   : "\8bó\95 \8a´\82ð\82¨\82Ú\82¦\82Í\82\82ß\82½\81D");
3799             if (incr && occupation
3800                 && (occupation != eatfood && occupation != opentin))
3801                 stop_occupation();
3802             context.travel = context.travel1 = context.mv = context.run = 0;
3803             break;
3804         case WEAK:
3805             if (Hallucination)
3806 /*JP
3807                 pline((!incr) ? "You still have the munchies."
3808 */
3809                 pline((!incr) ? "\83n\83\89\83w\83\8a\82ª\8c¸\82ç\82È\82¢\81D"
3810 /*JP
3811               : "The munchies are interfering with your motor capabilities.");
3812 */
3813               : "\83n\83\89\83w\83\8a\82ª\83\82\81[\83^\81[\90«\94\\82É\89e\8b¿\82ð\97^\82¦\82Ä\82¢\82é\81D");
3814             else if (incr && (Role_if(PM_WIZARD) || Race_if(PM_ELF)
3815                               || Role_if(PM_VALKYRIE)))
3816 /*JP
3817                 pline("%s needs food, badly!",
3818 */
3819                 pline("%s\82É\82Í\8e\8a\8b}\90H\97¿\82ª\95K\97v\82¾\81I",
3820                       (Role_if(PM_WIZARD) || Role_if(PM_VALKYRIE))
3821                           ? urole.name.m
3822 /*JP
3823                           : "Elf");
3824 */
3825                           : "\83G\83\8b\83t");
3826             else
3827                 You((!incr)
3828 /*JP
3829                         ? "feel weak now."
3830 */
3831                         ? "\90\8a\8eã\8fó\91Ô\82É\82È\82Á\82½\81D"
3832 /*JP
3833                         : (u.uhunger < 45) ? "feel weak."
3834 */
3835                         : (u.uhunger < 45) ? "\90\8a\8eã\82µ\82Ä\82«\82½\81D"
3836 /*JP
3837                                            : "are beginning to feel weak.");
3838 */
3839                                            : "\8eã\82­\82È\82Á\82Ä\82«\82½\82æ\82¤\82É\8a´\82\82½\81D");
3840             if (incr && occupation
3841                 && (occupation != eatfood && occupation != opentin))
3842                 stop_occupation();
3843             context.travel = context.travel1 = context.mv = context.run = 0;
3844             break;
3845         }
3846         u.uhs = newhs;
3847         context.botl = 1;
3848         bot();
3849         if ((Upolyd ? u.mh : u.uhp) < 1) {
3850 /*JP
3851             You("die from hunger and exhaustion.");
3852 */
3853             You("\8bó\95 \82Æ\90\8a\8eã\82Å\8e\80\82ñ\82¾\81D");
3854             killer.format = KILLED_BY;
3855 /*JP
3856             Strcpy(killer.name, "exhaustion");
3857 */
3858             Strcpy(killer.name, "\8bó\95 \82Æ\90\8a\8eã\82Å\8e\80\82ñ\82¾");
3859             done(STARVING);
3860             return;
3861         }
3862     }
3863 }
3864
3865 /* Returns an object representing food.
3866  * Object may be either on floor or in inventory.
3867  */
3868 /*JP CHECK: 3.6.2 \82Å\82Ì\8cÄ\82Ñ\8fo\82µ\8c³
3869 apply.c:2500:    if (!(corpse = floorfood("tin", 2)))
3870 eat.c:3089:    if (!(otmp = floorfood("eat", 0)))
3871 pray.c:1684:    otmp = floorfood("sacrifice", 1);
3872   \82±\82Ì\8aÖ\90\94\82Í\89p\8cê\96¼\82Ì\82Ü\82Ü\8cÄ\82Ñ\8fo\82·\82±\82Æ\81B
3873 */
3874 struct obj *
3875 floorfood(verb, corpsecheck)
3876 const char *verb;
3877 int corpsecheck; /* 0, no check, 1, corpses, 2, tinnable corpses */
3878 {
3879     register struct obj *otmp;
3880     char qbuf[QBUFSZ];
3881     char c;
3882     boolean feeding = !strcmp(verb, "eat"),    /* corpsecheck==0 */
3883         offering = !strcmp(verb, "sacrifice"); /* corpsecheck==1 */
3884
3885 #if 1 /*JP*/
3886     const char *jverb = trans_verb(verb)->jp;
3887 #endif
3888
3889     /* if we can't touch floor objects then use invent food only */
3890     if (iflags.menu_requested /* command was preceded by 'm' prefix */
3891         || !can_reach_floor(TRUE) || (feeding && u.usteed)
3892         || (is_pool_or_lava(u.ux, u.uy)
3893             && (Wwalking || is_clinger(youmonst.data)
3894                 || (Flying && !Breathless))))
3895         goto skipfloor;
3896
3897     if (feeding && metallivorous(youmonst.data)) {
3898         struct obj *gold;
3899         struct trap *ttmp = t_at(u.ux, u.uy);
3900
3901         if (ttmp && ttmp->tseen && ttmp->ttyp == BEAR_TRAP) {
3902             boolean u_in_beartrap = (u.utrap && u.utraptype == TT_BEARTRAP);
3903
3904             /* If not already stuck in the trap, perhaps there should
3905                be a chance to becoming trapped?  Probably not, because
3906                then the trap would just get eaten on the _next_ turn... */
3907 #if 0 /*JP:T*/
3908             Sprintf(qbuf, "There is a bear trap here (%s); eat it?",
3909                     u_in_beartrap ? "holding you" : "armed");
3910 #else
3911             Sprintf(qbuf, "\82±\82±\82É\82Í\8cF\82Ìã©(%s)\82ª\82 \82é; \90H\82×\82Ü\82·\82©\81H",
3912                     u_in_beartrap ? "\82 \82È\82½\82ð\92Í\82Ü\82¦\82Ä\82¢\82é" : "\89Ò\93®\92\86");
3913 #endif
3914             if ((c = yn_function(qbuf, ynqchars, 'n')) == 'y') {
3915                 deltrap(ttmp);
3916                 if (u_in_beartrap)
3917                     reset_utrap(TRUE);
3918                 return mksobj(BEARTRAP, TRUE, FALSE);
3919             } else if (c == 'q') {
3920                 return (struct obj *) 0;
3921             }
3922         }
3923
3924         if (youmonst.data != &mons[PM_RUST_MONSTER]
3925             && (gold = g_at(u.ux, u.uy)) != 0) {
3926 #if 0 /*JP:T*/
3927             if (gold->quan == 1L)
3928                 Sprintf(qbuf, "There is 1 gold piece here; eat it?");
3929             else
3930                 Sprintf(qbuf, "There are %ld gold pieces here; eat them?",
3931                         gold->quan);
3932 #else
3933             Sprintf(qbuf, "\82±\82±\82É\82Í%ld\96\87\82Ì\8bà\89Ý\82ª\82 \82é\81D\90H\82×\82Ü\82·\82©\81H", gold->quan);
3934 #endif
3935             if ((c = yn_function(qbuf, ynqchars, 'n')) == 'y') {
3936                 return gold;
3937             } else if (c == 'q') {
3938                 return (struct obj *) 0;
3939             }
3940         }
3941     }
3942
3943     /* Is there some food (probably a heavy corpse) here on the ground? */
3944     for (otmp = level.objects[u.ux][u.uy]; otmp; otmp = otmp->nexthere) {
3945         if (corpsecheck
3946                 ? (otmp->otyp == CORPSE
3947                    && (corpsecheck == 1 || tinnable(otmp)))
3948                 : feeding ? (otmp->oclass != COIN_CLASS && is_edible(otmp))
3949                           : otmp->oclass == FOOD_CLASS) {
3950             char qsfx[QBUFSZ];
3951             boolean one = (otmp->quan == 1L);
3952
3953             /* if blind and without gloves, attempting to eat (or tin or
3954                offer) a cockatrice corpse is fatal before asking whether
3955                or not to use it; otherwise, 'm<dir>' followed by 'e' could
3956                be used to locate cockatrice corpses without touching them */
3957             if (otmp->otyp == CORPSE && will_feel_cockatrice(otmp, FALSE)) {
3958                 feel_cockatrice(otmp, FALSE);
3959                 /* if life-saved (or poly'd into stone golem), terminate
3960                    attempt to eat off floor */
3961                 return (struct obj *) 0;
3962             }
3963             /* "There is <an object> here; <verb> it?" or
3964                "There are <N objects> here; <verb> one?" */
3965 #if 0 /*JP*/
3966             Sprintf(qbuf, "There %s ", otense(otmp, "are"));
3967             Sprintf(qsfx, " here; %s %s?", verb, one ? "it" : "one");
3968             (void) safe_qbuf(qbuf, qbuf, qsfx, otmp, doname, ansimpleoname,
3969                              one ? something : (const char *) "things");
3970 #else
3971             Strcpy(qbuf, "\82±\82±\82É");
3972             Sprintf(qsfx, "\82ª\82 \82é; %s%s?", one ? "" : "\88ê\82Â", jverb);
3973             (void) safe_qbuf(qbuf, qbuf, qsfx, otmp, doname, ansimpleoname,
3974                              one ? something : (const char *) "\89½\82©");
3975 #endif
3976             if ((c = yn_function(qbuf, ynqchars, 'n')) == 'y')
3977                 return  otmp;
3978             else if (c == 'q')
3979                 return (struct obj *) 0;
3980         }
3981     }
3982
3983  skipfloor:
3984     /* We cannot use ALL_CLASSES since that causes getobj() to skip its
3985      * "ugly checks" and we need to check for inedible items.
3986      */
3987     otmp = getobj(feeding ? allobj : offering ? offerfodder : comestibles,
3988                   verb);
3989     if (corpsecheck && otmp && !(offering && otmp->oclass == AMULET_CLASS))
3990         if (otmp->otyp != CORPSE || (corpsecheck == 2 && !tinnable(otmp))) {
3991 /*JP
3992             You_cant("%s that!", verb);
3993 */
3994             You_cant("\82»\82ê\82ð%s\82±\82Æ\82Í\82Å\82«\82È\82¢\81I", jverb);
3995             return (struct obj *) 0;
3996         }
3997     return otmp;
3998 }
3999
4000 /* Side effects of vomiting */
4001 /* added nomul (MRS) - it makes sense, you're too busy being sick! */
4002 void
4003 vomit() /* A good idea from David Neves */
4004 {
4005     if (cantvomit(youmonst.data)) {
4006         /* doesn't cure food poisoning; message assumes that we aren't
4007            dealing with some esoteric body_part() */
4008 /*JP
4009         Your("jaw gapes convulsively.");
4010 */
4011         Your("\82 \82²\82Í\94­\8dì\93I\82É\91å\82«\82­\8aJ\82¢\82½\81D");
4012     } else {
4013         if (Sick && (u.usick_type & SICK_VOMITABLE) != 0)
4014             make_sick(0L, (char *) 0, TRUE, SICK_VOMITABLE);
4015         /* if not enough in stomach to actually vomit then dry heave;
4016            vomiting_dialog() gives a vomit message when its countdown
4017            reaches 0, but only if u.uhs < FAINTING (and !cantvomit()) */
4018         if (u.uhs >= FAINTING)
4019 /*JP
4020             Your("%s heaves convulsively!", body_part(STOMACH));
4021 */
4022             Your("%s\82Í\8c\83\82µ\82¢\93f\82«\8bC\82ð\82à\82æ\82¨\82µ\82½\81I", body_part(STOMACH));
4023     }
4024
4025     /* nomul()/You_can_move_again used to be unconditional, which was
4026        viable while eating but not for Vomiting countdown where hero might
4027        be immobilized for some other reason at the time vomit() is called */
4028     if (multi >= -2) {
4029         nomul(-2);
4030 /*JP
4031         multi_reason = "vomiting";
4032 */
4033         multi_reason = "\9aq\93f\82µ\82Ä\82¢\82é\8dÅ\92\86\82É";
4034         nomovemsg = You_can_move_again;
4035     }
4036 }
4037
4038 int
4039 eaten_stat(base, obj)
4040 int base;
4041 struct obj *obj;
4042 {
4043     long uneaten_amt, full_amount;
4044
4045     /* get full_amount first; obj_nutrition() might modify obj->oeaten */
4046     full_amount = (long) obj_nutrition(obj);
4047     uneaten_amt = (long) obj->oeaten;
4048     if (uneaten_amt > full_amount) {
4049         impossible(
4050           "partly eaten food (%ld) more nutritious than untouched food (%ld)",
4051                    uneaten_amt, full_amount);
4052         uneaten_amt = full_amount;
4053     }
4054
4055     base = (int) (full_amount ? (long) base * uneaten_amt / full_amount : 0L);
4056     return (base < 1) ? 1 : base;
4057 }
4058
4059 /* reduce obj's oeaten field, making sure it never hits or passes 0 */
4060 void
4061 consume_oeaten(obj, amt)
4062 struct obj *obj;
4063 int amt;
4064 {
4065     /*
4066      * This is a hack to try to squelch several long standing mystery
4067      * food bugs.  A better solution would be to rewrite the entire
4068      * victual handling mechanism from scratch using a less complex
4069      * model.  Alternatively, this routine could call done_eating()
4070      * or food_disappears() but its callers would need revisions to
4071      * cope with context.victual.piece unexpectedly going away.
4072      *
4073      * Multi-turn eating operates by setting the food's oeaten field
4074      * to its full nutritional value and then running a counter which
4075      * independently keeps track of whether there is any food left.
4076      * The oeaten field can reach exactly zero on the last turn, and
4077      * the object isn't removed from inventory until the next turn
4078      * when the "you finish eating" message gets delivered, so the
4079      * food would be restored to the status of untouched during that
4080      * interval.  This resulted in unexpected encumbrance messages
4081      * at the end of a meal (if near enough to a threshold) and would
4082      * yield full food if there was an interruption on the critical
4083      * turn.  Also, there have been reports over the years of food
4084      * becoming massively heavy or producing unlimited satiation;
4085      * this would occur if reducing oeaten via subtraction attempted
4086      * to drop it below 0 since its unsigned type would produce a
4087      * huge positive value instead.  So far, no one has figured out
4088      * _why_ that inappropriate subtraction might sometimes happen.
4089      */
4090
4091     if (amt > 0) {
4092         /* bit shift to divide the remaining amount of food */
4093         obj->oeaten >>= amt;
4094     } else {
4095         /* simple decrement; value is negative so we actually add it */
4096         if ((int) obj->oeaten > -amt)
4097             obj->oeaten += amt;
4098         else
4099             obj->oeaten = 0;
4100     }
4101
4102     if (obj->oeaten == 0) {
4103         if (obj == context.victual.piece) /* always true unless wishing... */
4104             context.victual.reqtime =
4105                 context.victual.usedtime; /* no bites left */
4106         obj->oeaten = 1; /* smallest possible positive value */
4107     }
4108 }
4109
4110 /* called when eatfood occupation has been interrupted,
4111    or in the case of theft, is about to be interrupted */
4112 boolean
4113 maybe_finished_meal(stopping)
4114 boolean stopping;
4115 {
4116     /* in case consume_oeaten() has decided that the food is all gone */
4117     if (occupation == eatfood
4118         && context.victual.usedtime >= context.victual.reqtime) {
4119         if (stopping)
4120             occupation = 0; /* for do_reset_eat */
4121         (void) eatfood();   /* calls done_eating() to use up
4122                                context.victual.piece */
4123         return TRUE;
4124     }
4125     return FALSE;
4126 }
4127
4128 /* Tin of <something> to the rescue?  Decide whether current occupation
4129    is an attempt to eat a tin of something capable of saving hero's life.
4130    We don't care about consumption of non-tinned food here because special
4131    effects there take place on first bite rather than at end of occupation.
4132    [Popeye the Sailor gets out of trouble by eating tins of spinach. :-] */
4133 boolean
4134 Popeye(threat)
4135 int threat;
4136 {
4137     struct obj *otin;
4138     int mndx;
4139
4140     if (occupation != opentin)
4141         return FALSE;
4142     otin = context.tin.tin;
4143     /* make sure hero still has access to tin */
4144     if (!carried(otin)
4145         && (!obj_here(otin, u.ux, u.uy) || !can_reach_floor(TRUE)))
4146         return FALSE;
4147     /* unknown tin is assumed to be helpful */
4148     if (!otin->known)
4149         return TRUE;
4150     /* known tin is helpful if it will stop life-threatening problem */
4151     mndx = otin->corpsenm;
4152     switch (threat) {
4153     /* note: not used; hunger code bypasses stop_occupation() when eating */
4154     case HUNGER:
4155         return (boolean) (mndx != NON_PM || otin->spe == 1);
4156     /* flesh from lizards and acidic critters stops petrification */
4157     case STONED:
4158         return (boolean) (mndx >= LOW_PM
4159                           && (mndx == PM_LIZARD || acidic(&mons[mndx])));
4160     /* no tins can cure these (yet?) */
4161     case SLIMED:
4162     case SICK:
4163     case VOMITING:
4164         break;
4165     default:
4166         break;
4167     }
4168     return FALSE;
4169 }
4170
4171 /*eat.c*/