added mixing thread, as well as start and stop
git-svn-id: file:///srv/svn/repos/haiku/trunk/current@3660 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -40,7 +40,9 @@ MixerCore::MixerCore()
|
|||||||
fDoubleRateMixing(DOUBLE_RATE_MIXING),
|
fDoubleRateMixing(DOUBLE_RATE_MIXING),
|
||||||
fLastMixStartTime(0),
|
fLastMixStartTime(0),
|
||||||
fBufferGroup(0),
|
fBufferGroup(0),
|
||||||
fTimeSource(0)
|
fTimeSource(0),
|
||||||
|
fMixThread(-1),
|
||||||
|
fMixThreadWaitSem(-1)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -49,6 +51,9 @@ MixerCore::~MixerCore()
|
|||||||
delete fLocker;
|
delete fLocker;
|
||||||
delete fInputs;
|
delete fInputs;
|
||||||
|
|
||||||
|
ASSERT(fMixThreadWaitSem == -1);
|
||||||
|
ASSERT(fMixThread == -1);
|
||||||
|
|
||||||
if (fMixBuffer)
|
if (fMixBuffer)
|
||||||
rtm_free(fMixBuffer);
|
rtm_free(fMixBuffer);
|
||||||
|
|
||||||
@@ -221,6 +226,9 @@ MixerCore::Start(bigtime_t time)
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
fRunning = true;
|
fRunning = true;
|
||||||
|
fMixThreadWaitSem = create_sem(0, "mix thread wait");
|
||||||
|
fMixThread = spawn_thread(_mix_thread_, "Yeah baby, very shagadelic", 12, this);
|
||||||
|
resume_thread(fMixThread);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
@@ -229,7 +237,16 @@ MixerCore::Stop()
|
|||||||
ASSERT_LOCKED();
|
ASSERT_LOCKED();
|
||||||
if (!fRunning)
|
if (!fRunning)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
ASSERT(fMixThread > 0);
|
||||||
|
ASSERT(fMixThreadWaitSem > 0);
|
||||||
|
|
||||||
|
status_t unused;
|
||||||
|
delete_sem(fMixThreadWaitSem);
|
||||||
|
wait_for_thread(fMixThread, &unused);
|
||||||
|
|
||||||
|
fMixThread = -1;
|
||||||
|
fMixThreadWaitSem = -1;
|
||||||
fRunning = false;
|
fRunning = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -249,44 +266,50 @@ MixerCore::IsStarted()
|
|||||||
return fRunning;
|
return fRunning;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
void BufferReceived(BBuffer *buffer, bigtime_t lateness);
|
|
||||||
|
|
||||||
|
|
||||||
if (buffer->SizeUsed() > (channel->fDataSize - total_offset))
|
|
||||||
{
|
|
||||||
memcpy(channel->fData + total_offset, indata, channel->fDataSize - total_offset);
|
|
||||||
memcpy(channel->fData, indata + (channel->fDataSize - total_offset), buffer->SizeUsed() - (channel->fDataSize - total_offset));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
memcpy(channel->fData + total_offset, indata, buffer->SizeUsed());
|
|
||||||
|
|
||||||
if ((B_OFFLINE == RunMode()) && (B_DATA_AVAILABLE == channel->fProducerDataStatus))
|
|
||||||
{
|
|
||||||
RequestAdditionalBuffer(channel->fInput.source, buffer);
|
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// use this later for separate threads
|
|
||||||
|
|
||||||
int32
|
int32
|
||||||
AudioMixer::_mix_thread_(void *data)
|
MixerCore::_mix_thread_(void *arg)
|
||||||
{
|
{
|
||||||
return ((AudioMixer *)data)->MixThread();
|
static_cast<MixerCore *>(arg)->MixThread();
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int32
|
void
|
||||||
AudioMixer::MixThread()
|
MixerCore::MixThread()
|
||||||
{
|
{
|
||||||
while (1)
|
bigtime_t event_time;
|
||||||
{
|
bigtime_t base;
|
||||||
snooze(500000);
|
bigtime_t latency;
|
||||||
}
|
int64 pos;
|
||||||
|
|
||||||
}
|
pos = 0;
|
||||||
|
latency = 30000;
|
||||||
|
base = event_time = fTimeSource->Now();
|
||||||
|
for (;;) {
|
||||||
|
status_t rv;
|
||||||
|
rv = acquire_sem_etc(fMixThreadWaitSem, 1, B_ABSOLUTE_TIMEOUT, fTimeSource->RealTimeFor(event_time, latency));
|
||||||
|
if (rv == B_INTERRUPTED)
|
||||||
|
continue;
|
||||||
|
if (rv < B_OK)
|
||||||
|
return;
|
||||||
|
|
||||||
|
// mix all data from all inputs into the mix buffer
|
||||||
|
|
||||||
|
// request a buffer
|
||||||
|
BBuffer* buf = fBufferGroup->RequestBuffer(fOutput->MediaOutput().format.u.raw_audio.buffer_size, 10000);
|
||||||
|
|
||||||
|
// copy data from mix buffer into output buffer
|
||||||
|
|
||||||
*/
|
// fill in the buffer header
|
||||||
|
media_header* hdr = buf->Header();
|
||||||
|
hdr->type = B_MEDIA_RAW_AUDIO;
|
||||||
|
hdr->size_used = fOutput->MediaOutput().format.u.raw_audio.buffer_size;
|
||||||
|
hdr->time_source = fTimeSource->ID();
|
||||||
|
hdr->start_time = event_time;
|
||||||
|
|
||||||
|
// send the buffer
|
||||||
|
|
||||||
|
// shedule next event
|
||||||
|
pos += fMixBufferFrameCount;
|
||||||
|
event_time = base + bigtime_t((1000000LL * pos) / fMixBufferFrameRate);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -43,15 +43,11 @@ public:
|
|||||||
uint32 OutputChannelCount();
|
uint32 OutputChannelCount();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
// handle mixing in separate thread
|
static int32 _mix_thread_(void *arg);
|
||||||
// not implemented (yet)
|
void MixThread();
|
||||||
|
|
||||||
static int32 _mix_thread_(void *data);
|
|
||||||
int32 MixThread();
|
|
||||||
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
BLocker *fLocker;
|
BLocker *fLocker;
|
||||||
|
|
||||||
BList *fInputs;
|
BList *fInputs;
|
||||||
MixerOutput *fOutput;
|
MixerOutput *fOutput;
|
||||||
@@ -68,6 +64,8 @@ private:
|
|||||||
|
|
||||||
BBufferGroup *fBufferGroup;
|
BBufferGroup *fBufferGroup;
|
||||||
BTimeSource *fTimeSource;
|
BTimeSource *fTimeSource;
|
||||||
|
thread_id fMixThread;
|
||||||
|
sem_id fMixThreadWaitSem;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user