зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1245216: Fix getUserMedia input in full_duplex mode coming from the wrong place r=padenot
Also cleanup of an leftover overrridden interface, and re-add a line lost in merges MozReview-Commit-ID: 7sjtbbtq1RG
This commit is contained in:
Родитель
0a6b21aecf
Коммит
85f3c6a92d
|
@ -52,7 +52,6 @@ GraphDriver::GraphDriver(MediaStreamGraphImpl* aGraphImpl)
|
||||||
mIterationEnd(0),
|
mIterationEnd(0),
|
||||||
mGraphImpl(aGraphImpl),
|
mGraphImpl(aGraphImpl),
|
||||||
mWaitState(WAITSTATE_RUNNING),
|
mWaitState(WAITSTATE_RUNNING),
|
||||||
mAudioInput(nullptr),
|
|
||||||
mCurrentTimeStamp(TimeStamp::Now()),
|
mCurrentTimeStamp(TimeStamp::Now()),
|
||||||
mPreviousDriver(nullptr),
|
mPreviousDriver(nullptr),
|
||||||
mNextDriver(nullptr)
|
mNextDriver(nullptr)
|
||||||
|
@ -546,6 +545,7 @@ StreamAndPromiseForOperation::StreamAndPromiseForOperation(MediaStream* aStream,
|
||||||
AudioCallbackDriver::AudioCallbackDriver(MediaStreamGraphImpl* aGraphImpl)
|
AudioCallbackDriver::AudioCallbackDriver(MediaStreamGraphImpl* aGraphImpl)
|
||||||
: GraphDriver(aGraphImpl)
|
: GraphDriver(aGraphImpl)
|
||||||
, mSampleRate(0)
|
, mSampleRate(0)
|
||||||
|
, mInputChannels(1)
|
||||||
, mIterationDurationMS(MEDIA_GRAPH_TARGET_PERIOD_MS)
|
, mIterationDurationMS(MEDIA_GRAPH_TARGET_PERIOD_MS)
|
||||||
, mStarted(false)
|
, mStarted(false)
|
||||||
, mAudioInput(nullptr)
|
, mAudioInput(nullptr)
|
||||||
|
@ -604,7 +604,7 @@ AudioCallbackDriver::Init()
|
||||||
}
|
}
|
||||||
|
|
||||||
input = output;
|
input = output;
|
||||||
input.channels = 1; // change to support optional stereo capture
|
input.channels = mInputChannels; // change to support optional stereo capture
|
||||||
|
|
||||||
cubeb_stream* stream;
|
cubeb_stream* stream;
|
||||||
// XXX Only pass input input if we have an input listener. Always
|
// XXX Only pass input input if we have an input listener. Always
|
||||||
|
@ -929,7 +929,7 @@ AudioCallbackDriver::DataCallback(const AudioDataValue* aInputBuffer,
|
||||||
if (mAudioInput) { // for this specific input-only or full-duplex stream
|
if (mAudioInput) { // for this specific input-only or full-duplex stream
|
||||||
mAudioInput->NotifyInputData(mGraphImpl, aInputBuffer,
|
mAudioInput->NotifyInputData(mGraphImpl, aInputBuffer,
|
||||||
static_cast<size_t>(aFrames),
|
static_cast<size_t>(aFrames),
|
||||||
mSampleRate, ChannelCount);
|
mSampleRate, mInputChannels);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -197,15 +197,6 @@ public:
|
||||||
|
|
||||||
virtual bool OnThread() = 0;
|
virtual bool OnThread() = 0;
|
||||||
|
|
||||||
// These are invoked on the MSG thread (or MainThread in shutdown)
|
|
||||||
virtual void SetInputListener(AudioDataListener *aListener) {
|
|
||||||
mAudioInput = aListener;
|
|
||||||
}
|
|
||||||
// XXX do we need the param? probably no
|
|
||||||
virtual void RemoveInputListener(AudioDataListener *aListener) {
|
|
||||||
mAudioInput = nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
GraphTime StateComputedTime() const;
|
GraphTime StateComputedTime() const;
|
||||||
|
|
||||||
|
@ -236,9 +227,6 @@ protected:
|
||||||
// This must be access with the monitor.
|
// This must be access with the monitor.
|
||||||
WaitState mWaitState;
|
WaitState mWaitState;
|
||||||
|
|
||||||
// Callback for mic data, if any
|
|
||||||
AudioDataListener *mAudioInput;
|
|
||||||
|
|
||||||
// This is used on the main thread (during initialization), and the graph
|
// This is used on the main thread (during initialization), and the graph
|
||||||
// thread. No monitor needed because we know the graph thread does not run
|
// thread. No monitor needed because we know the graph thread does not run
|
||||||
// during the initialization.
|
// during the initialization.
|
||||||
|
@ -421,6 +409,17 @@ public:
|
||||||
uint32_t aFrames,
|
uint32_t aFrames,
|
||||||
uint32_t aSampleRate) override;
|
uint32_t aSampleRate) override;
|
||||||
|
|
||||||
|
// These are invoked on the MSG thread (we don't call this if not LIFECYCLE_RUNNING)
|
||||||
|
virtual void SetInputListener(AudioDataListener *aListener) {
|
||||||
|
MOZ_ASSERT(OnThread());
|
||||||
|
mAudioInput = aListener;
|
||||||
|
}
|
||||||
|
// XXX do we need the param? probably no
|
||||||
|
virtual void RemoveInputListener(AudioDataListener *aListener) {
|
||||||
|
MOZ_ASSERT(OnThread());
|
||||||
|
mAudioInput = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
AudioCallbackDriver* AsAudioCallbackDriver() override {
|
AudioCallbackDriver* AsAudioCallbackDriver() override {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
@ -486,6 +485,9 @@ private:
|
||||||
/* The sample rate for the aforementionned cubeb stream. This is set on
|
/* The sample rate for the aforementionned cubeb stream. This is set on
|
||||||
* initialization and can be read safely afterwards. */
|
* initialization and can be read safely afterwards. */
|
||||||
uint32_t mSampleRate;
|
uint32_t mSampleRate;
|
||||||
|
/* The number of input channels from cubeb. Should be set before opening cubeb
|
||||||
|
* and then be static. */
|
||||||
|
uint32_t mInputChannels;
|
||||||
/* Approximation of the time between two callbacks. This is used to schedule
|
/* Approximation of the time between two callbacks. This is used to schedule
|
||||||
* video frames. This is in milliseconds. Only even used (after
|
* video frames. This is in milliseconds. Only even used (after
|
||||||
* inizatialization) on the audio callback thread. */
|
* inizatialization) on the audio callback thread. */
|
||||||
|
|
|
@ -955,6 +955,7 @@ MediaStreamGraphImpl::OpenAudioInputImpl(CubebUtils::AudioDeviceID aID,
|
||||||
MonitorAutoLock mon(mMonitor);
|
MonitorAutoLock mon(mMonitor);
|
||||||
if (mLifecycleState == LIFECYCLE_RUNNING) {
|
if (mLifecycleState == LIFECYCLE_RUNNING) {
|
||||||
AudioCallbackDriver* driver = new AudioCallbackDriver(this);
|
AudioCallbackDriver* driver = new AudioCallbackDriver(this);
|
||||||
|
driver->SetInputListener(aListener);
|
||||||
CurrentDriver()->SwitchAtNextIteration(driver);
|
CurrentDriver()->SwitchAtNextIteration(driver);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -994,7 +995,10 @@ MediaStreamGraphImpl::CloseAudioInputImpl(AudioDataListener *aListener)
|
||||||
{
|
{
|
||||||
mInputDeviceID = nullptr;
|
mInputDeviceID = nullptr;
|
||||||
mInputWanted = false;
|
mInputWanted = false;
|
||||||
CurrentDriver()->RemoveInputListener(aListener);
|
AudioCallbackDriver *driver = CurrentDriver()->AsAudioCallbackDriver();
|
||||||
|
if (driver) {
|
||||||
|
driver->RemoveInputListener(aListener);
|
||||||
|
}
|
||||||
mAudioInputs.RemoveElement(aListener);
|
mAudioInputs.RemoveElement(aListener);
|
||||||
|
|
||||||
// Switch Drivers since we're adding or removing an input (to nothing/system or output only)
|
// Switch Drivers since we're adding or removing an input (to nothing/system or output only)
|
||||||
|
|
|
@ -375,6 +375,10 @@ MediaEngineWebRTCMicrophoneSource::Start(SourceMediaStream *aStream,
|
||||||
if (mVoEBase->StartReceive(mChannel)) {
|
if (mVoEBase->StartReceive(mChannel)) {
|
||||||
return NS_ERROR_FAILURE;
|
return NS_ERROR_FAILURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Must be *before* StartSend() so it will notice we selected external input (full_duplex)
|
||||||
|
mAudioInput->StartRecording(aStream->Graph(), mListener);
|
||||||
|
|
||||||
if (mVoEBase->StartSend(mChannel)) {
|
if (mVoEBase->StartSend(mChannel)) {
|
||||||
return NS_ERROR_FAILURE;
|
return NS_ERROR_FAILURE;
|
||||||
}
|
}
|
||||||
|
@ -382,8 +386,6 @@ MediaEngineWebRTCMicrophoneSource::Start(SourceMediaStream *aStream,
|
||||||
// Attach external media processor, so this::Process will be called.
|
// Attach external media processor, so this::Process will be called.
|
||||||
mVoERender->RegisterExternalMediaProcessing(mChannel, webrtc::kRecordingPerChannel, *this);
|
mVoERender->RegisterExternalMediaProcessing(mChannel, webrtc::kRecordingPerChannel, *this);
|
||||||
|
|
||||||
mAudioInput->StartRecording(aStream->Graph(), mListener);
|
|
||||||
|
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Загрузка…
Ссылка в новой задаче