Skip to content

Remove unused volume model in SamplePlayHandle#8349

Merged
sakertooth merged 2 commits intoLMMS:masterfrom
sakertooth:remove-unused-model-sample-handle
Apr 21, 2026
Merged

Remove unused volume model in SamplePlayHandle#8349
sakertooth merged 2 commits intoLMMS:masterfrom
sakertooth:remove-unused-model-sample-handle

Conversation

@sakertooth
Copy link
Copy Markdown
Contributor

@sakertooth sakertooth commented Apr 5, 2026

Removes the unused volume model in SamplePlayHandle, as allocating this was causing performance issues under extreme conditions (see #8348). Profiling showed a performance bottleneck in lmms::ProjectJournal::allocID, which creates a new journaling ID for the model.

jo_id_t ProjectJournal::allocID(JournallingObject* obj)
{
	jo_id_t id;
	for (jo_id_t tid = fastRand(); m_joIDs.contains(id = tid % EO_ID_MSB | EO_ID_MSB); tid++) {}
	m_joIDs[id] = obj;
	return id;
}

Given that this was called so rapidly, its likely that the map filled very quickly (fastRand only has a range of 32,767 values) and over time, tid kept incrementing for longer and longer periods of time, taking up CPU cycles.

Here is the backtrace as well:

Thread 4 (Thread 0x7f4357fff6c0 (LWP 172461) "SDLAudioP15"):
#0  0x000055989de4889b in lmms::ProjectJournal::allocID(lmms::JournallingObject*) ()
#1  0x000055989de19532 in lmms::JournallingObject::JournallingObject() ()
#2  0x000055989ddbd386 in lmms::AutomatableModel::AutomatableModel(float, float, float, float, lmms::Model*, QString const&, bool) ()
#3  0x000055989de58bc2 in lmms::SamplePlayHandle::SamplePlayHandle(lmms::Sample*, bool) ()
#4  0x000055989de58d9b in lmms::SamplePlayHandle::SamplePlayHandle(QString const&) ()
#5  0x000055989de27a4d in lmms::Metronome::processTick(int, int, int, unsigned long) ()
#6  0x000055989de5e124 in lmms::Song::processMetronome(unsigned long) ()
#7  0x000055989de5d8c1 in lmms::Song::processNextBuffer() ()
#8  0x000055989ddba3b7 in lmms::AudioEngine::renderStageNoteSetup() ()
#9  0x000055989ddbad66 in lmms::AudioEngine::renderNextPeriod() ()
#10 0x000055989de73f4e in _ZN4lmms11AudioEngine16renderNextBufferITkNS_15AudioBufferViewIfEENS_21InterleavedBufferViewIfLt65535EEEEEvT_ ()
#11 0x000055989de83140 in lmms::AudioSdl::sdlAudioCallback(void*, unsigned char*, int) ()

Couple of points:

  1. There are still performance issues because rapid allocations of SamplePlayHandle objects (when not allocated from a SampleClip* but a path to a sample) lead to decoding the audio file repetitively on the audio thread. This problem is currently only seen with the metronome (and theoretically also tap tempo).
  2. At some point we still may need to figure out a design if we want to control the volume from the SamplePlayHandle object directly without performance headaches. Currently, we can't and don't do that anyways (e.g., clips and their volume are handled via AudioBusHandle, which has a pointer to the volume model contained within the track) so this unused volume model was causing more problems than anything else.
  3. I'm not focusing on the allocations of the voice objects themselves, since this is more of an issue with the overall design of the audio engine, which allocates the handles on demand. Eventually, we will use some kind of voice pool for these allocations.

Fixes #8348.

@sakertooth
Copy link
Copy Markdown
Contributor Author

There are still performance issues because rapid allocations of SamplePlayHandle objects (when not allocated from a SampleClip* but a path to a sample) lead to decoding the audio file repetitively on the audio thread. This problem is currently only seen with the metronome (and theoretically also tap tempo).

Fixed in #8350.

Copy link
Copy Markdown
Contributor

@rubiefawn rubiefawn left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM. I'd suggest using NSDMI for some of the members of SamplePlayHandle (coding conventions) but that's non-blocking.

@sakertooth
Copy link
Copy Markdown
Contributor Author

LGTM. I'd suggest using NSDMI for some of the members of SamplePlayHandle (coding conventions) but that's non-blocking.

Great. And will get around to doing that eventually.

@sakertooth sakertooth merged commit fc3dfda into LMMS:master Apr 21, 2026
10 of 11 checks passed
@sakertooth sakertooth deleted the remove-unused-model-sample-handle branch April 21, 2026 11:37
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

CPU meter maxes out when playing short samples rapidly

2 participants