From 16018ac824db17481f2e741294f2a370ffae38ec Mon Sep 17 00:00:00 2001 From: Pasi Kallinen Date: Sun, 11 Oct 2015 18:52:24 +0300 Subject: [PATCH] Put monsters into limbo if they cannot be placed Whenever mnearto tries to displace a monster from underneath another, and the displaced one cannot be placed anywhere, make it drop special objects and put it into migration, with the current level as the target. This should be a good enough stopgap measure - it's not going to happen unless the level is (nearly) full of monsters. And it seems to cure a near-impossible-to-track data corruption, with monster list pointing to garbage. --- src/mon.c | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/src/mon.c b/src/mon.c index f257e7f31..44f4c48ae 100644 --- a/src/mon.c +++ b/src/mon.c @@ -2342,13 +2342,15 @@ boolean move_other; /* make sure mtmp gets to x, y! so move m_at(x, y) */ xchar oldx = othermon->mx, oldy = othermon->my; othermon->mx = othermon->my = 0; - if (!mnearto(othermon, x, y, FALSE)) { + (void) mnearto(othermon, x, y, FALSE); + if (othermon->mx == 0 && othermon->my == 0) { + /* reloc failed, dump monster into "limbo" + (aka migrate to current level) */ othermon->mx = oldx; othermon->my = oldy; - return FALSE; + mdrop_special_objs(othermon); + migrate_to_level(othermon, ledger_no(&u.uz), MIGR_APPROX_XY, NULL); } - if (othermon->mx != x || othermon->my != y) - return TRUE; } return FALSE;