sound: Drive updates more sensibly from the sound manager, fixing some asserts.

This commit is contained in:
Aaron Giles 2020-09-14 11:08:10 -07:00
parent e652ab5279
commit 6ebf956324
3 changed files with 27 additions and 27 deletions

View File

@ -1528,10 +1528,24 @@ void sound_manager::update(void *ptr, int param)
g_profiler.start(PROFILER_SOUND);
// determine the duration of this update
attotime update_period = machine().time() - m_last_update;
sound_assert(update_period.seconds() == 0);
// use that to compute the number of samples we need from the speakers
attoseconds_t sample_rate_attos = HZ_TO_ATTOSECONDS(machine().sample_rate());
m_samples_this_update = update_period.attoseconds() / sample_rate_attos;
// recompute the end time to an even sample boundary
attotime endtime = m_last_update + attotime(0, m_samples_this_update * sample_rate_attos);
// clear out the mix bufers
std::fill_n(&m_leftmix[0], m_samples_this_update, 0);
std::fill_n(&m_rightmix[0], m_samples_this_update, 0);
// force all the speaker streams to generate the proper number of samples
m_samples_this_update = 0;
for (speaker_device &speaker : speaker_device_iterator(machine().root_device()))
speaker.mix(&m_leftmix[0], &m_rightmix[0], m_samples_this_update, (m_muted & MUTE_REASON_SYSTEM));
speaker.mix(&m_leftmix[0], &m_rightmix[0], m_last_update, endtime, m_samples_this_update, (m_muted & MUTE_REASON_SYSTEM));
// determine the maximum in this section
stream_buffer::sample_t curmax = 0;
@ -1633,13 +1647,8 @@ void sound_manager::update(void *ptr, int param)
for (auto &stream : m_orphan_stream_list)
stream.first->update();
// see if we ticked over to the next second
attotime curtime = machine().time();
if (curtime.seconds() != m_last_update.seconds())
sound_assert(curtime.seconds() == m_last_update.seconds() + 1);
// remember the update time
m_last_update = curtime;
m_last_update = endtime;
m_update_number++;
// apply sample rate changes

View File

@ -56,34 +56,25 @@ speaker_device::~speaker_device()
// mix - mix in samples from the speaker's stream
//-------------------------------------------------
void speaker_device::mix(stream_buffer::sample_t *leftmix, stream_buffer::sample_t *rightmix, u32 &samples_this_update, bool suppress)
void speaker_device::mix(stream_buffer::sample_t *leftmix, stream_buffer::sample_t *rightmix, attotime start, attotime end, int expected_samples, bool suppress)
{
// skip if no stream
if (m_mixer_stream == nullptr)
return;
// update the stream, getting the start/end pointers around the operation
attotime start = m_mixer_stream->sample_time();
attotime end = machine().time();
// skip if invalid range
if (start > end)
return;
// get a view on the desired range
read_stream_view view = m_mixer_stream->update_view(start, end);
// set or assert that all streams have the same count
if (samples_this_update == 0)
{
samples_this_update = view.samples();
// reset the mixing streams
std::fill_n(leftmix, samples_this_update, 0);
std::fill_n(rightmix, samples_this_update, 0);
}
sound_assert(view.samples() >= expected_samples);
// track maximum sample value for each 0.1s bucket
if (machine().options().speaker_report() != 0)
{
u32 samples_per_bucket = m_mixer_stream->sample_rate() / BUCKETS_PER_SECOND;
for (int sample = 0; sample < samples_this_update; sample++)
for (int sample = 0; sample < expected_samples; sample++)
{
m_current_max = std::max(m_current_max, fabsf(view.get(sample)));
if (++m_samples_this_bucket >= samples_per_bucket)
@ -100,7 +91,7 @@ void speaker_device::mix(stream_buffer::sample_t *leftmix, stream_buffer::sample
{
// if the speaker is centered, send to both left and right
if (m_x == 0)
for (int sample = 0; sample < samples_this_update; sample++)
for (int sample = 0; sample < expected_samples; sample++)
{
stream_buffer::sample_t cursample = view.get(sample);
leftmix[sample] += cursample;
@ -109,12 +100,12 @@ void speaker_device::mix(stream_buffer::sample_t *leftmix, stream_buffer::sample
// if the speaker is to the left, send only to the left
else if (m_x < 0)
for (int sample = 0; sample < samples_this_update; sample++)
for (int sample = 0; sample < expected_samples; sample++)
leftmix[sample] += view.get(sample);
// if the speaker is to the right, send only to the right
else
for (int sample = 0; sample < samples_this_update; sample++)
for (int sample = 0; sample < expected_samples; sample++)
rightmix[sample] += view.get(sample);
}
}

View File

@ -69,7 +69,7 @@ public:
speaker_device &backrest() { set_position( 0.0, -0.2, 0.1); return *this; }
// internally for use by the sound system
void mix(stream_buffer::sample_t *leftmix, stream_buffer::sample_t *rightmix, u32 &samples_this_update, bool suppress);
void mix(stream_buffer::sample_t *leftmix, stream_buffer::sample_t *rightmix, attotime start, attotime end, int expected_samples, bool suppress);
protected:
// device-level overrides