firefox/SOURCES/005-firefox-always-register-video-input-feedback-for-newly-created-deviceinfo.patch
2025-01-09 11:48:53 +00:00

294 lines
12 KiB
Diff

From df57b21200c7cde7ac34705e8fceab2fbe933bc5 Mon Sep 17 00:00:00 2001
From: Jan Grulich <jgrulich@redhat.com>
Date: Tue, 3 Sep 2024 07:56:39 +0000
Subject: [PATCH] Bug 1912778 - Always register video input feedback for newly
created DeviceInfo r=pehrsons
Make sure to always register video input feedback when a new DeviceInfo
is created. We always destroy DeviceInfo once request to camera access
is resolved, making it to be created again, but this time skipping the
part where video input feedback is registered as we use already existing
VideoEngine. There is now just one place where DeviceInfo gets created
and the logic for video input feedback registration has been moved to
VideoEngine as it's the only place where we know when new DeviceInfo is
created.
Differential Revision: https://phabricator.services.mozilla.com/D219060
---
dom/media/systemservices/CamerasParent.cpp | 164 ++++++++++-----------
dom/media/systemservices/CamerasParent.h | 5 +
dom/media/systemservices/VideoEngine.cpp | 7 +-
dom/media/systemservices/VideoEngine.h | 2 +-
4 files changed, 91 insertions(+), 87 deletions(-)
diff --git a/dom/media/systemservices/CamerasParent.cpp b/dom/media/systemservices/CamerasParent.cpp
index 048d07b7fa..d6fe5986da 100644
--- a/dom/media/systemservices/CamerasParent.cpp
+++ b/dom/media/systemservices/CamerasParent.cpp
@@ -405,15 +405,25 @@ void CamerasParent::CloseEngines() {
Unused << ReleaseCapture(capEngine, streamNum);
}
- if (VideoEngine* engine = mEngines->ElementAt(CameraEngine); engine) {
- auto device_info = engine->GetOrCreateVideoCaptureDeviceInfo();
- MOZ_ASSERT(device_info);
- if (device_info) {
- device_info->DeRegisterVideoInputFeedBack(this);
- }
+ auto device_info = GetDeviceInfo(CameraEngine);
+ MOZ_ASSERT(device_info);
+ if (device_info) {
+ device_info->DeRegisterVideoInputFeedBack(this);
}
}
+std::shared_ptr<webrtc::VideoCaptureModule::DeviceInfo>
+CamerasParent::GetDeviceInfo(int aEngine) {
+ MOZ_ASSERT(mVideoCaptureThread->IsOnCurrentThread());
+ LOG_VERBOSE("CamerasParent(%p)::%s", this, __func__);
+
+ auto* engine = EnsureInitialized(aEngine);
+ if (!engine) {
+ return nullptr;
+ }
+ return engine->GetOrCreateVideoCaptureDeviceInfo(this);
+}
+
VideoEngine* CamerasParent::EnsureInitialized(int aEngine) {
MOZ_ASSERT(mVideoCaptureThread->IsOnCurrentThread());
LOG_VERBOSE("CamerasParent(%p)::%s", this, __func__);
@@ -449,14 +459,6 @@ VideoEngine* CamerasParent::EnsureInitialized(int aEngine) {
return nullptr;
}
- if (capEngine == CameraEngine) {
- auto device_info = engine->GetOrCreateVideoCaptureDeviceInfo();
- MOZ_ASSERT(device_info);
- if (device_info) {
- device_info->RegisterVideoInputFeedBack(this);
- }
- }
-
return mEngines->ElementAt(capEngine) = std::move(engine);
}
@@ -474,19 +476,16 @@ ipc::IPCResult CamerasParent::RecvNumberOfCaptureDevices(
LOG("CaptureEngine=%d", aCapEngine);
using Promise = MozPromise<int, bool, true>;
- InvokeAsync(
- mVideoCaptureThread, __func__,
- [this, self = RefPtr(this), aCapEngine] {
- int num = -1;
- if (auto* engine = EnsureInitialized(aCapEngine)) {
- if (auto devInfo = engine->GetOrCreateVideoCaptureDeviceInfo()) {
- num = static_cast<int>(devInfo->NumberOfDevices());
- }
- }
+ InvokeAsync(mVideoCaptureThread, __func__,
+ [this, self = RefPtr(this), aCapEngine] {
+ int num = -1;
+ if (auto devInfo = GetDeviceInfo(aCapEngine)) {
+ num = static_cast<int>(devInfo->NumberOfDevices());
+ }
- return Promise::CreateAndResolve(
- num, "CamerasParent::RecvNumberOfCaptureDevices");
- })
+ return Promise::CreateAndResolve(
+ num, "CamerasParent::RecvNumberOfCaptureDevices");
+ })
->Then(
mPBackgroundEventTarget, __func__,
[this, self = RefPtr(this)](Promise::ResolveOrRejectValue&& aValue) {
@@ -558,10 +557,8 @@ ipc::IPCResult CamerasParent::RecvNumberOfCapabilities(
mVideoCaptureThread, __func__,
[this, self = RefPtr(this), id = nsCString(aUniqueId), aCapEngine]() {
int num = -1;
- if (auto* engine = EnsureInitialized(aCapEngine)) {
- if (auto devInfo = engine->GetOrCreateVideoCaptureDeviceInfo()) {
- num = devInfo->NumberOfCapabilities(id.get());
- }
+ if (auto devInfo = GetDeviceInfo(aCapEngine)) {
+ num = devInfo->NumberOfCapabilities(id.get());
}
return Promise::CreateAndResolve(
num, "CamerasParent::RecvNumberOfCapabilities");
@@ -599,36 +596,34 @@ ipc::IPCResult CamerasParent::RecvGetCaptureCapability(
aIndex);
using Promise = MozPromise<webrtc::VideoCaptureCapability, int, true>;
- InvokeAsync(
- mVideoCaptureThread, __func__,
- [this, self = RefPtr(this), id = nsCString(aUniqueId), aCapEngine,
- aIndex] {
- webrtc::VideoCaptureCapability webrtcCaps;
- int error = -1;
- if (auto* engine = EnsureInitialized(aCapEngine)) {
- if (auto devInfo = engine->GetOrCreateVideoCaptureDeviceInfo()) {
- error = devInfo->GetCapability(id.get(), aIndex, webrtcCaps);
- }
- }
+ InvokeAsync(mVideoCaptureThread, __func__,
+ [this, self = RefPtr(this), id = nsCString(aUniqueId), aCapEngine,
+ aIndex] {
+ webrtc::VideoCaptureCapability webrtcCaps;
+ int error = -1;
+ if (auto devInfo = GetDeviceInfo(aCapEngine)) {
+ error = devInfo->GetCapability(id.get(), aIndex, webrtcCaps);
+ }
- if (!error && aCapEngine == CameraEngine) {
- auto iter = mAllCandidateCapabilities.find(id);
- if (iter == mAllCandidateCapabilities.end()) {
- std::map<uint32_t, webrtc::VideoCaptureCapability>
- candidateCapabilities;
- candidateCapabilities.emplace(aIndex, webrtcCaps);
- mAllCandidateCapabilities.emplace(id, candidateCapabilities);
- } else {
- (iter->second).emplace(aIndex, webrtcCaps);
- }
- }
- if (error) {
- return Promise::CreateAndReject(
- error, "CamerasParent::RecvGetCaptureCapability");
- }
- return Promise::CreateAndResolve(
- webrtcCaps, "CamerasParent::RecvGetCaptureCapability");
- })
+ if (!error && aCapEngine == CameraEngine) {
+ auto iter = mAllCandidateCapabilities.find(id);
+ if (iter == mAllCandidateCapabilities.end()) {
+ std::map<uint32_t, webrtc::VideoCaptureCapability>
+ candidateCapabilities;
+ candidateCapabilities.emplace(aIndex, webrtcCaps);
+ mAllCandidateCapabilities.emplace(id,
+ candidateCapabilities);
+ } else {
+ (iter->second).emplace(aIndex, webrtcCaps);
+ }
+ }
+ if (error) {
+ return Promise::CreateAndReject(
+ error, "CamerasParent::RecvGetCaptureCapability");
+ }
+ return Promise::CreateAndResolve(
+ webrtcCaps, "CamerasParent::RecvGetCaptureCapability");
+ })
->Then(
mPBackgroundEventTarget, __func__,
[this, self = RefPtr(this)](Promise::ResolveOrRejectValue&& aValue) {
@@ -664,33 +659,32 @@ ipc::IPCResult CamerasParent::RecvGetCaptureDevice(
using Data = std::tuple<nsCString, nsCString, pid_t, bool, int>;
using Promise = MozPromise<Data, bool, true>;
- InvokeAsync(
- mVideoCaptureThread, __func__,
- [this, self = RefPtr(this), aCapEngine, aDeviceIndex] {
- char deviceName[MediaEngineSource::kMaxDeviceNameLength];
- char deviceUniqueId[MediaEngineSource::kMaxUniqueIdLength];
- nsCString name;
- nsCString uniqueId;
- pid_t devicePid = 0;
- bool placeholder = false;
- int error = -1;
- if (auto* engine = EnsureInitialized(aCapEngine)) {
- if (auto devInfo = engine->GetOrCreateVideoCaptureDeviceInfo()) {
- error = devInfo->GetDeviceName(
- aDeviceIndex, deviceName, sizeof(deviceName), deviceUniqueId,
- sizeof(deviceUniqueId), nullptr, 0, &devicePid, &placeholder);
- }
- }
- if (error == 0) {
- name.Assign(deviceName);
- uniqueId.Assign(deviceUniqueId);
- }
+ InvokeAsync(mVideoCaptureThread, __func__,
+ [this, self = RefPtr(this), aCapEngine, aDeviceIndex] {
+ char deviceName[MediaEngineSource::kMaxDeviceNameLength];
+ char deviceUniqueId[MediaEngineSource::kMaxUniqueIdLength];
+ nsCString name;
+ nsCString uniqueId;
+ pid_t devicePid = 0;
+ bool placeholder = false;
+ int error = -1;
+ if (auto devInfo = GetDeviceInfo(aCapEngine)) {
+ error = devInfo->GetDeviceName(
+ aDeviceIndex, deviceName, sizeof(deviceName),
+ deviceUniqueId, sizeof(deviceUniqueId), nullptr, 0,
+ &devicePid, &placeholder);
+ }
- return Promise::CreateAndResolve(
- std::make_tuple(std::move(name), std::move(uniqueId), devicePid,
- placeholder, error),
- "CamerasParent::RecvGetCaptureDevice");
- })
+ if (error == 0) {
+ name.Assign(deviceName);
+ uniqueId.Assign(deviceUniqueId);
+ }
+
+ return Promise::CreateAndResolve(
+ std::make_tuple(std::move(name), std::move(uniqueId),
+ devicePid, placeholder, error),
+ "CamerasParent::RecvGetCaptureDevice");
+ })
->Then(
mPBackgroundEventTarget, __func__,
[this, self = RefPtr(this)](Promise::ResolveOrRejectValue&& aValue) {
diff --git a/dom/media/systemservices/CamerasParent.h b/dom/media/systemservices/CamerasParent.h
index 9d6a6f2f35..11a5229629 100644
--- a/dom/media/systemservices/CamerasParent.h
+++ b/dom/media/systemservices/CamerasParent.h
@@ -144,6 +144,11 @@ class CamerasParent final : public PCamerasParent,
// VideoInputFeedBack
void OnDeviceChange() override;
+ // Creates a new DeviceInfo or returns an existing DeviceInfo for given
+ // capture engine. Returns a nullptr in case capture engine failed to be
+ // initialized. Video capture thread only.
+ std::shared_ptr<webrtc::VideoCaptureModule::DeviceInfo> GetDeviceInfo(
+ int aEngine);
VideoEngine* EnsureInitialized(int aEngine);
// Stops any ongoing capturing and releases resources. Called on
diff --git a/dom/media/systemservices/VideoEngine.cpp b/dom/media/systemservices/VideoEngine.cpp
index d03149e3ac..ec4657d755 100644
--- a/dom/media/systemservices/VideoEngine.cpp
+++ b/dom/media/systemservices/VideoEngine.cpp
@@ -112,7 +112,8 @@ int VideoEngine::ReleaseVideoCapture(const int32_t aId) {
}
std::shared_ptr<webrtc::VideoCaptureModule::DeviceInfo>
-VideoEngine::GetOrCreateVideoCaptureDeviceInfo() {
+VideoEngine::GetOrCreateVideoCaptureDeviceInfo(
+ webrtc::VideoInputFeedBack* callBack) {
LOG(("%s", __PRETTY_FUNCTION__));
webrtc::Timestamp currentTime = webrtc::Timestamp::Micros(0);
@@ -157,6 +158,10 @@ VideoEngine::GetOrCreateVideoCaptureDeviceInfo() {
mDeviceInfo =
mVideoCaptureFactory->CreateDeviceInfo(mId, mCaptureDevInfo.type);
+ if (mDeviceInfo && mCaptureDevInfo.type == CaptureDeviceType::Camera) {
+ mDeviceInfo->RegisterVideoInputFeedBack(callBack);
+ }
+
LOG(("EXIT %s", __PRETTY_FUNCTION__));
return mDeviceInfo;
}
diff --git a/dom/media/systemservices/VideoEngine.h b/dom/media/systemservices/VideoEngine.h
index 588be92c27..289a1ab181 100644
--- a/dom/media/systemservices/VideoEngine.h
+++ b/dom/media/systemservices/VideoEngine.h
@@ -88,7 +88,7 @@ class VideoEngine {
* @see bug 1305212 https://bugzilla.mozilla.org/show_bug.cgi?id=1305212
*/
std::shared_ptr<webrtc::VideoCaptureModule::DeviceInfo>
- GetOrCreateVideoCaptureDeviceInfo();
+ GetOrCreateVideoCaptureDeviceInfo(webrtc::VideoInputFeedBack* callBack);
/**
* Destroys existing DeviceInfo.