Polyobject waypoint movement: Prevent infinite loop if all waypoints are in the same location

This commit is contained in:
MascaraSnake 2020-05-16 10:24:06 +02:00
parent 536e355cdf
commit 371a1851e3
3 changed files with 41 additions and 0 deletions

View File

@ -631,6 +631,7 @@ mobj_t *P_GetLastWaypoint(UINT8 sequence);
mobj_t *P_GetPreviousWaypoint(mobj_t *current, boolean wrap);
mobj_t *P_GetNextWaypoint(mobj_t *current, boolean wrap);
mobj_t *P_GetClosestWaypoint(UINT8 sequence, mobj_t *mo);
boolean P_IsDegeneratedWaypointSequence(UINT8 sequence);
// =====================================
// Internal parameters, used for engine.

View File

@ -2173,6 +2173,14 @@ boolean EV_DoPolyObjWaypoint(polywaypointdata_t *pwdata)
return false;
}
// Sanity check: If all waypoints are in the same location,
// don't allow the movement to be continuous so we don't get stuck in an infinite loop.
if (th->continuous && P_IsDegeneratedWaypointSequence(th->sequence))
{
CONS_Debug(DBG_POLYOBJ, "EV_DoPolyObjWaypoint: All waypoints are in the same location!\n");
th->continuous = false;
}
th->pointnum = first->health;
return true;

View File

@ -239,6 +239,38 @@ mobj_t *P_GetClosestWaypoint(UINT8 sequence, mobj_t *mo)
return result;
}
// Return true if all waypoints are in the same location
boolean P_IsDegeneratedWaypointSequence(UINT8 sequence)
{
mobj_t *first, *waypoint;
UINT8 wp;
if (numwaypoints[sequence] <= 1)
return true;
first = waypoints[sequence][0];
for (wp = 1; wp < numwaypoints[sequence]; wp++)
{
waypoint = waypoints[sequence][wp];
if (!waypoint)
continue;
if (waypoint->x != first->x)
return false;
if (waypoint->y != first->y)
return false;
if (waypoint->z != first->z)
return false;
}
return true;
}
/** Logs an error about a map being corrupt, then terminate.
* This allows reporting highly technical errors for usefulness, without
* confusing a novice map designer who simply needs to run ZenNode.