gfx/layers/ipc/LayerTransactionParent.cpp

Tue, 06 Jan 2015 21:39:09 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Tue, 06 Jan 2015 21:39:09 +0100
branch
TOR_BUG_9701
changeset 8
97036ab72558
permissions
-rw-r--r--

Conditionally force memory storage according to privacy.thirdparty.isolate;
This solves Tor bug #9701, complying with disk avoidance documented in
https://www.torproject.org/projects/torbrowser/design/#disk-avoidance.

michael@0 1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*-
michael@0 2 * vim: sw=2 ts=8 et :
michael@0 3 */
michael@0 4 /* This Source Code Form is subject to the terms of the Mozilla Public
michael@0 5 * License, v. 2.0. If a copy of the MPL was not distributed with this
michael@0 6 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
michael@0 7
michael@0 8 #include "LayerTransactionParent.h"
michael@0 9 #include <vector> // for vector
michael@0 10 #include "CompositableHost.h" // for CompositableParent, Get, etc
michael@0 11 #include "ImageLayers.h" // for ImageLayer
michael@0 12 #include "Layers.h" // for Layer, ContainerLayer, etc
michael@0 13 #include "ShadowLayerParent.h" // for ShadowLayerParent
michael@0 14 #include "gfx3DMatrix.h" // for gfx3DMatrix
michael@0 15 #include "gfxPoint3D.h" // for gfxPoint3D
michael@0 16 #include "CompositableTransactionParent.h" // for EditReplyVector
michael@0 17 #include "ShadowLayersManager.h" // for ShadowLayersManager
michael@0 18 #include "mozilla/gfx/BasePoint3D.h" // for BasePoint3D
michael@0 19 #include "mozilla/layers/CanvasLayerComposite.h"
michael@0 20 #include "mozilla/layers/ColorLayerComposite.h"
michael@0 21 #include "mozilla/layers/Compositor.h" // for Compositor
michael@0 22 #include "mozilla/layers/ContainerLayerComposite.h"
michael@0 23 #include "mozilla/layers/ImageLayerComposite.h"
michael@0 24 #include "mozilla/layers/LayerManagerComposite.h"
michael@0 25 #include "mozilla/layers/LayersMessages.h" // for EditReply, etc
michael@0 26 #include "mozilla/layers/LayersSurfaces.h" // for PGrallocBufferParent
michael@0 27 #include "mozilla/layers/LayersTypes.h" // for MOZ_LAYERS_LOG
michael@0 28 #include "mozilla/layers/PCompositableParent.h"
michael@0 29 #include "mozilla/layers/PLayerParent.h" // for PLayerParent
michael@0 30 #include "mozilla/layers/ThebesLayerComposite.h"
michael@0 31 #include "mozilla/mozalloc.h" // for operator delete, etc
michael@0 32 #include "nsCoord.h" // for NSAppUnitsToFloatPixels
michael@0 33 #include "nsDebug.h" // for NS_RUNTIMEABORT
michael@0 34 #include "nsDeviceContext.h" // for AppUnitsPerCSSPixel
michael@0 35 #include "nsISupportsImpl.h" // for Layer::Release, etc
michael@0 36 #include "nsLayoutUtils.h" // for nsLayoutUtils
michael@0 37 #include "nsMathUtils.h" // for NS_round
michael@0 38 #include "nsPoint.h" // for nsPoint
michael@0 39 #include "nsTArray.h" // for nsTArray, nsTArray_Impl, etc
michael@0 40 #include "GeckoProfiler.h"
michael@0 41 #include "mozilla/layers/TextureHost.h"
michael@0 42 #include "mozilla/layers/AsyncCompositionManager.h"
michael@0 43 #include "mozilla/layers/AsyncPanZoomController.h"
michael@0 44
michael@0 45 typedef std::vector<mozilla::layers::EditReply> EditReplyVector;
michael@0 46
michael@0 47 using mozilla::layout::RenderFrameParent;
michael@0 48
michael@0 49 namespace mozilla {
michael@0 50 namespace layers {
michael@0 51
michael@0 52 class PGrallocBufferParent;
michael@0 53
michael@0 54 //--------------------------------------------------
michael@0 55 // Convenience accessors
michael@0 56 static ShadowLayerParent*
michael@0 57 cast(const PLayerParent* in)
michael@0 58 {
michael@0 59 return const_cast<ShadowLayerParent*>(
michael@0 60 static_cast<const ShadowLayerParent*>(in));
michael@0 61 }
michael@0 62
michael@0 63 template<class OpCreateT>
michael@0 64 static ShadowLayerParent*
michael@0 65 AsLayerComposite(const OpCreateT& op)
michael@0 66 {
michael@0 67 return cast(op.layerParent());
michael@0 68 }
michael@0 69
michael@0 70 static ShadowLayerParent*
michael@0 71 AsLayerComposite(const OpSetRoot& op)
michael@0 72 {
michael@0 73 return cast(op.rootParent());
michael@0 74 }
michael@0 75
michael@0 76 static ShadowLayerParent*
michael@0 77 ShadowContainer(const OpInsertAfter& op)
michael@0 78 {
michael@0 79 return cast(op.containerParent());
michael@0 80 }
michael@0 81 static ShadowLayerParent*
michael@0 82 ShadowChild(const OpInsertAfter& op)
michael@0 83 {
michael@0 84 return cast(op.childLayerParent());
michael@0 85 }
michael@0 86 static ShadowLayerParent*
michael@0 87 ShadowAfter(const OpInsertAfter& op)
michael@0 88 {
michael@0 89 return cast(op.afterParent());
michael@0 90 }
michael@0 91
michael@0 92 static ShadowLayerParent*
michael@0 93 ShadowContainer(const OpPrependChild& op)
michael@0 94 {
michael@0 95 return cast(op.containerParent());
michael@0 96 }
michael@0 97 static ShadowLayerParent*
michael@0 98 ShadowChild(const OpPrependChild& op)
michael@0 99 {
michael@0 100 return cast(op.childLayerParent());
michael@0 101 }
michael@0 102
michael@0 103 static ShadowLayerParent*
michael@0 104 ShadowContainer(const OpRemoveChild& op)
michael@0 105 {
michael@0 106 return cast(op.containerParent());
michael@0 107 }
michael@0 108 static ShadowLayerParent*
michael@0 109 ShadowChild(const OpRemoveChild& op)
michael@0 110 {
michael@0 111 return cast(op.childLayerParent());
michael@0 112 }
michael@0 113
michael@0 114 static ShadowLayerParent*
michael@0 115 ShadowContainer(const OpRepositionChild& op)
michael@0 116 {
michael@0 117 return cast(op.containerParent());
michael@0 118 }
michael@0 119 static ShadowLayerParent*
michael@0 120 ShadowChild(const OpRepositionChild& op)
michael@0 121 {
michael@0 122 return cast(op.childLayerParent());
michael@0 123 }
michael@0 124 static ShadowLayerParent*
michael@0 125 ShadowAfter(const OpRepositionChild& op)
michael@0 126 {
michael@0 127 return cast(op.afterParent());
michael@0 128 }
michael@0 129
michael@0 130 static ShadowLayerParent*
michael@0 131 ShadowContainer(const OpRaiseToTopChild& op)
michael@0 132 {
michael@0 133 return cast(op.containerParent());
michael@0 134 }
michael@0 135 static ShadowLayerParent*
michael@0 136 ShadowChild(const OpRaiseToTopChild& op)
michael@0 137 {
michael@0 138 return cast(op.childLayerParent());
michael@0 139 }
michael@0 140
michael@0 141 //--------------------------------------------------
michael@0 142 // LayerTransactionParent
michael@0 143 LayerTransactionParent::LayerTransactionParent(LayerManagerComposite* aManager,
michael@0 144 ShadowLayersManager* aLayersManager,
michael@0 145 uint64_t aId)
michael@0 146 : mLayerManager(aManager)
michael@0 147 , mShadowLayersManager(aLayersManager)
michael@0 148 , mId(aId)
michael@0 149 , mDestroyed(false)
michael@0 150 , mIPCOpen(false)
michael@0 151 {
michael@0 152 MOZ_COUNT_CTOR(LayerTransactionParent);
michael@0 153 }
michael@0 154
michael@0 155 LayerTransactionParent::~LayerTransactionParent()
michael@0 156 {
michael@0 157 MOZ_COUNT_DTOR(LayerTransactionParent);
michael@0 158 }
michael@0 159
michael@0 160 void
michael@0 161 LayerTransactionParent::Destroy()
michael@0 162 {
michael@0 163 mDestroyed = true;
michael@0 164 for (size_t i = 0; i < ManagedPLayerParent().Length(); ++i) {
michael@0 165 ShadowLayerParent* slp =
michael@0 166 static_cast<ShadowLayerParent*>(ManagedPLayerParent()[i]);
michael@0 167 slp->Destroy();
michael@0 168 }
michael@0 169 }
michael@0 170
michael@0 171 LayersBackend
michael@0 172 LayerTransactionParent::GetCompositorBackendType() const
michael@0 173 {
michael@0 174 return mLayerManager->GetBackendType();
michael@0 175 }
michael@0 176
michael@0 177 /* virtual */
michael@0 178 bool
michael@0 179 LayerTransactionParent::RecvUpdateNoSwap(const InfallibleTArray<Edit>& cset,
michael@0 180 const TargetConfig& targetConfig,
michael@0 181 const bool& isFirstPaint,
michael@0 182 const bool& scheduleComposite)
michael@0 183 {
michael@0 184 return RecvUpdate(cset, targetConfig, isFirstPaint, scheduleComposite, nullptr);
michael@0 185 }
michael@0 186
michael@0 187 bool
michael@0 188 LayerTransactionParent::RecvUpdate(const InfallibleTArray<Edit>& cset,
michael@0 189 const TargetConfig& targetConfig,
michael@0 190 const bool& isFirstPaint,
michael@0 191 const bool& scheduleComposite,
michael@0 192 InfallibleTArray<EditReply>* reply)
michael@0 193 {
michael@0 194 profiler_tracing("Paint", "Composite", TRACING_INTERVAL_START);
michael@0 195 PROFILER_LABEL("LayerTransactionParent", "RecvUpdate");
michael@0 196 #ifdef COMPOSITOR_PERFORMANCE_WARNING
michael@0 197 TimeStamp updateStart = TimeStamp::Now();
michael@0 198 #endif
michael@0 199
michael@0 200 MOZ_LAYERS_LOG(("[ParentSide] received txn with %d edits", cset.Length()));
michael@0 201
michael@0 202 if (mDestroyed || !layer_manager() || layer_manager()->IsDestroyed()) {
michael@0 203 return true;
michael@0 204 }
michael@0 205
michael@0 206 if (mLayerManager && mLayerManager->GetCompositor() &&
michael@0 207 !targetConfig.naturalBounds().IsEmpty()) {
michael@0 208 mLayerManager->GetCompositor()->SetScreenRotation(targetConfig.rotation());
michael@0 209 }
michael@0 210
michael@0 211 // Clear fence handles used in previsou transaction.
michael@0 212 ClearPrevFenceHandles();
michael@0 213
michael@0 214 EditReplyVector replyv;
michael@0 215
michael@0 216 {
michael@0 217 AutoResolveRefLayers resolve(mShadowLayersManager->GetCompositionManager(this));
michael@0 218 layer_manager()->BeginTransaction();
michael@0 219 }
michael@0 220
michael@0 221 for (EditArray::index_type i = 0; i < cset.Length(); ++i) {
michael@0 222 const Edit& edit = cset[i];
michael@0 223
michael@0 224 switch (edit.type()) {
michael@0 225 // Create* ops
michael@0 226 case Edit::TOpCreateThebesLayer: {
michael@0 227 MOZ_LAYERS_LOG(("[ParentSide] CreateThebesLayer"));
michael@0 228
michael@0 229 nsRefPtr<ThebesLayerComposite> layer =
michael@0 230 layer_manager()->CreateThebesLayerComposite();
michael@0 231 AsLayerComposite(edit.get_OpCreateThebesLayer())->Bind(layer);
michael@0 232 break;
michael@0 233 }
michael@0 234 case Edit::TOpCreateContainerLayer: {
michael@0 235 MOZ_LAYERS_LOG(("[ParentSide] CreateContainerLayer"));
michael@0 236
michael@0 237 nsRefPtr<ContainerLayer> layer = layer_manager()->CreateContainerLayerComposite();
michael@0 238 AsLayerComposite(edit.get_OpCreateContainerLayer())->Bind(layer);
michael@0 239 break;
michael@0 240 }
michael@0 241 case Edit::TOpCreateImageLayer: {
michael@0 242 MOZ_LAYERS_LOG(("[ParentSide] CreateImageLayer"));
michael@0 243
michael@0 244 nsRefPtr<ImageLayerComposite> layer =
michael@0 245 layer_manager()->CreateImageLayerComposite();
michael@0 246 AsLayerComposite(edit.get_OpCreateImageLayer())->Bind(layer);
michael@0 247 break;
michael@0 248 }
michael@0 249 case Edit::TOpCreateColorLayer: {
michael@0 250 MOZ_LAYERS_LOG(("[ParentSide] CreateColorLayer"));
michael@0 251
michael@0 252 nsRefPtr<ColorLayerComposite> layer = layer_manager()->CreateColorLayerComposite();
michael@0 253 AsLayerComposite(edit.get_OpCreateColorLayer())->Bind(layer);
michael@0 254 break;
michael@0 255 }
michael@0 256 case Edit::TOpCreateCanvasLayer: {
michael@0 257 MOZ_LAYERS_LOG(("[ParentSide] CreateCanvasLayer"));
michael@0 258
michael@0 259 nsRefPtr<CanvasLayerComposite> layer =
michael@0 260 layer_manager()->CreateCanvasLayerComposite();
michael@0 261 AsLayerComposite(edit.get_OpCreateCanvasLayer())->Bind(layer);
michael@0 262 break;
michael@0 263 }
michael@0 264 case Edit::TOpCreateRefLayer: {
michael@0 265 MOZ_LAYERS_LOG(("[ParentSide] CreateRefLayer"));
michael@0 266
michael@0 267 nsRefPtr<RefLayerComposite> layer =
michael@0 268 layer_manager()->CreateRefLayerComposite();
michael@0 269 AsLayerComposite(edit.get_OpCreateRefLayer())->Bind(layer);
michael@0 270 break;
michael@0 271 }
michael@0 272
michael@0 273 // Attributes
michael@0 274 case Edit::TOpSetLayerAttributes: {
michael@0 275 MOZ_LAYERS_LOG(("[ParentSide] SetLayerAttributes"));
michael@0 276
michael@0 277 const OpSetLayerAttributes& osla = edit.get_OpSetLayerAttributes();
michael@0 278 ShadowLayerParent* layerParent = AsLayerComposite(osla);
michael@0 279 Layer* layer = layerParent->AsLayer();
michael@0 280 if (!layer) {
michael@0 281 return false;
michael@0 282 }
michael@0 283 const LayerAttributes& attrs = osla.attrs();
michael@0 284
michael@0 285 const CommonLayerAttributes& common = attrs.common();
michael@0 286 layer->SetVisibleRegion(common.visibleRegion());
michael@0 287 layer->SetEventRegions(common.eventRegions());
michael@0 288 layer->SetContentFlags(common.contentFlags());
michael@0 289 layer->SetOpacity(common.opacity());
michael@0 290 layer->SetClipRect(common.useClipRect() ? &common.clipRect() : nullptr);
michael@0 291 layer->SetBaseTransform(common.transform().value());
michael@0 292 layer->SetPostScale(common.postXScale(), common.postYScale());
michael@0 293 layer->SetIsFixedPosition(common.isFixedPosition());
michael@0 294 layer->SetFixedPositionAnchor(common.fixedPositionAnchor());
michael@0 295 layer->SetFixedPositionMargins(common.fixedPositionMargin());
michael@0 296 if (common.isStickyPosition()) {
michael@0 297 layer->SetStickyPositionData(common.stickyScrollContainerId(),
michael@0 298 common.stickyScrollRangeOuter(),
michael@0 299 common.stickyScrollRangeInner());
michael@0 300 }
michael@0 301 layer->SetScrollbarData(common.scrollbarTargetContainerId(),
michael@0 302 static_cast<Layer::ScrollDirection>(common.scrollbarDirection()));
michael@0 303 if (PLayerParent* maskLayer = common.maskLayerParent()) {
michael@0 304 layer->SetMaskLayer(cast(maskLayer)->AsLayer());
michael@0 305 } else {
michael@0 306 layer->SetMaskLayer(nullptr);
michael@0 307 }
michael@0 308 layer->SetAnimations(common.animations());
michael@0 309 layer->SetInvalidRegion(common.invalidRegion());
michael@0 310
michael@0 311 typedef SpecificLayerAttributes Specific;
michael@0 312 const SpecificLayerAttributes& specific = attrs.specific();
michael@0 313 switch (specific.type()) {
michael@0 314 case Specific::Tnull_t:
michael@0 315 break;
michael@0 316
michael@0 317 case Specific::TThebesLayerAttributes: {
michael@0 318 MOZ_LAYERS_LOG(("[ParentSide] thebes layer"));
michael@0 319
michael@0 320 ThebesLayerComposite* thebesLayer = layerParent->AsThebesLayerComposite();
michael@0 321 if (!thebesLayer) {
michael@0 322 return false;
michael@0 323 }
michael@0 324 const ThebesLayerAttributes& attrs =
michael@0 325 specific.get_ThebesLayerAttributes();
michael@0 326
michael@0 327 thebesLayer->SetValidRegion(attrs.validRegion());
michael@0 328
michael@0 329 break;
michael@0 330 }
michael@0 331 case Specific::TContainerLayerAttributes: {
michael@0 332 MOZ_LAYERS_LOG(("[ParentSide] container layer"));
michael@0 333
michael@0 334 ContainerLayerComposite* containerLayer = layerParent->AsContainerLayerComposite();
michael@0 335 if (!containerLayer) {
michael@0 336 return false;
michael@0 337 }
michael@0 338 const ContainerLayerAttributes& attrs =
michael@0 339 specific.get_ContainerLayerAttributes();
michael@0 340 containerLayer->SetFrameMetrics(attrs.metrics());
michael@0 341 containerLayer->SetScrollHandoffParentId(attrs.scrollParentId());
michael@0 342 containerLayer->SetPreScale(attrs.preXScale(), attrs.preYScale());
michael@0 343 containerLayer->SetInheritedScale(attrs.inheritedXScale(), attrs.inheritedYScale());
michael@0 344 break;
michael@0 345 }
michael@0 346 case Specific::TColorLayerAttributes: {
michael@0 347 MOZ_LAYERS_LOG(("[ParentSide] color layer"));
michael@0 348
michael@0 349 ColorLayerComposite* colorLayer = layerParent->AsColorLayerComposite();
michael@0 350 if (!colorLayer) {
michael@0 351 return false;
michael@0 352 }
michael@0 353 colorLayer->SetColor(specific.get_ColorLayerAttributes().color().value());
michael@0 354 colorLayer->SetBounds(specific.get_ColorLayerAttributes().bounds());
michael@0 355 break;
michael@0 356 }
michael@0 357 case Specific::TCanvasLayerAttributes: {
michael@0 358 MOZ_LAYERS_LOG(("[ParentSide] canvas layer"));
michael@0 359
michael@0 360 CanvasLayerComposite* canvasLayer = layerParent->AsCanvasLayerComposite();
michael@0 361 if (!canvasLayer) {
michael@0 362 return false;
michael@0 363 }
michael@0 364 canvasLayer->SetFilter(specific.get_CanvasLayerAttributes().filter());
michael@0 365 canvasLayer->SetBounds(specific.get_CanvasLayerAttributes().bounds());
michael@0 366 break;
michael@0 367 }
michael@0 368 case Specific::TRefLayerAttributes: {
michael@0 369 MOZ_LAYERS_LOG(("[ParentSide] ref layer"));
michael@0 370
michael@0 371 RefLayerComposite* refLayer = layerParent->AsRefLayerComposite();
michael@0 372 if (!refLayer) {
michael@0 373 return false;
michael@0 374 }
michael@0 375 refLayer->SetReferentId(specific.get_RefLayerAttributes().id());
michael@0 376 break;
michael@0 377 }
michael@0 378 case Specific::TImageLayerAttributes: {
michael@0 379 MOZ_LAYERS_LOG(("[ParentSide] image layer"));
michael@0 380
michael@0 381 ImageLayerComposite* imageLayer = layerParent->AsImageLayerComposite();
michael@0 382 if (!imageLayer) {
michael@0 383 return false;
michael@0 384 }
michael@0 385 const ImageLayerAttributes& attrs = specific.get_ImageLayerAttributes();
michael@0 386 imageLayer->SetFilter(attrs.filter());
michael@0 387 imageLayer->SetScaleToSize(attrs.scaleToSize(), attrs.scaleMode());
michael@0 388 break;
michael@0 389 }
michael@0 390 default:
michael@0 391 NS_RUNTIMEABORT("not reached");
michael@0 392 }
michael@0 393 break;
michael@0 394 }
michael@0 395 case Edit::TOpSetDiagnosticTypes: {
michael@0 396 mLayerManager->GetCompositor()->SetDiagnosticTypes(
michael@0 397 edit.get_OpSetDiagnosticTypes().diagnostics());
michael@0 398 break;
michael@0 399 }
michael@0 400 // Tree ops
michael@0 401 case Edit::TOpSetRoot: {
michael@0 402 MOZ_LAYERS_LOG(("[ParentSide] SetRoot"));
michael@0 403
michael@0 404 Layer* newRoot = AsLayerComposite(edit.get_OpSetRoot())->AsLayer();
michael@0 405 if (!newRoot) {
michael@0 406 return false;
michael@0 407 }
michael@0 408 if (newRoot->GetParent()) {
michael@0 409 // newRoot is not a root!
michael@0 410 return false;
michael@0 411 }
michael@0 412 mRoot = newRoot;
michael@0 413 break;
michael@0 414 }
michael@0 415 case Edit::TOpInsertAfter: {
michael@0 416 MOZ_LAYERS_LOG(("[ParentSide] InsertAfter"));
michael@0 417
michael@0 418 const OpInsertAfter& oia = edit.get_OpInsertAfter();
michael@0 419 Layer* child = ShadowChild(oia)->AsLayer();
michael@0 420 if (!child) {
michael@0 421 return false;
michael@0 422 }
michael@0 423 ContainerLayerComposite* container = ShadowContainer(oia)->AsContainerLayerComposite();
michael@0 424 if (!container ||
michael@0 425 !container->InsertAfter(child, ShadowAfter(oia)->AsLayer()))
michael@0 426 {
michael@0 427 return false;
michael@0 428 }
michael@0 429 break;
michael@0 430 }
michael@0 431 case Edit::TOpPrependChild: {
michael@0 432 MOZ_LAYERS_LOG(("[ParentSide] PrependChild"));
michael@0 433
michael@0 434 const OpPrependChild& oac = edit.get_OpPrependChild();
michael@0 435 Layer* child = ShadowChild(oac)->AsLayer();
michael@0 436 if (!child) {
michael@0 437 return false;
michael@0 438 }
michael@0 439 ContainerLayerComposite* container = ShadowContainer(oac)->AsContainerLayerComposite();
michael@0 440 if (!container ||
michael@0 441 !container->InsertAfter(child, nullptr))
michael@0 442 {
michael@0 443 return false;
michael@0 444 }
michael@0 445 break;
michael@0 446 }
michael@0 447 case Edit::TOpRemoveChild: {
michael@0 448 MOZ_LAYERS_LOG(("[ParentSide] RemoveChild"));
michael@0 449
michael@0 450 const OpRemoveChild& orc = edit.get_OpRemoveChild();
michael@0 451 Layer* childLayer = ShadowChild(orc)->AsLayer();
michael@0 452 if (!childLayer) {
michael@0 453 return false;
michael@0 454 }
michael@0 455 ContainerLayerComposite* container = ShadowContainer(orc)->AsContainerLayerComposite();
michael@0 456 if (!container ||
michael@0 457 !container->RemoveChild(childLayer))
michael@0 458 {
michael@0 459 return false;
michael@0 460 }
michael@0 461 break;
michael@0 462 }
michael@0 463 case Edit::TOpRepositionChild: {
michael@0 464 MOZ_LAYERS_LOG(("[ParentSide] RepositionChild"));
michael@0 465
michael@0 466 const OpRepositionChild& orc = edit.get_OpRepositionChild();
michael@0 467 Layer* child = ShadowChild(orc)->AsLayer();
michael@0 468 if (!child) {
michael@0 469 return false;
michael@0 470 }
michael@0 471 ContainerLayerComposite* container = ShadowContainer(orc)->AsContainerLayerComposite();
michael@0 472 if (!container ||
michael@0 473 !container->RepositionChild(child, ShadowAfter(orc)->AsLayer()))
michael@0 474 {
michael@0 475 return false;
michael@0 476 }
michael@0 477 break;
michael@0 478 }
michael@0 479 case Edit::TOpRaiseToTopChild: {
michael@0 480 MOZ_LAYERS_LOG(("[ParentSide] RaiseToTopChild"));
michael@0 481
michael@0 482 const OpRaiseToTopChild& rtc = edit.get_OpRaiseToTopChild();
michael@0 483 Layer* child = ShadowChild(rtc)->AsLayer();
michael@0 484 if (!child) {
michael@0 485 return false;
michael@0 486 }
michael@0 487 ContainerLayerComposite* container = ShadowContainer(rtc)->AsContainerLayerComposite();
michael@0 488 if (!container ||
michael@0 489 !container->RepositionChild(child, nullptr))
michael@0 490 {
michael@0 491 return false;
michael@0 492 }
michael@0 493 break;
michael@0 494 }
michael@0 495 case Edit::TCompositableOperation: {
michael@0 496 if (!ReceiveCompositableUpdate(edit.get_CompositableOperation(),
michael@0 497 replyv)) {
michael@0 498 return false;
michael@0 499 }
michael@0 500 break;
michael@0 501 }
michael@0 502 case Edit::TOpAttachCompositable: {
michael@0 503 const OpAttachCompositable& op = edit.get_OpAttachCompositable();
michael@0 504 CompositableHost* host = CompositableHost::FromIPDLActor(op.compositableParent());
michael@0 505 if (!Attach(cast(op.layerParent()), host, false)) {
michael@0 506 return false;
michael@0 507 }
michael@0 508 host->SetCompositorID(mLayerManager->GetCompositor()->GetCompositorID());
michael@0 509 break;
michael@0 510 }
michael@0 511 case Edit::TOpAttachAsyncCompositable: {
michael@0 512 const OpAttachAsyncCompositable& op = edit.get_OpAttachAsyncCompositable();
michael@0 513 PCompositableParent* compositableParent = CompositableMap::Get(op.containerID());
michael@0 514 if (!compositableParent) {
michael@0 515 NS_ERROR("CompositableParent not found in the map");
michael@0 516 return false;
michael@0 517 }
michael@0 518 CompositableHost* host = CompositableHost::FromIPDLActor(compositableParent);
michael@0 519 if (!Attach(cast(op.layerParent()), host, true)) {
michael@0 520 return false;
michael@0 521 }
michael@0 522
michael@0 523 host->SetCompositorID(mLayerManager->GetCompositor()->GetCompositorID());
michael@0 524 break;
michael@0 525 }
michael@0 526 default:
michael@0 527 NS_RUNTIMEABORT("not reached");
michael@0 528 }
michael@0 529 }
michael@0 530
michael@0 531 {
michael@0 532 AutoResolveRefLayers resolve(mShadowLayersManager->GetCompositionManager(this));
michael@0 533 layer_manager()->EndTransaction(nullptr, nullptr, LayerManager::END_NO_IMMEDIATE_REDRAW);
michael@0 534 }
michael@0 535
michael@0 536 if (reply) {
michael@0 537 reply->SetCapacity(replyv.size());
michael@0 538 if (replyv.size() > 0) {
michael@0 539 reply->AppendElements(&replyv.front(), replyv.size());
michael@0 540 }
michael@0 541 }
michael@0 542
michael@0 543 // Ensure that any pending operations involving back and front
michael@0 544 // buffers have completed, so that neither process stomps on the
michael@0 545 // other's buffer contents.
michael@0 546 LayerManagerComposite::PlatformSyncBeforeReplyUpdate();
michael@0 547
michael@0 548 mShadowLayersManager->ShadowLayersUpdated(this, targetConfig, isFirstPaint, scheduleComposite);
michael@0 549
michael@0 550 #ifdef COMPOSITOR_PERFORMANCE_WARNING
michael@0 551 int compositeTime = (int)(mozilla::TimeStamp::Now() - updateStart).ToMilliseconds();
michael@0 552 if (compositeTime > 15) {
michael@0 553 printf_stderr("Compositor: Layers update took %i ms (blocking gecko).\n", compositeTime);
michael@0 554 }
michael@0 555 #endif
michael@0 556
michael@0 557 return true;
michael@0 558 }
michael@0 559
michael@0 560 bool
michael@0 561 LayerTransactionParent::RecvSetTestSampleTime(const TimeStamp& aTime)
michael@0 562 {
michael@0 563 return mShadowLayersManager->SetTestSampleTime(this, aTime);
michael@0 564 }
michael@0 565
michael@0 566 bool
michael@0 567 LayerTransactionParent::RecvLeaveTestMode()
michael@0 568 {
michael@0 569 mShadowLayersManager->LeaveTestMode(this);
michael@0 570 return true;
michael@0 571 }
michael@0 572
michael@0 573 bool
michael@0 574 LayerTransactionParent::RecvGetOpacity(PLayerParent* aParent,
michael@0 575 float* aOpacity)
michael@0 576 {
michael@0 577 if (mDestroyed || !layer_manager() || layer_manager()->IsDestroyed()) {
michael@0 578 return false;
michael@0 579 }
michael@0 580
michael@0 581 Layer* layer = cast(aParent)->AsLayer();
michael@0 582 if (!layer) {
michael@0 583 return false;
michael@0 584 }
michael@0 585
michael@0 586 *aOpacity = layer->GetLocalOpacity();
michael@0 587 return true;
michael@0 588 }
michael@0 589
michael@0 590 bool
michael@0 591 LayerTransactionParent::RecvGetAnimationTransform(PLayerParent* aParent,
michael@0 592 MaybeTransform* aTransform)
michael@0 593 {
michael@0 594 if (mDestroyed || !layer_manager() || layer_manager()->IsDestroyed()) {
michael@0 595 return false;
michael@0 596 }
michael@0 597
michael@0 598 Layer* layer = cast(aParent)->AsLayer();
michael@0 599 if (!layer) {
michael@0 600 return false;
michael@0 601 }
michael@0 602
michael@0 603 // This method is specific to transforms applied by animation.
michael@0 604 // This is because this method uses the information stored with an animation
michael@0 605 // such as the origin of the reference frame corresponding to the layer, to
michael@0 606 // recover the untranslated transform from the shadow transform. For
michael@0 607 // transforms that are not set by animation we don't have this information
michael@0 608 // available.
michael@0 609 if (!layer->AsLayerComposite()->GetShadowTransformSetByAnimation()) {
michael@0 610 *aTransform = mozilla::void_t();
michael@0 611 return true;
michael@0 612 }
michael@0 613
michael@0 614 // The following code recovers the untranslated transform
michael@0 615 // from the shadow transform by undoing the translations in
michael@0 616 // AsyncCompositionManager::SampleValue.
michael@0 617
michael@0 618 gfx3DMatrix transform;
michael@0 619 gfx::To3DMatrix(layer->AsLayerComposite()->GetShadowTransform(), transform);
michael@0 620 if (ContainerLayer* c = layer->AsContainerLayer()) {
michael@0 621 // Undo the scale transform applied by AsyncCompositionManager::SampleValue
michael@0 622 transform.ScalePost(1.0f/c->GetInheritedXScale(),
michael@0 623 1.0f/c->GetInheritedYScale(),
michael@0 624 1.0f);
michael@0 625 }
michael@0 626 float scale = 1;
michael@0 627 gfxPoint3D scaledOrigin;
michael@0 628 gfxPoint3D transformOrigin;
michael@0 629 for (uint32_t i=0; i < layer->GetAnimations().Length(); i++) {
michael@0 630 if (layer->GetAnimations()[i].data().type() == AnimationData::TTransformData) {
michael@0 631 const TransformData& data = layer->GetAnimations()[i].data().get_TransformData();
michael@0 632 scale = data.appUnitsPerDevPixel();
michael@0 633 scaledOrigin =
michael@0 634 gfxPoint3D(NS_round(NSAppUnitsToFloatPixels(data.origin().x, scale)),
michael@0 635 NS_round(NSAppUnitsToFloatPixels(data.origin().y, scale)),
michael@0 636 0.0f);
michael@0 637 double cssPerDev =
michael@0 638 double(nsDeviceContext::AppUnitsPerCSSPixel()) / double(scale);
michael@0 639 transformOrigin = data.transformOrigin() * cssPerDev;
michael@0 640 break;
michael@0 641 }
michael@0 642 }
michael@0 643
michael@0 644 // Undo the translation to the origin of the reference frame applied by
michael@0 645 // AsyncCompositionManager::SampleValue
michael@0 646 transform.Translate(-scaledOrigin);
michael@0 647
michael@0 648 // Undo the rebasing applied by
michael@0 649 // nsDisplayTransform::GetResultingTransformMatrixInternal
michael@0 650 transform = nsLayoutUtils::ChangeMatrixBasis(-scaledOrigin - transformOrigin,
michael@0 651 transform);
michael@0 652
michael@0 653 // Convert to CSS pixels (this undoes the operations performed by
michael@0 654 // nsStyleTransformMatrix::ProcessTranslatePart which is called from
michael@0 655 // nsDisplayTransform::GetResultingTransformMatrix)
michael@0 656 double devPerCss =
michael@0 657 double(scale) / double(nsDeviceContext::AppUnitsPerCSSPixel());
michael@0 658 transform._41 *= devPerCss;
michael@0 659 transform._42 *= devPerCss;
michael@0 660 transform._43 *= devPerCss;
michael@0 661
michael@0 662 *aTransform = transform;
michael@0 663 return true;
michael@0 664 }
michael@0 665
michael@0 666 bool
michael@0 667 LayerTransactionParent::RecvSetAsyncScrollOffset(PLayerParent* aLayer,
michael@0 668 const int32_t& aX, const int32_t& aY)
michael@0 669 {
michael@0 670 if (mDestroyed || !layer_manager() || layer_manager()->IsDestroyed()) {
michael@0 671 return false;
michael@0 672 }
michael@0 673
michael@0 674 Layer* layer = cast(aLayer)->AsLayer();
michael@0 675 if (!layer) {
michael@0 676 return false;
michael@0 677 }
michael@0 678 ContainerLayer* containerLayer = layer->AsContainerLayer();
michael@0 679 if (!containerLayer) {
michael@0 680 return false;
michael@0 681 }
michael@0 682 AsyncPanZoomController* controller = containerLayer->GetAsyncPanZoomController();
michael@0 683 if (!controller) {
michael@0 684 return false;
michael@0 685 }
michael@0 686 controller->SetTestAsyncScrollOffset(CSSPoint(aX, aY));
michael@0 687 return true;
michael@0 688 }
michael@0 689
michael@0 690 bool
michael@0 691 LayerTransactionParent::Attach(ShadowLayerParent* aLayerParent,
michael@0 692 CompositableHost* aCompositable,
michael@0 693 bool aIsAsync)
michael@0 694 {
michael@0 695 if (!aCompositable) {
michael@0 696 return false;
michael@0 697 }
michael@0 698
michael@0 699 Layer* baselayer = aLayerParent->AsLayer();
michael@0 700 if (!baselayer) {
michael@0 701 return false;
michael@0 702 }
michael@0 703 LayerComposite* layer = baselayer->AsLayerComposite();
michael@0 704 if (!layer) {
michael@0 705 return false;
michael@0 706 }
michael@0 707
michael@0 708 Compositor* compositor
michael@0 709 = static_cast<LayerManagerComposite*>(aLayerParent->AsLayer()->Manager())->GetCompositor();
michael@0 710
michael@0 711 if (!layer->SetCompositableHost(aCompositable)) {
michael@0 712 // not all layer types accept a compositable, see bug 967824
michael@0 713 return false;
michael@0 714 }
michael@0 715 aCompositable->Attach(aLayerParent->AsLayer(),
michael@0 716 compositor,
michael@0 717 aIsAsync
michael@0 718 ? CompositableHost::ALLOW_REATTACH
michael@0 719 | CompositableHost::KEEP_ATTACHED
michael@0 720 : CompositableHost::NO_FLAGS);
michael@0 721 return true;
michael@0 722 }
michael@0 723
michael@0 724 bool
michael@0 725 LayerTransactionParent::RecvClearCachedResources()
michael@0 726 {
michael@0 727 if (mRoot) {
michael@0 728 // NB: |mRoot| here is the *child* context's root. In this parent
michael@0 729 // context, it's just a subtree root. We need to scope the clear
michael@0 730 // of resources to exactly that subtree, so we specify it here.
michael@0 731 mLayerManager->ClearCachedResources(mRoot);
michael@0 732 }
michael@0 733 return true;
michael@0 734 }
michael@0 735
michael@0 736 bool
michael@0 737 LayerTransactionParent::RecvForceComposite()
michael@0 738 {
michael@0 739 mShadowLayersManager->ForceComposite(this);
michael@0 740 return true;
michael@0 741 }
michael@0 742
michael@0 743
michael@0 744 PGrallocBufferParent*
michael@0 745 LayerTransactionParent::AllocPGrallocBufferParent(const IntSize& aSize,
michael@0 746 const uint32_t& aFormat,
michael@0 747 const uint32_t& aUsage,
michael@0 748 MaybeMagicGrallocBufferHandle* aOutHandle)
michael@0 749 {
michael@0 750 #ifdef MOZ_HAVE_SURFACEDESCRIPTORGRALLOC
michael@0 751 return GrallocBufferActor::Create(aSize, aFormat, aUsage, aOutHandle);
michael@0 752 #else
michael@0 753 NS_RUNTIMEABORT("No gralloc buffers for you");
michael@0 754 return nullptr;
michael@0 755 #endif
michael@0 756 }
michael@0 757
michael@0 758 bool
michael@0 759 LayerTransactionParent::DeallocPGrallocBufferParent(PGrallocBufferParent* actor)
michael@0 760 {
michael@0 761 #ifdef MOZ_HAVE_SURFACEDESCRIPTORGRALLOC
michael@0 762 delete actor;
michael@0 763 return true;
michael@0 764 #else
michael@0 765 NS_RUNTIMEABORT("Um, how did we get here?");
michael@0 766 return false;
michael@0 767 #endif
michael@0 768 }
michael@0 769
michael@0 770 PLayerParent*
michael@0 771 LayerTransactionParent::AllocPLayerParent()
michael@0 772 {
michael@0 773 return new ShadowLayerParent();
michael@0 774 }
michael@0 775
michael@0 776 bool
michael@0 777 LayerTransactionParent::DeallocPLayerParent(PLayerParent* actor)
michael@0 778 {
michael@0 779 delete actor;
michael@0 780 return true;
michael@0 781 }
michael@0 782
michael@0 783 PCompositableParent*
michael@0 784 LayerTransactionParent::AllocPCompositableParent(const TextureInfo& aInfo)
michael@0 785 {
michael@0 786 return CompositableHost::CreateIPDLActor(this, aInfo, 0);
michael@0 787 }
michael@0 788
michael@0 789 bool
michael@0 790 LayerTransactionParent::DeallocPCompositableParent(PCompositableParent* aActor)
michael@0 791 {
michael@0 792 return CompositableHost::DestroyIPDLActor(aActor);
michael@0 793 }
michael@0 794
michael@0 795 PTextureParent*
michael@0 796 LayerTransactionParent::AllocPTextureParent(const SurfaceDescriptor& aSharedData,
michael@0 797 const TextureFlags& aFlags)
michael@0 798 {
michael@0 799 return TextureHost::CreateIPDLActor(this, aSharedData, aFlags);
michael@0 800 }
michael@0 801
michael@0 802 bool
michael@0 803 LayerTransactionParent::DeallocPTextureParent(PTextureParent* actor)
michael@0 804 {
michael@0 805 return TextureHost::DestroyIPDLActor(actor);
michael@0 806 }
michael@0 807
michael@0 808 bool LayerTransactionParent::IsSameProcess() const
michael@0 809 {
michael@0 810 return OtherProcess() == ipc::kInvalidProcessHandle;
michael@0 811 }
michael@0 812
michael@0 813 } // namespace layers
michael@0 814 } // namespace mozilla

mercurial