Skip to content

Commit

Permalink
ChaosMod/EffectDispatcher: Effect update loop fixes
Browse files Browse the repository at this point in the history
- Prevent non-timed ActiveEffect instances from potentially interfering with the effect threads of other non-timed ActiveEffect instances

- Print if an effect misbehaves and takes over 60 secs to stop in release builds as well
  • Loading branch information
pongo1231 committed Feb 6, 2025
1 parent 0e997e1 commit f9ef72b
Show file tree
Hide file tree
Showing 2 changed files with 21 additions and 16 deletions.
36 changes: 20 additions & 16 deletions ChaosMod/Components/EffectDispatcher.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,7 @@ static void _DispatchEffect(EffectDispatcher *effectDispatcher, const EffectDisp
{
// Replace previous instance of non-timed effect with this new one
EffectThreads::StopThreadImmediately(activeEffect.ThreadId);
activeEffect.IsZombie = true;
}

break;
Expand Down Expand Up @@ -309,8 +310,16 @@ void EffectDispatcher::UpdateEffects(float deltaTime)
auto &activeEffect = *it;
bool isEffectPaused = EffectThreads::IsThreadPaused(activeEffect.ThreadId);

if (!EffectThreads::DoesThreadExist(activeEffect.ThreadId))
activeEffect.Timer -=
(adjustedDeltaTime
/ (!ComponentExists<MetaModifiers>() ? 1.f : GetComponent<MetaModifiers>()->EffectDurationModifier))
* (activeEffect.IsTimed
? 1.f
: std::max(1.f, .5f * (activeEffects - EFFECT_NONTIMED_TIMER_SPEEDUP_MIN_EFFECTS + 3)));

if (!EffectThreads::DoesThreadExist(activeEffect.ThreadId) || activeEffect.IsZombie)
{
activeEffect.IsZombie = true;
if (activeEffect.IsTimed || activeEffect.Timer <= 0.f)
{
DEBUG_LOG("Discarding ActiveEffect " << activeEffect.Id.Id());
Expand Down Expand Up @@ -365,27 +374,22 @@ void EffectDispatcher::UpdateEffects(float deltaTime)
}
}

activeEffect.Timer -=
(adjustedDeltaTime
/ (!ComponentExists<MetaModifiers>() ? 1.f : GetComponent<MetaModifiers>()->EffectDurationModifier))
* (activeEffect.IsTimed
? 1.f
: std::max(1.f, .5f * (activeEffects - EFFECT_NONTIMED_TIMER_SPEEDUP_MIN_EFFECTS + 3)));

if (activeEffect.Timer <= 0.f || (!activeEffect.IsMeta && activeEffects > m_MaxRunningEffects))
if (!activeEffect.IsZombie // Shouldn't ever occur since the ActiveEffect is removed if timer <= 0 above, but
// just in case this check is moved in the future
&& (activeEffect.Timer <= 0.f || (!activeEffect.IsMeta && activeEffects > m_MaxRunningEffects)))
{
if (activeEffect.Timer < -60.f)
{
// Effect took over 60 seconds to stop, forcibly stop it in a blocking manner
DEBUG_LOG("Tiemout reached, forcefully stopping effect " << activeEffect.Id.Id());
EffectThreads::StopThreadImmediately(activeEffect.ThreadId);
}
else if (!activeEffect.IsStopping)
if (!activeEffect.IsStopping)
{
DEBUG_LOG("Stopping effect " << activeEffect.Id.Id());
EffectThreads::StopThread(activeEffect.ThreadId);
activeEffect.IsStopping = true;
}
else if (activeEffect.Timer < -60.f)
{
// Effect took over 60 seconds to stop, forcibly stop it in a blocking manner
LOG("Timeout reached, forcefully stopping effect " << activeEffect.Id.Id());
EffectThreads::StopThreadImmediately(activeEffect.ThreadId);
}
}

it++;
Expand Down
1 change: 1 addition & 0 deletions ChaosMod/Components/EffectDispatcher.h
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@ class EffectDispatcher : public Component

bool HideEffectName = false;
bool IsStopping = false;
bool IsZombie = false;

DWORD64 SoundId = 0;
};
Expand Down

0 comments on commit f9ef72b

Please sign in to comment.