Replace async image container IDs with a typed struct. (bug 1323957 part 1, r=mattwoodrow)

--HG--
extra : rebase_source : 4ff77f95ef818f59edb3d3b167548d84773a416f
This commit is contained in:
David Anderson 2017-01-17 18:47:05 -08:00
parent 440ada1d59
commit c74b40959d
19 changed files with 79 additions and 56 deletions

View File

@ -1206,7 +1206,7 @@ PluginInstanceParent::SetScrollCaptureId(uint64_t aScrollCaptureId)
return NS_ERROR_FAILURE;
}
mImageContainer = new ImageContainer(aScrollCaptureId);
mImageContainer = new ImageContainer(CompositableHandle(aScrollCaptureId));
return NS_OK;
}

View File

@ -29,7 +29,6 @@ AsyncCanvasRenderer::AsyncCanvasRenderer()
, mIsAlphaPremultiplied(true)
, mWidth(0)
, mHeight(0)
, mCanvasClientAsyncID(0)
, mCanvasClient(nullptr)
, mMutex("AsyncCanvasRenderer::mMutex")
{
@ -116,9 +115,9 @@ AsyncCanvasRenderer::SetCanvasClient(CanvasClient* aClient)
{
mCanvasClient = aClient;
if (aClient) {
mCanvasClientAsyncID = aClient->GetAsyncID();
mCanvasClientAsyncHandle = aClient->GetAsyncHandle();
} else {
mCanvasClientAsyncID = 0;
mCanvasClientAsyncHandle = CompositableHandle();
}
}

View File

@ -106,9 +106,9 @@ public:
return gfx::IntSize(mWidth, mHeight);
}
uint64_t GetCanvasClientAsyncID() const
CompositableHandle GetCanvasClientAsyncHandle() const
{
return mCanvasClientAsyncID;
return mCanvasClientAsyncHandle;
}
CanvasClient* GetCanvasClient() const
@ -140,7 +140,7 @@ private:
uint32_t mWidth;
uint32_t mHeight;
uint64_t mCanvasClientAsyncID;
CompositableHandle mCanvasClientAsyncHandle;
// The lifetime of this pointer is controlled by OffscreenCanvas
// Can be accessed in active thread and ImageBridge thread.

View File

@ -136,7 +136,7 @@ ImageContainer::EnsureImageClient(bool aCreate)
if (imageBridge) {
mImageClient = imageBridge->CreateImageClient(CompositableType::IMAGE, this);
if (mImageClient) {
mAsyncContainerID = mImageClient->GetAsyncID();
mAsyncContainerHandle = mImageClient->GetAsyncHandle();
mNotifyCompositeListener = new ImageContainerListener(this);
}
}
@ -153,22 +153,20 @@ ImageContainer::ImageContainer(Mode flag)
{
if (flag == ASYNCHRONOUS) {
EnsureImageClient(true);
} else {
mAsyncContainerID = sInvalidAsyncContainerId;
}
}
ImageContainer::ImageContainer(uint64_t aAsyncContainerID)
ImageContainer::ImageContainer(const CompositableHandle& aHandle)
: mReentrantMonitor("ImageContainer.mReentrantMonitor"),
mGenerationCounter(++sGenerationCounter),
mPaintCount(0),
mDroppedImageCount(0),
mImageFactory(nullptr),
mRecycleBin(nullptr),
mAsyncContainerID(aAsyncContainerID),
mAsyncContainerHandle(aHandle),
mCurrentProducerID(-1)
{
MOZ_ASSERT(mAsyncContainerID != sInvalidAsyncContainerId);
MOZ_ASSERT(mAsyncContainerHandle);
}
ImageContainer::~ImageContainer()
@ -176,9 +174,9 @@ ImageContainer::~ImageContainer()
if (mNotifyCompositeListener) {
mNotifyCompositeListener->ClearImageContainer();
}
if (mAsyncContainerID) {
if (mAsyncContainerHandle) {
if (RefPtr<ImageBridgeChild> imageBridge = ImageBridgeChild::GetSingleton()) {
imageBridge->ForgetImageContainer(mAsyncContainerID);
imageBridge->ForgetImageContainer(mAsyncContainerHandle);
}
}
}
@ -344,14 +342,14 @@ ImageContainer::SetCurrentImagesInTransaction(const nsTArray<NonOwningImage>& aI
bool ImageContainer::IsAsync() const
{
return mAsyncContainerID != sInvalidAsyncContainerId;
return !!mAsyncContainerHandle;
}
uint64_t ImageContainer::GetAsyncContainerID()
CompositableHandle ImageContainer::GetAsyncContainerHandle()
{
NS_ASSERTION(IsAsync(),"Shared image ID is only relevant to async ImageContainers");
EnsureImageClient(false);
return mAsyncContainerID;
return mAsyncContainerHandle;
}
bool

View File

@ -385,7 +385,7 @@ public:
* async container ID.
* @param aAsyncContainerID async container ID for which we are a proxy
*/
explicit ImageContainer(uint64_t aAsyncContainerID);
explicit ImageContainer(const CompositableHandle& aHandle);
typedef uint32_t FrameID;
typedef uint32_t ProducerID;
@ -486,7 +486,7 @@ public:
*
* Can be called from any thread.
*/
uint64_t GetAsyncContainerID();
CompositableHandle GetAsyncContainerHandle();
/**
* Returns if the container currently has an image.
@ -649,7 +649,7 @@ private:
// asynchronusly using the ImageBridge IPDL protocol.
RefPtr<ImageClient> mImageClient;
uint64_t mAsyncContainerID;
CompositableHandle mAsyncContainerHandle;
nsTArray<FrameID> mFrameIDsNotYetComposited;
// ProducerID for last current image(s), including the frames in

View File

@ -279,6 +279,36 @@ private:
uint64_t mHandle;
};
// This is used to communicate Compositables across IPC channels. The Handle is valid
// for layers in the same PLayerTransaction or PImageBridge. Handles are created by
// ClientLayerManager or ImageBridgeChild, and are cached in the parent side on first
// use.
class CompositableHandle
{
friend struct IPC::ParamTraits<mozilla::layers::CompositableHandle>;
public:
CompositableHandle() : mHandle(0)
{}
CompositableHandle(const CompositableHandle& aOther) : mHandle(aOther.mHandle)
{}
explicit CompositableHandle(uint64_t aHandle) : mHandle(aHandle)
{}
bool IsValid() const {
return mHandle != 0;
}
explicit operator bool() const {
return IsValid();
}
bool operator ==(const CompositableHandle& aOther) const {
return mHandle == aOther.mHandle;
}
uint64_t Value() const {
return mHandle;
}
private:
uint64_t mHandle;
};
} // namespace layers
} // namespace mozilla

View File

@ -55,14 +55,14 @@ CanvasClientBridge::UpdateAsync(AsyncCanvasRenderer* aRenderer)
return;
}
uint64_t asyncID = aRenderer->GetCanvasClientAsyncID();
if (asyncID == 0 || mAsyncID == asyncID) {
CompositableHandle asyncID = aRenderer->GetCanvasClientAsyncHandle();
if (!asyncID || mAsyncHandle == asyncID) {
return;
}
static_cast<ShadowLayerForwarder*>(GetForwarder())
->AttachAsyncCompositable(asyncID, mLayer);
mAsyncID = asyncID;
mAsyncHandle = asyncID;
}
void

View File

@ -184,7 +184,6 @@ public:
CanvasClientBridge(CompositableForwarder* aLayerForwarder,
TextureFlags aFlags)
: CanvasClient(aLayerForwarder, aFlags)
, mAsyncID(0)
, mLayer(nullptr)
{
}
@ -206,7 +205,7 @@ public:
}
protected:
uint64_t mAsyncID;
CompositableHandle mAsyncHandle;
ShadowableLayer* mLayer;
};

View File

@ -28,13 +28,13 @@ namespace layers {
using namespace mozilla::gfx;
void
CompositableClient::InitIPDLActor(PCompositableChild* aActor, uint64_t aAsyncID)
CompositableClient::InitIPDLActor(PCompositableChild* aActor, const CompositableHandle& aAsyncHandle)
{
MOZ_ASSERT(aActor);
mForwarder->AssertInForwarderThread();
mAsyncID = aAsyncID;
mAsyncHandle = aAsyncHandle;
mCompositableChild = static_cast<CompositableChild*>(aActor);
mCompositableChild->Init(this);
}
@ -57,7 +57,6 @@ CompositableClient::CompositableClient(CompositableForwarder* aForwarder,
TextureFlags aTextureFlags)
: mForwarder(aForwarder)
, mTextureFlags(aTextureFlags)
, mAsyncID(0)
{
}
@ -118,13 +117,13 @@ CompositableClient::Destroy()
mCompositableChild = nullptr;
}
uint64_t
CompositableClient::GetAsyncID() const
CompositableHandle
CompositableClient::GetAsyncHandle() const
{
if (mCompositableChild) {
return mAsyncID;
return mAsyncHandle;
}
return 0; // zero is always an invalid async ID
return CompositableHandle();
}
already_AddRefed<TextureClient>

View File

@ -125,10 +125,10 @@ public:
* layer. It is not used if the compositable is used with the regular shadow
* layer forwarder.
*
* If this returns zero, it means the compositable is not async (it is used
* If this returns empty, it means the compositable is not async (it is used
* on the main thread).
*/
uint64_t GetAsyncID() const;
CompositableHandle GetAsyncHandle() const;
/**
* Tells the Compositor to create a TextureHost for this TextureClient.
@ -162,7 +162,7 @@ public:
static RefPtr<CompositableClient> FromIPDLActor(PCompositableChild* aActor);
void InitIPDLActor(PCompositableChild* aActor, uint64_t aAsyncID = 0);
void InitIPDLActor(PCompositableChild* aActor, const CompositableHandle& aHandle);
TextureFlags GetTextureFlags() const { return mTextureFlags; }
@ -181,7 +181,8 @@ protected:
TextureFlags mTextureFlags;
RefPtr<TextureClientRecycleAllocator> mTextureClientRecycler;
uint64_t mAsyncID;
// Handle for IPDL operations.
CompositableHandle mAsyncHandle;
friend class CompositableChild;
};

View File

@ -278,7 +278,6 @@ ImageClient::ImageClient(CompositableForwarder* aFwd, TextureFlags aFlags,
ImageClientBridge::ImageClientBridge(CompositableForwarder* aFwd,
TextureFlags aFlags)
: ImageClient(aFwd, aFlags, CompositableType::IMAGE_BRIDGE)
, mAsyncContainerID(0)
{
}
@ -288,11 +287,11 @@ ImageClientBridge::UpdateImage(ImageContainer* aContainer, uint32_t aContentFlag
if (!GetForwarder() || !mLayer) {
return false;
}
if (mAsyncContainerID == aContainer->GetAsyncContainerID()) {
if (mAsyncContainerHandle == aContainer->GetAsyncContainerHandle()) {
return true;
}
mAsyncContainerID = aContainer->GetAsyncContainerID();
static_cast<ShadowLayerForwarder*>(GetForwarder())->AttachAsyncCompositable(mAsyncContainerID, mLayer);
mAsyncContainerHandle = aContainer->GetAsyncContainerHandle();
static_cast<ShadowLayerForwarder*>(GetForwarder())->AttachAsyncCompositable(mAsyncContainerHandle, mLayer);
return true;
}

View File

@ -129,7 +129,7 @@ public:
}
protected:
uint64_t mAsyncContainerID;
CompositableHandle mAsyncContainerHandle;
};
} // namespace layers

View File

@ -396,14 +396,14 @@ ImageBridgeChild::Connect(CompositableClient* aCompositable,
if (!child) {
return;
}
aCompositable->InitIPDLActor(child, id);
aCompositable->InitIPDLActor(child, CompositableHandle(id));
}
void
ImageBridgeChild::ForgetImageContainer(uint64_t aAsyncContainerID)
ImageBridgeChild::ForgetImageContainer(const CompositableHandle& aHandle)
{
MutexAutoLock lock(mContainerMapLock);
mImageContainers.Remove(aAsyncContainerID);
mImageContainers.Remove(aHandle.Value());
}
PCompositableChild*

View File

@ -270,7 +270,7 @@ public:
void Destroy(CompositableChild* aCompositable) override;
void ForgetImageContainer(uint64_t aAsyncContainerID);
void ForgetImageContainer(const CompositableHandle& aHandle);
/**
* Hold TextureClient ref until end of usage on host side if TextureFlags::RECYCLE is set.

View File

@ -819,7 +819,7 @@ ShadowLayerForwarder::Connect(CompositableClient* aCompositable,
if (!actor) {
return;
}
aCompositable->InitIPDLActor(actor);
aCompositable->InitIPDLActor(actor, CompositableHandle());
}
void ShadowLayerForwarder::Attach(CompositableClient* aCompositable,
@ -830,12 +830,12 @@ void ShadowLayerForwarder::Attach(CompositableClient* aCompositable,
mTxn->AddEdit(OpAttachCompositable(Shadow(aLayer), nullptr, aCompositable->GetIPDLActor()));
}
void ShadowLayerForwarder::AttachAsyncCompositable(uint64_t aCompositableID,
void ShadowLayerForwarder::AttachAsyncCompositable(const CompositableHandle& aHandle,
ShadowableLayer* aLayer)
{
MOZ_ASSERT(aLayer);
MOZ_ASSERT(aCompositableID != 0); // zero is always an invalid compositable id.
mTxn->AddEdit(OpAttachAsyncCompositable(Shadow(aLayer), aCompositableID));
MOZ_ASSERT(aHandle);
mTxn->AddEdit(OpAttachAsyncCompositable(Shadow(aLayer), aHandle.Value()));
}
void ShadowLayerForwarder::SetShadowManager(PLayerTransactionChild* aShadowManager)

View File

@ -182,7 +182,7 @@ public:
* the compositable or it's IPDL actor here, so we use an ID instead, that
* is matched on the compositor side.
*/
void AttachAsyncCompositable(uint64_t aCompositableID,
void AttachAsyncCompositable(const CompositableHandle& aHandle,
ShadowableLayer* aLayer);
/**

View File

@ -36,8 +36,7 @@ SharedPlanarYCbCrImage::SharedPlanarYCbCrImage(ImageClient* aCompositable)
SharedPlanarYCbCrImage::~SharedPlanarYCbCrImage() {
MOZ_COUNT_DTOR(SharedPlanarYCbCrImage);
if (mCompositable->GetAsyncID() != 0 &&
!InImageBridgeChildThread()) {
if (mCompositable->GetAsyncHandle() && !InImageBridgeChildThread()) {
if (mTextureClient) {
ADDREF_MANUALLY(mTextureClient);
ImageBridgeChild::DispatchReleaseTextureClient(mTextureClient);

View File

@ -63,8 +63,7 @@ SharedRGBImage::~SharedRGBImage()
{
MOZ_COUNT_DTOR(SharedRGBImage);
if (mCompositable->GetAsyncID() != 0 &&
!InImageBridgeChildThread()) {
if (mCompositable->GetAsyncHandle() && !InImageBridgeChildThread()) {
ADDREF_MANUALLY(mTextureClient);
ImageBridgeChild::DispatchReleaseTextureClient(mTextureClient);
mTextureClient = nullptr;

View File

@ -2210,7 +2210,7 @@ nsBaseWidget::CreateScrollCaptureContainer()
return ImageContainer::sInvalidAsyncContainerId;
}
return mScrollCaptureContainer->GetAsyncContainerID();
return mScrollCaptureContainer->GetAsyncContainerHandle().Value();
}
void