fix(memory): Fix memory leak for audio events when pausing the game#2731
fix(memory): Fix memory leak for audio events when pausing the game#2731Caball009 wants to merge 2 commits into
Conversation
|
| Filename | Overview |
|---|---|
| Core/GameEngine/Include/Common/AudioRequest.h | Adds releasePendingEvent() declaration; existing struct layout unchanged. Clean change. |
| Core/GameEngine/Source/Common/Audio/AudioRequest.cpp | Implements the destructor fix and releasePendingEvent(). Destructor guards with m_usePendingEvent before deleting, and releasePendingEvent() clears the flag and pointer atomically before returning to prevent double-free. |
| Core/GameEngineDevice/Include/MilesAudioDevice/MilesAudioManager.h | Updates playAudioEvent signature from AudioEventRTS* to AudioRequest* to enable ownership tracking within the function. |
| Core/GameEngineDevice/Source/MilesAudioDevice/MilesAudioManager.cpp | Refactors playAudioEvent to accept AudioRequest*. Transfers ownership via releasePendingEvent() exactly once in each code path (Streaming, 3D sample, 2D sample). Uses audio->m_audioEventRTS exclusively for all post-release accesses; the local event alias is only read before transfer. |
Sequence Diagram
sequenceDiagram
participant ARC as AudioRequestContainer
participant PAE as processRequest
participant PAF as playAudioEvent
participant AR as AudioRequest
participant PA as PlayingAudio
ARC->>PAE: iterate queued requests on pause
PAE->>PAF: playAudioEvent(req) [AR_Play]
PAF->>AR: "read req->m_pendingEvent (local alias)"
PAF->>AR: getAudioEventInfo() — early return?
alt "info == nullptr"
PAF-->>PAE: return (req destructor frees event)
PAE->>AR: ~AudioRequest() — delete m_pendingEvent
else valid info
PAF->>AR: releasePendingEvent()
AR-->>PAF: "returns AudioEventRTS* (clears m_usePendingEvent)"
PAF->>PA: "audio->m_audioEventRTS = released event"
PA-->>PAF: owns event henceforth
end
Reviews (5): Last reviewed commit: "Implemented 'releasePendingEvent' member..." | Re-trigger Greptile
057637e to
977bd8b
Compare
977bd8b to
afb337c
Compare
|
Rebased to include the fix for the CI Replay checker. |
9e09418 to
08f2330
Compare
|
|
||
| // Put this on here, so that the audio event RTS will be cleaned up regardless. | ||
| audio->m_audioEventRTS = event; | ||
| audio->m_audioEventRTS = req->releasePendingEvent(); |
There was a problem hiding this comment.
You could also write audio->m_audioEventRTS = event = req->releasePendingEvent(); and just keep using event everywhere.
There was a problem hiding this comment.
What's the point of the assignment to event?
There was a problem hiding this comment.
It's optional, but just a tiny bit more robust if releasePendingEvent was changed and would suddenly introduce a new pointer.
08f2330 to
130a39f
Compare
Pausing the game leaks audio events that were in the audio request container at the time. This PR fixes that.
This code is called to get rid of some of the audio requests when pausing the game:
GeneralsGameCode/Core/GameEngineDevice/Source/MilesAudioDevice/MilesAudioManager.cpp
Lines 587 to 601 in 2219f63
AudioRequest::m_pendingEventcan be an owning raw pointer, though, which the destructor ofAudioRequestshould delete when needed. It currently doesn't, which is why the leak happens.GeneralsGameCode/Core/GameEngine/Include/Common/AudioRequest.h
Line 51 in 2219f63
There's one exception where the ownership of the audio event is taken away from the audio request:
GeneralsGameCode/Core/GameEngineDevice/Source/MilesAudioDevice/MilesAudioManager.cpp
Line 2238 in 2219f63