зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1672072 - P9. Make EnsureRDDProcessAndCreateBridge an async API. r=mattwoodrow,bryce,mjf,padenot,ipc-reviewers,mccr8
We can now chaincreation of the decoder to the launch of the RDD process as needed and setting up the PRemoteDecoderManager Differential Revision: https://phabricator.services.mozilla.com/D96365
This commit is contained in:
Родитель
7a6315ba80
Коммит
8ffdd4eaef
|
@ -26,8 +26,9 @@ using namespace layers;
|
||||||
using namespace gfx;
|
using namespace gfx;
|
||||||
|
|
||||||
// Used so that we only ever attempt to check if the RDD process should be
|
// Used so that we only ever attempt to check if the RDD process should be
|
||||||
// launched serially.
|
// launched serially. Protects sLaunchPromise
|
||||||
StaticMutex sLaunchMutex;
|
StaticMutex sLaunchMutex;
|
||||||
|
static StaticRefPtr<GenericNonExclusivePromise> sLaunchRDDPromise;
|
||||||
|
|
||||||
// Only modified on the main-thread, read on any thread. While it could be read
|
// Only modified on the main-thread, read on any thread. While it could be read
|
||||||
// on the main thread directly, for clarity we force access via the DataMutex
|
// on the main thread directly, for clarity we force access via the DataMutex
|
||||||
|
@ -202,9 +203,9 @@ RemoteDecoderManagerChild::CreateAudioDecoder(
|
||||||
return PlatformDecoderModule::CreateDecoderPromise::CreateAndReject(
|
return PlatformDecoderModule::CreateDecoderPromise::CreateAndReject(
|
||||||
NS_ERROR_DOM_MEDIA_CANCELED, __func__);
|
NS_ERROR_DOM_MEDIA_CANCELED, __func__);
|
||||||
}
|
}
|
||||||
return InvokeAsync(
|
return LaunchRDDProcessIfNeeded()->Then(
|
||||||
managerThread, __func__,
|
managerThread, __func__,
|
||||||
[params = CreateDecoderParamsForAsync(aParams)]() {
|
[params = CreateDecoderParamsForAsync(aParams)](bool) {
|
||||||
auto child = MakeRefPtr<RemoteAudioDecoderChild>();
|
auto child = MakeRefPtr<RemoteAudioDecoderChild>();
|
||||||
MediaResult result =
|
MediaResult result =
|
||||||
child->InitIPDL(params.AudioConfig(), params.mOptions);
|
child->InitIPDL(params.AudioConfig(), params.mOptions);
|
||||||
|
@ -213,6 +214,10 @@ RemoteDecoderManagerChild::CreateAudioDecoder(
|
||||||
result, __func__);
|
result, __func__);
|
||||||
}
|
}
|
||||||
return Construct(std::move(child));
|
return Construct(std::move(child));
|
||||||
|
},
|
||||||
|
[](nsresult aResult) {
|
||||||
|
return PlatformDecoderModule::CreateDecoderPromise::CreateAndReject(
|
||||||
|
MediaResult(aResult, "Couldn't start RDD process"), __func__);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -235,10 +240,15 @@ RemoteDecoderManagerChild::CreateVideoDecoder(
|
||||||
}
|
}
|
||||||
|
|
||||||
MOZ_ASSERT(aLocation != RemoteDecodeIn::Unspecified);
|
MOZ_ASSERT(aLocation != RemoteDecodeIn::Unspecified);
|
||||||
return InvokeAsync(
|
|
||||||
|
RefPtr<GenericNonExclusivePromise> p =
|
||||||
|
aLocation == RemoteDecodeIn::GpuProcess
|
||||||
|
? GenericNonExclusivePromise::CreateAndResolve(true, __func__)
|
||||||
|
: LaunchRDDProcessIfNeeded();
|
||||||
|
|
||||||
|
return p->Then(
|
||||||
managerThread, __func__,
|
managerThread, __func__,
|
||||||
[aLocation, params = CreateDecoderParamsForAsync(aParams)]()
|
[aLocation, params = CreateDecoderParamsForAsync(aParams)](bool) {
|
||||||
-> RefPtr<PlatformDecoderModule::CreateDecoderPromise> {
|
|
||||||
auto child = MakeRefPtr<RemoteVideoDecoderChild>(aLocation);
|
auto child = MakeRefPtr<RemoteVideoDecoderChild>(aLocation);
|
||||||
MediaResult result = child->InitIPDL(
|
MediaResult result = child->InitIPDL(
|
||||||
params.VideoConfig(), params.mRate.mValue, params.mOptions,
|
params.VideoConfig(), params.mRate.mValue, params.mOptions,
|
||||||
|
@ -250,6 +260,10 @@ RemoteDecoderManagerChild::CreateVideoDecoder(
|
||||||
result, __func__);
|
result, __func__);
|
||||||
}
|
}
|
||||||
return Construct(std::move(child));
|
return Construct(std::move(child));
|
||||||
|
},
|
||||||
|
[](nsresult aResult) {
|
||||||
|
return PlatformDecoderModule::CreateDecoderPromise::CreateAndReject(
|
||||||
|
MediaResult(aResult, "Couldn't start RDD process"), __func__);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -287,24 +301,24 @@ RemoteDecoderManagerChild::Construct(RefPtr<RemoteDecoderChild>&& aChild) {
|
||||||
}
|
}
|
||||||
|
|
||||||
/* static */
|
/* static */
|
||||||
void RemoteDecoderManagerChild::LaunchRDDProcessIfNeeded(
|
RefPtr<GenericNonExclusivePromise>
|
||||||
RemoteDecodeIn aLocation) {
|
RemoteDecoderManagerChild::LaunchRDDProcessIfNeeded() {
|
||||||
MOZ_DIAGNOSTIC_ASSERT(XRE_IsContentProcess(),
|
MOZ_DIAGNOSTIC_ASSERT(XRE_IsContentProcess(),
|
||||||
"Only supported from a content process.");
|
"Only supported from a content process.");
|
||||||
|
|
||||||
if (aLocation != RemoteDecodeIn::RddProcess) {
|
|
||||||
// Not targeting RDD process? No need to launch RDD.
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
nsCOMPtr<nsISerialEventTarget> managerThread = GetManagerThread();
|
nsCOMPtr<nsISerialEventTarget> managerThread = GetManagerThread();
|
||||||
if (!managerThread) {
|
if (!managerThread) {
|
||||||
// We got shutdown.
|
// We got shutdown.
|
||||||
return;
|
return GenericNonExclusivePromise::CreateAndReject(NS_ERROR_FAILURE,
|
||||||
|
__func__);
|
||||||
}
|
}
|
||||||
|
|
||||||
StaticMutexAutoLock lock(sLaunchMutex);
|
StaticMutexAutoLock lock(sLaunchMutex);
|
||||||
|
|
||||||
|
if (sLaunchRDDPromise) {
|
||||||
|
return sLaunchRDDPromise;
|
||||||
|
}
|
||||||
|
|
||||||
// We have a couple possible states here. We are in a content process
|
// We have a couple possible states here. We are in a content process
|
||||||
// and:
|
// and:
|
||||||
// 1) the RDD process has never been launched. RDD should be launched
|
// 1) the RDD process has never been launched. RDD should be launched
|
||||||
|
@ -319,33 +333,51 @@ void RemoteDecoderManagerChild::LaunchRDDProcessIfNeeded(
|
||||||
// LaunchRDDProcess which will launch RDD if necessary, and setup the
|
// LaunchRDDProcess which will launch RDD if necessary, and setup the
|
||||||
// IPC connections between *this* content process and the RDD process.
|
// IPC connections between *this* content process and the RDD process.
|
||||||
|
|
||||||
bool needsLaunch = true;
|
RefPtr<GenericNonExclusivePromise> p = InvokeAsync(
|
||||||
RefPtr<Runnable> task = NS_NewRunnableFunction(
|
managerThread, __func__, []() -> RefPtr<GenericNonExclusivePromise> {
|
||||||
"RemoteDecoderManagerChild::LaunchRDDProcessIfNeeded-CheckSend", [&]() {
|
|
||||||
auto* rps = GetSingleton(RemoteDecodeIn::RddProcess);
|
auto* rps = GetSingleton(RemoteDecodeIn::RddProcess);
|
||||||
needsLaunch = rps ? !rps->CanSend() : true;
|
if (rps && rps->CanSend()) {
|
||||||
});
|
return GenericNonExclusivePromise::CreateAndResolve(true, __func__);
|
||||||
if (NS_FAILED(SyncRunnable::DispatchToThread(managerThread, task))) {
|
}
|
||||||
return;
|
nsCOMPtr<nsISerialEventTarget> managerThread = GetManagerThread();
|
||||||
};
|
ipc::PBackgroundChild* bgActor =
|
||||||
|
ipc::BackgroundChild::GetForCurrentThread();
|
||||||
|
if (!managerThread || NS_WARN_IF(!bgActor)) {
|
||||||
|
return GenericNonExclusivePromise::CreateAndReject(NS_ERROR_FAILURE,
|
||||||
|
__func__);
|
||||||
|
}
|
||||||
|
|
||||||
if (needsLaunch) {
|
return bgActor->SendEnsureRDDProcessAndCreateBridge()->Then(
|
||||||
managerThread->Dispatch(NS_NewRunnableFunction(
|
managerThread, __func__,
|
||||||
"RemoteDecoderManagerChild::EnsureRDDProcessAndCreateBridge", [&]() {
|
[](ipc::PBackgroundChild::EnsureRDDProcessAndCreateBridgePromise::
|
||||||
ipc::PBackgroundChild* bgActor =
|
ResolveOrRejectValue&& aResult) {
|
||||||
ipc::BackgroundChild::GetForCurrentThread();
|
nsCOMPtr<nsISerialEventTarget> managerThread = GetManagerThread();
|
||||||
if (NS_WARN_IF(!bgActor)) {
|
if (!managerThread || aResult.IsReject()) {
|
||||||
return;
|
// The parent process died or we got shutdown
|
||||||
}
|
return GenericNonExclusivePromise::CreateAndReject(
|
||||||
nsresult rv;
|
NS_ERROR_FAILURE, __func__);
|
||||||
Endpoint<PRemoteDecoderManagerChild> endpoint;
|
}
|
||||||
Unused << bgActor->SendEnsureRDDProcessAndCreateBridge(&rv,
|
nsresult rv = Get<0>(aResult.ResolveValue());
|
||||||
&endpoint);
|
if (NS_FAILED(rv)) {
|
||||||
if (NS_SUCCEEDED(rv)) {
|
return GenericNonExclusivePromise::CreateAndReject(rv,
|
||||||
OpenForRDDProcess(std::move(endpoint));
|
__func__);
|
||||||
}
|
}
|
||||||
}));
|
OpenForRDDProcess(Get<1>(std::move(aResult.ResolveValue())));
|
||||||
}
|
return GenericNonExclusivePromise::CreateAndResolve(true,
|
||||||
|
__func__);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
p = p->Then(
|
||||||
|
GetCurrentSerialEventTarget(), __func__,
|
||||||
|
[](const GenericNonExclusivePromise::ResolveOrRejectValue& aResult) {
|
||||||
|
StaticMutexAutoLock lock(sLaunchMutex);
|
||||||
|
sLaunchRDDPromise = nullptr;
|
||||||
|
return GenericNonExclusivePromise::CreateAndResolveOrReject(aResult,
|
||||||
|
__func__);
|
||||||
|
});
|
||||||
|
sLaunchRDDPromise = p;
|
||||||
|
return sLaunchRDDPromise;
|
||||||
}
|
}
|
||||||
|
|
||||||
PRemoteDecoderChild* RemoteDecoderManagerChild::AllocPRemoteDecoderChild(
|
PRemoteDecoderChild* RemoteDecoderManagerChild::AllocPRemoteDecoderChild(
|
||||||
|
|
|
@ -44,7 +44,6 @@ class RemoteDecoderManagerChild final
|
||||||
|
|
||||||
// Can be called from any thread.
|
// Can be called from any thread.
|
||||||
static nsISerialEventTarget* GetManagerThread();
|
static nsISerialEventTarget* GetManagerThread();
|
||||||
static void LaunchRDDProcessIfNeeded(RemoteDecodeIn aLocation);
|
|
||||||
|
|
||||||
// Can be called from any thread, dispatches the request to the IPDL thread
|
// Can be called from any thread, dispatches the request to the IPDL thread
|
||||||
// internally and will be ignored if the IPDL actor has been destroyed.
|
// internally and will be ignored if the IPDL actor has been destroyed.
|
||||||
|
@ -106,6 +105,7 @@ class RemoteDecoderManagerChild final
|
||||||
Endpoint<PRemoteDecoderManagerChild>&& aEndpoint);
|
Endpoint<PRemoteDecoderManagerChild>&& aEndpoint);
|
||||||
static void OpenForGPUProcess(
|
static void OpenForGPUProcess(
|
||||||
Endpoint<PRemoteDecoderManagerChild>&& aEndpoint);
|
Endpoint<PRemoteDecoderManagerChild>&& aEndpoint);
|
||||||
|
static RefPtr<GenericNonExclusivePromise> LaunchRDDProcessIfNeeded();
|
||||||
|
|
||||||
RefPtr<RemoteDecoderManagerChild> mIPDLSelfRef;
|
RefPtr<RemoteDecoderManagerChild> mIPDLSelfRef;
|
||||||
// The location for decoding, Rdd or Gpu process.
|
// The location for decoding, Rdd or Gpu process.
|
||||||
|
|
|
@ -5,11 +5,6 @@
|
||||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||||
#include "RemoteDecoderModule.h"
|
#include "RemoteDecoderModule.h"
|
||||||
|
|
||||||
#include "mozilla/StaticPrefs_media.h"
|
|
||||||
#include "mozilla/SyncRunnable.h"
|
|
||||||
#include "mozilla/dom/ContentChild.h" // for launching RDD w/ ContentChild
|
|
||||||
#include "mozilla/layers/SynchronousTask.h"
|
|
||||||
|
|
||||||
#ifdef MOZ_AV1
|
#ifdef MOZ_AV1
|
||||||
# include "AOMDecoder.h"
|
# include "AOMDecoder.h"
|
||||||
#endif
|
#endif
|
||||||
|
@ -63,8 +58,6 @@ bool RemoteDecoderModule::Supports(
|
||||||
|
|
||||||
RefPtr<RemoteDecoderModule::CreateDecoderPromise>
|
RefPtr<RemoteDecoderModule::CreateDecoderPromise>
|
||||||
RemoteDecoderModule::AsyncCreateDecoder(const CreateDecoderParams& aParams) {
|
RemoteDecoderModule::AsyncCreateDecoder(const CreateDecoderParams& aParams) {
|
||||||
RemoteDecoderManagerChild::LaunchRDDProcessIfNeeded(mLocation);
|
|
||||||
|
|
||||||
if (aParams.mConfig.IsAudio()) {
|
if (aParams.mConfig.IsAudio()) {
|
||||||
// OpusDataDecoder will check this option to provide the same info
|
// OpusDataDecoder will check this option to provide the same info
|
||||||
// that IsDefaultPlaybackDeviceMono provides. We want to avoid calls
|
// that IsDefaultPlaybackDeviceMono provides. We want to avoid calls
|
||||||
|
|
|
@ -1314,13 +1314,16 @@ mozilla::ipc::IPCResult BackgroundParentImpl::RecvPEndpointForReportConstructor(
|
||||||
|
|
||||||
mozilla::ipc::IPCResult
|
mozilla::ipc::IPCResult
|
||||||
BackgroundParentImpl::RecvEnsureRDDProcessAndCreateBridge(
|
BackgroundParentImpl::RecvEnsureRDDProcessAndCreateBridge(
|
||||||
nsresult* aRv, Endpoint<PRemoteDecoderManagerChild>* aEndpoint) {
|
EnsureRDDProcessAndCreateBridgeResolver&& aResolver) {
|
||||||
RDDProcessManager* rdd = RDDProcessManager::Get();
|
RDDProcessManager* rdd = RDDProcessManager::Get();
|
||||||
if (rdd && rdd->EnsureRDDProcessAndCreateBridge(OtherPid(), aEndpoint)) {
|
Endpoint<PRemoteDecoderManagerChild> endpoint;
|
||||||
*aRv = NS_OK;
|
nsresult rv =
|
||||||
} else {
|
rdd && rdd->EnsureRDDProcessAndCreateBridge(OtherPid(), &endpoint)
|
||||||
*aRv = NS_ERROR_NOT_AVAILABLE;
|
? NS_OK
|
||||||
}
|
: NS_ERROR_NOT_AVAILABLE;
|
||||||
|
aResolver(
|
||||||
|
Tuple<const nsresult&, Endpoint<mozilla::PRemoteDecoderManagerChild>&&>(
|
||||||
|
rv, std::move(endpoint)));
|
||||||
|
|
||||||
return IPC_OK();
|
return IPC_OK();
|
||||||
}
|
}
|
||||||
|
|
|
@ -392,7 +392,7 @@ class BackgroundParentImpl : public PBackgroundParent,
|
||||||
const PrincipalInfo& aPrincipalInfo) override;
|
const PrincipalInfo& aPrincipalInfo) override;
|
||||||
|
|
||||||
mozilla::ipc::IPCResult RecvEnsureRDDProcessAndCreateBridge(
|
mozilla::ipc::IPCResult RecvEnsureRDDProcessAndCreateBridge(
|
||||||
nsresult* aRv, Endpoint<PRemoteDecoderManagerChild>* aEndpoint) override;
|
EnsureRDDProcessAndCreateBridgeResolver&& aResolver) override;
|
||||||
|
|
||||||
bool DeallocPEndpointForReportParent(
|
bool DeallocPEndpointForReportParent(
|
||||||
PEndpointForReportParent* aActor) override;
|
PEndpointForReportParent* aActor) override;
|
||||||
|
|
|
@ -263,8 +263,7 @@ parent:
|
||||||
uint32_t aProviderFlags,
|
uint32_t aProviderFlags,
|
||||||
uint32_t aCertVerifierFlags);
|
uint32_t aCertVerifierFlags);
|
||||||
|
|
||||||
// See Bug 1518344 - Investigate using async for PBackground::EnsureRDDProcessAndCreateBridge
|
async EnsureRDDProcessAndCreateBridge()
|
||||||
sync EnsureRDDProcessAndCreateBridge()
|
|
||||||
returns (nsresult rv, Endpoint<PRemoteDecoderManagerChild> aEndpoint);
|
returns (nsresult rv, Endpoint<PRemoteDecoderManagerChild> aEndpoint);
|
||||||
|
|
||||||
child:
|
child:
|
||||||
|
|
|
@ -884,8 +884,6 @@ description = legacy sync IPC - please add detailed description
|
||||||
description = legacy sync IPC - please add detailed description
|
description = legacy sync IPC - please add detailed description
|
||||||
[PRemoteDecoderManager::Readback]
|
[PRemoteDecoderManager::Readback]
|
||||||
description = legacy sync IPC - please add detailed description
|
description = legacy sync IPC - please add detailed description
|
||||||
[PBackground::EnsureRDDProcessAndCreateBridge]
|
|
||||||
description = See Bug 1518344 - investigate using async for PBackground::EnsureRDDProcessAndCreateBridge
|
|
||||||
[PBackgroundStorage::Preload]
|
[PBackgroundStorage::Preload]
|
||||||
description = legacy sync IPC - please add detailed description
|
description = legacy sync IPC - please add detailed description
|
||||||
[PBackgroundLSDatabase::PBackgroundLSSnapshot]
|
[PBackgroundLSDatabase::PBackgroundLSSnapshot]
|
||||||
|
|
Загрузка…
Ссылка в новой задаче