gfx/layers/ipc/CompositableTransactionParent.cpp

branch
TOR_BUG_9701
changeset 8
97036ab72558
equal deleted inserted replaced
-1:000000000000 0:80a85d01869a
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2 * vim: sw=2 ts=8 et :
3 */
4 /* This Source Code Form is subject to the terms of the Mozilla Public
5 * License, v. 2.0. If a copy of the MPL was not distributed with this
6 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7
8 #include "CompositableTransactionParent.h"
9 #include "CompositableHost.h" // for CompositableParent, etc
10 #include "CompositorParent.h" // for CompositorParent
11 #include "GLContext.h" // for GLContext
12 #include "Layers.h" // for Layer
13 #include "RenderTrace.h" // for RenderTraceInvalidateEnd, etc
14 #include "TiledLayerBuffer.h" // for TiledLayerComposer
15 #include "mozilla/Assertions.h" // for MOZ_ASSERT, etc
16 #include "mozilla/RefPtr.h" // for RefPtr
17 #include "mozilla/layers/CompositorTypes.h"
18 #include "mozilla/layers/ContentHost.h" // for ContentHostBase
19 #include "mozilla/layers/LayerManagerComposite.h"
20 #include "mozilla/layers/LayersSurfaces.h" // for SurfaceDescriptor
21 #include "mozilla/layers/LayersTypes.h" // for MOZ_LAYERS_LOG
22 #include "mozilla/layers/TextureHost.h" // for TextureHost
23 #include "mozilla/layers/TextureHostOGL.h" // for TextureHostOGL
24 #include "mozilla/layers/ThebesLayerComposite.h"
25 #include "mozilla/mozalloc.h" // for operator delete
26 #include "nsDebug.h" // for NS_WARNING, NS_ASSERTION
27 #include "nsRegion.h" // for nsIntRegion
28
29 namespace mozilla {
30 namespace layers {
31
32 class ClientTiledLayerBuffer;
33 class Compositor;
34
35 template<typename Op>
36 CompositableHost* AsCompositable(const Op& op)
37 {
38 return CompositableHost::FromIPDLActor(op.compositableParent());
39 }
40
41 // This function can in some cases fail and return false without it being a bug.
42 // This can theoretically happen if the ImageBridge sends frames before
43 // we created the layer tree. Since we can't enforce that the layer
44 // tree is already created before ImageBridge operates, there isn't much
45 // we can do about it, but in practice it is very rare.
46 // Typically when a tab with a video is dragged from a window to another,
47 // there can be a short time when the video is still sending frames
48 // asynchonously while the layer tree is not reconstructed. It's not a
49 // big deal.
50 // Note that Layers transactions do not need to call this because they always
51 // schedule the composition, in LayerManagerComposite::EndTransaction.
52 template<typename T>
53 bool ScheduleComposition(const T& op)
54 {
55 CompositableHost* comp = AsCompositable(op);
56 uint64_t id = comp->GetCompositorID();
57 if (!comp || !id) {
58 return false;
59 }
60 CompositorParent* cp = CompositorParent::GetCompositor(id);
61 if (!cp) {
62 return false;
63 }
64 cp->ScheduleComposition();
65 return true;
66 }
67
68 bool
69 CompositableParentManager::ReceiveCompositableUpdate(const CompositableOperation& aEdit,
70 EditReplyVector& replyv)
71 {
72 switch (aEdit.type()) {
73 case CompositableOperation::TOpCreatedIncrementalTexture: {
74 MOZ_LAYERS_LOG(("[ParentSide] Created texture"));
75 const OpCreatedIncrementalTexture& op = aEdit.get_OpCreatedIncrementalTexture();
76 CompositableHost* compositable = AsCompositable(op);
77
78 bool success =
79 compositable->CreatedIncrementalTexture(this,
80 op.textureInfo(),
81 op.bufferRect());
82 if (!success) {
83 return false;
84 }
85 break;
86 }
87 case CompositableOperation::TOpPaintTextureRegion: {
88 MOZ_LAYERS_LOG(("[ParentSide] Paint ThebesLayer"));
89
90 const OpPaintTextureRegion& op = aEdit.get_OpPaintTextureRegion();
91 CompositableHost* compositable = AsCompositable(op);
92 Layer* layer = compositable->GetLayer();
93 if (!layer || layer->GetType() != Layer::TYPE_THEBES) {
94 return false;
95 }
96 ThebesLayerComposite* thebes = static_cast<ThebesLayerComposite*>(layer);
97
98 const ThebesBufferData& bufferData = op.bufferData();
99
100 RenderTraceInvalidateStart(thebes, "FF00FF", op.updatedRegion().GetBounds());
101
102 nsIntRegion frontUpdatedRegion;
103 if (!compositable->UpdateThebes(bufferData,
104 op.updatedRegion(),
105 thebes->GetValidRegion(),
106 &frontUpdatedRegion))
107 {
108 return false;
109 }
110 replyv.push_back(
111 OpContentBufferSwap(op.compositableParent(), nullptr, frontUpdatedRegion));
112
113 RenderTraceInvalidateEnd(thebes, "FF00FF");
114 // return texure data to client if necessary
115 ReturnTextureDataIfNecessary(compositable, replyv, op.compositableParent());
116 break;
117 }
118 case CompositableOperation::TOpPaintTextureIncremental: {
119 MOZ_LAYERS_LOG(("[ParentSide] Paint ThebesLayer"));
120
121 const OpPaintTextureIncremental& op = aEdit.get_OpPaintTextureIncremental();
122
123 CompositableHost* compositable = AsCompositable(op);
124
125 SurfaceDescriptor desc = op.image();
126
127 compositable->UpdateIncremental(op.textureId(),
128 desc,
129 op.updatedRegion(),
130 op.bufferRect(),
131 op.bufferRotation());
132 break;
133 }
134 case CompositableOperation::TOpUpdatePictureRect: {
135 const OpUpdatePictureRect& op = aEdit.get_OpUpdatePictureRect();
136 CompositableHost* compositable = AsCompositable(op);
137 MOZ_ASSERT(compositable);
138 compositable->SetPictureRect(op.picture());
139 break;
140 }
141 case CompositableOperation::TOpUseTiledLayerBuffer: {
142 MOZ_LAYERS_LOG(("[ParentSide] Paint TiledLayerBuffer"));
143 const OpUseTiledLayerBuffer& op = aEdit.get_OpUseTiledLayerBuffer();
144 CompositableHost* compositable = AsCompositable(op);
145
146 TiledLayerComposer* tileComposer = compositable->AsTiledLayerComposer();
147 NS_ASSERTION(tileComposer, "compositable is not a tile composer");
148
149 const SurfaceDescriptorTiles& tileDesc = op.tileLayerDescriptor();
150 tileComposer->UseTiledLayerBuffer(this, tileDesc);
151 break;
152 }
153 case CompositableOperation::TOpRemoveTexture: {
154 const OpRemoveTexture& op = aEdit.get_OpRemoveTexture();
155 CompositableHost* compositable = AsCompositable(op);
156 RefPtr<TextureHost> tex = TextureHost::AsTextureHost(op.textureParent());
157
158 MOZ_ASSERT(tex.get());
159 compositable->RemoveTextureHost(tex);
160 // return texure data to client if necessary
161 ReturnTextureDataIfNecessary(compositable, replyv, op.compositableParent());
162 break;
163 }
164 case CompositableOperation::TOpUseTexture: {
165 const OpUseTexture& op = aEdit.get_OpUseTexture();
166 CompositableHost* compositable = AsCompositable(op);
167 RefPtr<TextureHost> tex = TextureHost::AsTextureHost(op.textureParent());
168
169 MOZ_ASSERT(tex.get());
170 compositable->UseTextureHost(tex);
171
172 if (IsAsync()) {
173 ScheduleComposition(op);
174 // Async layer updates don't trigger invalidation, manually tell the layer
175 // that its content have changed.
176 if (compositable->GetLayer()) {
177 compositable->GetLayer()->SetInvalidRectToVisibleRegion();
178 }
179 }
180 // return texure data to client if necessary
181 ReturnTextureDataIfNecessary(compositable, replyv, op.compositableParent());
182 break;
183 }
184 case CompositableOperation::TOpUseComponentAlphaTextures: {
185 const OpUseComponentAlphaTextures& op = aEdit.get_OpUseComponentAlphaTextures();
186 CompositableHost* compositable = AsCompositable(op);
187 RefPtr<TextureHost> texOnBlack = TextureHost::AsTextureHost(op.textureOnBlackParent());
188 RefPtr<TextureHost> texOnWhite = TextureHost::AsTextureHost(op.textureOnWhiteParent());
189
190 MOZ_ASSERT(texOnBlack && texOnWhite);
191 compositable->UseComponentAlphaTextures(texOnBlack, texOnWhite);
192
193 if (IsAsync()) {
194 ScheduleComposition(op);
195 }
196 // return texure data to client if necessary
197 ReturnTextureDataIfNecessary(compositable, replyv, op.compositableParent());
198 break;
199 }
200 case CompositableOperation::TOpUpdateTexture: {
201 const OpUpdateTexture& op = aEdit.get_OpUpdateTexture();
202 RefPtr<TextureHost> texture = TextureHost::AsTextureHost(op.textureParent());
203 MOZ_ASSERT(texture);
204
205 texture->Updated(op.region().type() == MaybeRegion::TnsIntRegion
206 ? &op.region().get_nsIntRegion()
207 : nullptr); // no region means invalidate the entire surface
208 break;
209 }
210
211 default: {
212 MOZ_ASSERT(false, "bad type");
213 }
214 }
215
216 return true;
217 }
218
219 #if defined(MOZ_WIDGET_GONK) && ANDROID_VERSION >= 17
220 void
221 CompositableParentManager::ReturnTextureDataIfNecessary(CompositableHost* aCompositable,
222 EditReplyVector& replyv,
223 PCompositableParent* aParent)
224 {
225 if (!aCompositable || !aCompositable->GetCompositableBackendSpecificData()) {
226 return;
227 }
228
229 const std::vector< RefPtr<TextureHost> > textureList =
230 aCompositable->GetCompositableBackendSpecificData()->GetPendingReleaseFenceTextureList();
231 // Return pending Texture data
232 for (size_t i = 0; i < textureList.size(); i++) {
233 // File descriptor number is limited to 4 per IPC message.
234 // See Bug 986253
235 if (mPrevFenceHandles.size() >= 4) {
236 break;
237 }
238 TextureHostOGL* hostOGL = textureList[i]->AsHostOGL();
239 PTextureParent* actor = textureList[i]->GetIPDLActor();
240 if (!hostOGL || !actor) {
241 continue;
242 }
243 android::sp<android::Fence> fence = hostOGL->GetAndResetReleaseFence();
244 if (fence.get() && fence->isValid()) {
245 FenceHandle handle = FenceHandle(fence);
246 replyv.push_back(ReturnReleaseFence(aParent, nullptr, actor, nullptr, handle));
247 // Hold fence handle to prevent fence's file descriptor is closed before IPC happens.
248 mPrevFenceHandles.push_back(handle);
249 }
250 }
251 aCompositable->GetCompositableBackendSpecificData()->ClearPendingReleaseFenceTextureList();
252 }
253 #else
254 void
255 CompositableParentManager::ReturnTextureDataIfNecessary(CompositableHost* aCompositable,
256 EditReplyVector& replyv,
257 PCompositableParent* aParent)
258 {
259 if (!aCompositable || !aCompositable->GetCompositableBackendSpecificData()) {
260 return;
261 }
262 aCompositable->GetCompositableBackendSpecificData()->ClearPendingReleaseFenceTextureList();
263 }
264 #endif
265
266 void
267 CompositableParentManager::ClearPrevFenceHandles()
268 {
269 mPrevFenceHandles.clear();
270 }
271
272 } // namespace
273 } // namespace
274

mercurial