Fix a locking problem with inner locks to protect the race condition when

the producer media nodes would access the suppliers in their own thread
without having any locks held, while the window could replace the suppliers.
I think since I delayed the deletion of the suppliers in the controllers, this
problem was only theoretical... but this is just more clean.


git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@25734 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Stephan Aßmus 2008-05-31 10:39:45 +00:00
parent 7bed1cb42d
commit 4aa9ff58c6
5 changed files with 24 additions and 11 deletions

View File

@ -791,17 +791,12 @@ h->start_time = 0;
"playlistFrame: %Ld\n", fFrame, playlistFrame);
bool forceOrWasCached = forceSendingBuffer;
if (fManager->LockWithTimeout(5000) == B_OK) {
// we need to lock the manager, or our
// fSupplier might work on bad data
err = fSupplier->FillBuffer(playlistFrame,
buffer->Data(), &mf, forceOrWasCached);
fManager->Unlock();
} else {
err = B_ERROR;
}
err = fSupplier->FillBuffer(playlistFrame,
buffer->Data(), &mf, forceOrWasCached);
// clean the buffer if something went wrong
if (err != B_OK) {
// TODO: should use "back value" according
// to color space!
memset(buffer->Data(), 0, h->size_used);
err = B_OK;
}

View File

@ -43,7 +43,9 @@ struct PlayingInterval {
ProxyAudioSupplier::ProxyAudioSupplier(PlaybackManager* playbackManager)
: fPlaybackManager(playbackManager)
: fSupplierLock("audio supplier lock")
, fPlaybackManager(playbackManager)
, fVideoFrameRate(25.0)
, fSupplier(NULL)
@ -98,6 +100,8 @@ ProxyAudioSupplier::GetFrames(void* buffer, int64 frameCount,
TRACE("GetFrames() - LOCKING THE PLAYBACK MANAGER TIMED OUT!!!\n");
}
BAutolock _(fSupplierLock);
// retrieve the audio data for each interval.
int64 framesRead = 0;
while (!playingIntervals.IsEmpty()) {
@ -165,6 +169,8 @@ ProxyAudioSupplier::SetFormat(const media_format& format)
TRACE("SetFormat(%s)\n", string);
#endif
BAutolock _(fSupplierLock);
fAudioResampler.SetFormat(format);
// In case SetSupplier was called before, we need
@ -199,6 +205,8 @@ ProxyAudioSupplier::SetSupplier(AudioTrackSupplier* supplier,
//videoFrameRate);
TRACE("SetSupplier(%p, %.1f)\n", supplier, videoFrameRate);
BAutolock _(fSupplierLock);
fSupplier = supplier;
fVideoFrameRate = videoFrameRate;

View File

@ -5,6 +5,7 @@
#ifndef PROXY_AUDIO_SUPPLIER_H
#define PROXY_AUDIO_SUPPLIER_H
#include <Locker.h>
#include "AudioResampler.h"
#include "AudioSupplier.h"
@ -45,6 +46,8 @@ private:
void* _SkipFrames(void* buffer, int64 frames) const;
private:
BLocker fSupplierLock;
PlaybackManager* fPlaybackManager;
float fVideoFrameRate;

View File

@ -12,7 +12,8 @@
ProxyVideoSupplier::ProxyVideoSupplier()
: fSupplier(NULL)
: fSupplierLock("video supplier lock")
, fSupplier(NULL)
{
}
@ -26,6 +27,7 @@ status_t
ProxyVideoSupplier::FillBuffer(int64 startFrame, void* buffer,
const media_format* format, bool& wasCached)
{
BAutolock _(fSupplierLock);
//printf("ProxyVideoSupplier::FillBuffer(%lld)\n", startFrame);
if (fSupplier == NULL)
return B_NO_INIT;
@ -60,6 +62,8 @@ ProxyVideoSupplier::DeleteCaches()
void
ProxyVideoSupplier::SetSupplier(VideoTrackSupplier* supplier)
{
BAutolock _(fSupplierLock);
fSupplier = supplier;
}

View File

@ -5,6 +5,7 @@
#ifndef PROXY_VIDEO_SUPPLIER_H
#define PROXY_VIDEO_SUPPLIER_H
#include <Locker.h>
#include "VideoSupplier.h"
@ -26,6 +27,8 @@ public:
void SetSupplier(VideoTrackSupplier* supplier);
private:
BLocker fSupplierLock;
VideoTrackSupplier* fSupplier;
};