WebKit Bugzilla
New
Browse
Log In
×
Sign in with GitHub
or
Remember my login
Create Account
·
Forgot Password
Forgotten password account recovery
RESOLVED FIXED
78549
[Chromium] New CCOcclusionTracker class with tests
https://bugs.webkit.org/show_bug.cgi?id=78549
Summary
[Chromium] New CCOcclusionTracker class with tests
Dana Jansens
Reported
2012-02-13 16:20:02 PST
[Chromium] New CCOcclusionTracker class with tests
Attachments
Patch
(84.98 KB, patch)
2012-02-13 16:31 PST
,
Dana Jansens
no flags
Details
Formatted Diff
Diff
Patch
(84.27 KB, patch)
2012-02-14 15:21 PST
,
Dana Jansens
no flags
Details
Formatted Diff
Diff
Patch
(103.79 KB, patch)
2012-02-16 20:17 PST
,
Dana Jansens
no flags
Details
Formatted Diff
Diff
Patch
(100.54 KB, patch)
2012-02-21 19:58 PST
,
Dana Jansens
no flags
Details
Formatted Diff
Diff
Patch for landing
(100.54 KB, patch)
2012-02-22 07:34 PST
,
W. James MacLean
no flags
Details
Formatted Diff
Diff
Patch for landing
(100.54 KB, patch)
2012-02-22 10:00 PST
,
W. James MacLean
no flags
Details
Formatted Diff
Diff
Show Obsolete
(5)
View All
Add attachment
proposed patch, testcase, etc.
Dana Jansens
Comment 1
2012-02-13 16:31:19 PST
Created
attachment 126861
[details]
Patch Create the CCOcclusionTracker object, along with unit tests to verify its functionality. The object encapsulates the logic of CCLayerTreeHost's paint culling, and CCQuadCuller's draw culling together in an object that can be used for both scenarios. It tracks occlusion within the target surface, and within screen space. You can do a simple occluded() true/false test, or give it a rect in content space, and it will return a sub-rect that contains all the unoccluded parts (in both the target surface and screen space) of the original rect.
Dana Jansens
Comment 2
2012-02-13 18:09:18 PST
Comment on
attachment 126861
[details]
Patch For @wjmaclean review
W. James MacLean
Comment 3
2012-02-14 13:59:46 PST
Overall comments: Generally, looks good. I've heard some murmurings that "RenderSurfaces" could be on the road to extinction. Best to find out if that's true, and how (if at all) it will affect this CL. It seems expensive computing both both "Screen-then-Target-surface, or Target-surface-then-Screen" in unoccluded{Surface}ContentRect. Is there no way to avoid this and predict the correct (conservative) occlusion in advance?
> Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.h
>
> 43 template<typename RenderSurfaceType> void enterTargetRenderSurface(RenderSurfaceType* newTarget); > 44 template<typename RenderSurfaceType> void leaveToTargetRenderSurface(RenderSurfaceType* newTarget);
Seems awkward ... seems like they're the same, just the second assumes we're already in a target surface? Or are the names just misleading?
> 51 template<typename LayerType> bool occluded(LayerType*, const IntRect& contentRect) const; > 52 // Gives an unoccluded sub-rect of |contentRect| in the content space of the layer. Used when considering occlusion for a layer that paints/draws something.
Comment doesn't seem to match.
> 65 FloatQuad transformedBoundsQuad = transform.mapQuad(FloatQuad(centeredBounds)); > 66 if (!transformedBoundsQuad.isRectilinear()) > 67 return Region();
Add comment specifying what transform types will lead to rectilinear bounds.
> 118 // Scale from content space to layer space > 119 transform.scaleNonUniform(boundsInLayerSpace.width() / static_cast<double>(boundsInContentSpace.width()), > 120 boundsInLayerSpace.height() / static_cast<double>(boundsInContentSpace.height()));
Can this potentially fail for non-trivial transforms? E.g. rotation? Or is the transform from content to layer space always assumed to be translation + scale?I.e., how do we know when this is safe or is it always? Ditto for similar computations below. Nice occlusion diagrams :-)
Dana Jansens
Comment 4
2012-02-14 15:09:53 PST
(In reply to
comment #3
)
> Overall comments: > > Generally, looks good.
Thanks!
> I've heard some murmurings that "RenderSurfaces" could be on the road to extinction. Best to find out if that's true, and how (if at all) it will affect this CL.
They are getting layers so that we don't have all this layer-like state on a RenderSurface. In this case, it will change the loops which call CCOcclusion tracker, and clean them up some hopefully. The CCOcclusionTracker should be minimally affected, mostly in the transform calculation functions.
> It seems expensive computing both both "Screen-then-Target-surface, or Target-surface-then-Screen" in unoccluded{Surface}ContentRect. Is there no way to avoid this and predict the correct (conservative) occlusion in advance?
Described it to @vollick briefly and he helped me see I can return the Rect for screen and target, and just take the intersection back in content space. This passes the unit tests for these functions that are somewhat particular, so it will be accurate enough. Thanks.
> > Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.h > > > > 43 template<typename RenderSurfaceType> void enterTargetRenderSurface(RenderSurfaceType* newTarget); > > 44 template<typename RenderSurfaceType> void leaveToTargetRenderSurface(RenderSurfaceType* newTarget); > > Seems awkward ... seems like they're the same, just the second assumes we're already in a target surface? Or are the names just misleading?
The first is done when we see a new layer. It says "hey we're in this target surface (if we weren't already)". The second is done when we see a contributing layer. It says "hey we were in this target surface but now we're done with it, and moving up to its parent". It's a merge-up operation. I'll add comments.
> > 51 template<typename LayerType> bool occluded(LayerType*, const IntRect& contentRect) const; > > 52 // Gives an unoccluded sub-rect of |contentRect| in the content space of the layer. Used when considering occlusion for a layer that paints/draws something. > > Comment doesn't seem to match.
The comment matches the function below it. I'll add one for occluded() too.
> > 65 FloatQuad transformedBoundsQuad = transform.mapQuad(FloatQuad(centeredBounds)); > > 66 if (!transformedBoundsQuad.isRectilinear()) > > 67 return Region(); > > Add comment specifying what transform types will lead to rectilinear bounds.
done.
> > 118 // Scale from content space to layer space > > 119 transform.scaleNonUniform(boundsInLayerSpace.width() / static_cast<double>(boundsInContentSpace.width()), > > 120 boundsInLayerSpace.height() / static_cast<double>(boundsInContentSpace.height())); > > Can this potentially fail for non-trivial transforms? E.g. rotation? Or is the transform from content to layer space always assumed to be translation + scale?I.e., how do we know when this is safe or is it always? Ditto for similar computations below.
content<->layer space is only a scale.
> Nice occlusion diagrams :-)
Dana Jansens
Comment 5
2012-02-14 15:21:46 PST
Created
attachment 127055
[details]
Patch For @enne review.
Dana Jansens
Comment 6
2012-02-16 20:17:54 PST
Created
attachment 127505
[details]
Patch - make pointers const all over - add the CSS filter stuff that was added to CCLayerTreeHost, and unit test for it! - add finishedTargetRenderSurface() to do cleanup/processing for the surface once all layers have been visited in it. - add surfaceOccluded() which tells if part of the surface is occluded (by things outside the surface), and unit tests for this! and.. - add currentOcclusionInScreenSpace() and currentOcclusionInTargetSpace() temporarily to make transition CLs easier.
Adrienne Walker
Comment 7
2012-02-21 19:00:12 PST
Comment on
attachment 127505
[details]
Patch View in context:
https://bugs.webkit.org/attachment.cgi?id=127505&action=review
So, this is just a patch to land independent functionality and then you'll land another patch to transition to switch over to using this? Yay, for lots of tests. :)
> Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.cpp:210 > + if (!transformedQuad.isRectilinear()) > + return false; > + return occlusion.contains(transformedQuad.enclosingBoundingBox());
Why the conditional? Even if not rectilinear, if the occlusion still contains the enclosing bounding box, then this contentRect is still occluded, yeah?
> Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.cpp:275 > + // The use of enclosingIntRect, with floating point rounding, can give us a result that is not a sub-rect of contentRect. Shrink the result > + // down so that contentRect contains the result we return. > + int x = max(unoccludedRect.x(), contentRect.x()); > + int y = max(unoccludedRect.y(), contentRect.y()); > + int maxX = min(unoccludedRect.maxX(), contentRect.maxX()); > + int maxY = min(unoccludedRect.maxY(), contentRect.maxY()); > + return IntRect(x, y, maxX - x, maxY - y);
Why not just unoccludedRect.intersect(contentRect)?
> Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.cpp:297 > +IntRect CCOcclusionTrackerBase::surfaceUnoccludedContentRect(const LayerType* layer, const IntRect& surfaceContentRect) const
Where is this function going to get used? The other functions seem like a mirror of existing functionality in paint culling, but this and surfaceOccluded seems new and I'm not sure where they fit in the culling algorithm. Also, can you write a test for this function that does more than take in a rect and spit the same rect back out?
> Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.h:80 > + typedef void RenderSurfaceVoidType; > + > + struct StackObject { > + const RenderSurfaceVoidType* surface;
Along with the fact that a pair of types gets used consistently across all these functions, this piece of code says to me really says that your class should be templated. Maybe I'm missing something, but I don't see a need for void pointer shenanigans. Also, if the class were templated, you could just typedef CCOcclusionTracker(Impl) rather than adding boilerplate functions that thunk through.
Adrienne Walker
Comment 8
2012-02-21 19:47:36 PST
Comment on
attachment 127505
[details]
Patch View in context:
https://bugs.webkit.org/attachment.cgi?id=127505&action=review
>> Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.cpp:297 >> +IntRect CCOcclusionTrackerBase::surfaceUnoccludedContentRect(const LayerType* layer, const IntRect& surfaceContentRect) const > > Where is this function going to get used? The other functions seem like a mirror of existing functionality in paint culling, but this and surfaceOccluded seems new and I'm not sure where they fit in the culling algorithm. > > Also, can you write a test for this function that does more than take in a rect and spit the same rect back out?
Oops, line 870 does have a such a test. My bad.
Dana Jansens
Comment 9
2012-02-21 19:53:25 PST
(In reply to
comment #7
)
> (From update of
attachment 127505
[details]
) > View in context:
https://bugs.webkit.org/attachment.cgi?id=127505&action=review
> > So, this is just a patch to land independent functionality and then you'll land another patch to transition to switch over to using this?
Precisely. I'll make sure it's at feature-parity with any changes 'upstream' as I use it to replace existing code, and verify that any unit tests removed have the same cases covered for this class as I go.
> Yay, for lots of tests. :) > > > Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.cpp:210 > > + if (!transformedQuad.isRectilinear()) > > + return false; > > + return occlusion.contains(transformedQuad.enclosingBoundingBox()); > > Why the conditional? Even if not rectilinear, if the occlusion still contains the enclosing bounding box, then this contentRect is still occluded, yeah?
Yep! Thanks.
> > Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.cpp:275 > > + // The use of enclosingIntRect, with floating point rounding, can give us a result that is not a sub-rect of contentRect. Shrink the result > > + // down so that contentRect contains the result we return. > > + int x = max(unoccludedRect.x(), contentRect.x()); > > + int y = max(unoccludedRect.y(), contentRect.y()); > > + int maxX = min(unoccludedRect.maxX(), contentRect.maxX()); > > + int maxY = min(unoccludedRect.maxY(), contentRect.maxY()); > > + return IntRect(x, y, maxX - x, maxY - y); > > Why not just unoccludedRect.intersect(contentRect)?
Oh, duh.. thank you :)
> > Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.cpp:297 > > +IntRect CCOcclusionTrackerBase::surfaceUnoccludedContentRect(const LayerType* layer, const IntRect& surfaceContentRect) const > > Where is this function going to get used? The other functions seem like a mirror of existing functionality in paint culling, but this and surfaceOccluded seems new and I'm not sure where they fit in the culling algorithm.
I am planning to use it for culling of the surface itself on draw side. Right now we don't cull surface quads at all, but we can cull them based on things outside the surface in the future. The bool surfaceOccluded() method probably won't be used at the moment, but I included it just for completeness.
> Also, can you write a test for this function that does more than take in a rect and spit the same rect back out?
As we discussed, CCOcclusionTrackerTest.surfaceOcclusionInScreenSpace is meant to verify that this function works as intended. That said, if you can think of something more to test I'm very happy to!
> > Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.h:80 > > + typedef void RenderSurfaceVoidType; > > + > > + struct StackObject { > > + const RenderSurfaceVoidType* surface; > > Along with the fact that a pair of types gets used consistently across all these functions, this piece of code says to me really says that your class should be templated. Maybe I'm missing something, but I don't see a need for void pointer shenanigans. > > Also, if the class were templated, you could just typedef CCOcclusionTracker(Impl) rather than adding boilerplate functions that thunk through.
As per offline discussion, going with templates and typedefs. It really cleaned up the .h so yay.
Dana Jansens
Comment 10
2012-02-21 19:58:01 PST
Created
attachment 128120
[details]
Patch For @enne review. Comments addressed!
Adrienne Walker
Comment 11
2012-02-21 20:38:06 PST
Comment on
attachment 128120
[details]
Patch Thanks for those changes! I don't think I have anything else to add. :)
Dana Jansens
Comment 12
2012-02-21 21:06:42 PST
Comment on
attachment 128120
[details]
Patch Thanks enne! For @jamesr review then.
James Robinson
Comment 13
2012-02-21 23:05:15 PST
Comment on
attachment 128120
[details]
Patch View in context:
https://bugs.webkit.org/attachment.cgi?id=128120&action=review
Works for me! R=me with one style nit, feel free to address it when you address the other FIXME in that header.
> Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.h:94 > + WTF_MAKE_NONCOPYABLE(CCOcclusionTrackerBase);
style nit: normally we put this right below the class declaration and above the first public:
WebKit Review Bot
Comment 14
2012-02-21 23:59:35 PST
Comment on
attachment 128120
[details]
Patch Clearing flags on attachment: 128120 Committed
r108453
: <
http://trac.webkit.org/changeset/108453
>
WebKit Review Bot
Comment 15
2012-02-21 23:59:42 PST
All reviewed patches have been landed. Closing bug.
Yuta Kitamura
Comment 16
2012-02-22 01:37:02 PST
Hi, Chromium's webkit_unit_tests started to fail since
r108453
:
http://build.chromium.org/p/chromium.webkit/builders/Webkit%20Linux%20%28dbg%29/builds/3657/steps/webkit_unit_tests/logs/stdio
[ RUN ] CCOcclusionTrackerTest.surfaceOcclusionWithOverlappingSiblingSurfaces ASSERTION FAILED: layer->targetRenderSurface() == m_stack.last().surface third_party/WebKit/Source/WebCore/platform/graphics/chromium/cc/CCOcclusionTracker.cpp(217) : bool WebCore::CCOcclusionTrackerBase<LayerType, RenderSurfaceType>::occluded(const LayerType*, const WebCore::IntRect&) const [with LayerType = WebCore::LayerChromium, RenderSurfaceType = WebCore::RenderSurfaceChromium] 1 0x1140ffc 2 0x546edc 3 0x791cc1 4 0x78e99e 5 0x7833a2 6 0x783bc6 7 0x7842bc 8 0x789093 9 0x792ebb 10 0x78f361 11 0x787bb0 12 0x7a31d5 13 0x41fc7d 14 0x7f63e50c2c4d __libc_start_main 15 0x41fb79 [56389:56389:0222/011121:15415134960585:ERROR:process_util_posix.cc(142)] Received signal 11 base::debug::StackTrace::StackTrace() [0x1f69a3e] base::(anonymous namespace)::StackDumpSignalHandler() [0x1f1a9a5] 0x7f63e50d7af0 WebCore::CCOcclusionTrackerBase<>::occluded() [0x1141006] (anonymous namespace)::CCOcclusionTrackerTest_surfaceOcclusionWithOverlappingSiblingSurfaces_Test::TestBody() [0x546edc] testing::internal::HandleSehExceptionsInMethodIfSupported<>() [0x791cc1] testing::internal::HandleExceptionsInMethodIfSupported<>() [0x78e99e] testing::Test::Run() [0x7833a2] testing::TestInfo::Run() [0x783bc6] testing::TestCase::Run() [0x7842bc] testing::internal::UnitTestImpl::RunAllTests() [0x789093] testing::internal::HandleSehExceptionsInMethodIfSupported<>() [0x792ebb] testing::internal::HandleExceptionsInMethodIfSupported<>() [0x78f361] testing::UnitTest::Run() [0x787bb0] base::TestSuite::Run() [0x7a31d5] main [0x41fc7d] 0x7f63e50c2c4d 0x41fb79 Furthermore, one layout test started to fail and I'm suspecting this could be also due to
r108453
(not 100% sure though):
http://test-results.appspot.com/dashboards/flakiness_dashboard.html#showExpectations=true&tests=fast%2Fcanvas%2Fwebgl%2Ftex-image-with-format-and-type.html
Could you take a look and fix them ASAP? I'm going to roll out the change unless I hear back from you.
Yuta Kitamura
Comment 17
2012-02-22 01:48:59 PST
I'm rolling out the change. Please fix the issue and land again.
Yuta Kitamura
Comment 18
2012-02-22 01:59:45 PST
Reverted
r108453
for reason: Broke Chromium's webkit_unit_tests. Committed
r108467
: <
http://trac.webkit.org/changeset/108467
>
Yuta Kitamura
Comment 19
2012-02-22 04:37:09 PST
(In reply to
comment #16
)
> Furthermore, one layout test started to fail and I'm suspecting this could be also due to
r108453
(not 100% sure though):
This wasn't true, because the test keeps failing even after the rollout.
Dana Jansens
Comment 20
2012-02-22 07:32:25 PST
Comment on
attachment 128120
[details]
Patch Ok, going to resubmit then.
W. James MacLean
Comment 21
2012-02-22 07:34:42 PST
Created
attachment 128213
[details]
Patch for landing
WebKit Review Bot
Comment 22
2012-02-22 07:39:55 PST
Comment on
attachment 128213
[details]
Patch for landing Rejecting
attachment 128213
[details]
from commit-queue. Failed to run "['/mnt/git/webkit-commit-queue/Tools/Scripts/webkit-patch', '--status-host=queues.webkit.org', '-..." exit_code: 1 ERROR: /mnt/git/webkit-commit-queue/Source/WebCore/ChangeLog neither lists a valid reviewer nor contains the string "Unreviewed" or "Rubber stamp" (case insensitive). Full output:
http://queues.webkit.org/results/11560504
W. James MacLean
Comment 23
2012-02-22 10:00:21 PST
Created
attachment 128236
[details]
Patch for landing
WebKit Review Bot
Comment 24
2012-02-22 10:45:42 PST
Comment on
attachment 128236
[details]
Patch for landing Clearing flags on attachment: 128236 Committed
r108521
: <
http://trac.webkit.org/changeset/108521
>
WebKit Review Bot
Comment 25
2012-02-22 10:45:49 PST
All reviewed patches have been landed. Closing bug.
Yuta Kitamura
Comment 26
2012-02-22 17:38:49 PST
(In reply to
comment #20
)
> (From update of
attachment 128120
[details]
) > Ok, going to resubmit then.
I'm sorry I wasn't clear, but I meant only layout test failure wasn't your fault. Your change still causes the following assertion failure. ASSERTION FAILED: layer->targetRenderSurface() == m_stack.last().surface Please investigate further as soon as possible. This error causes webkit_unit_tests to abort in the middle of the run, which is undesirable.
Yuta Kitamura
Comment 27
2012-02-22 18:21:58 PST
Um, you seem to fix the bug in
r108587
(
bug 79275
). Please leave some comments to show the linkage of bugs, and notify WebKit gardeners about build fixes from next time. Thanks.
Dana Jansens
Comment 28
2012-02-22 19:05:35 PST
Yup. Sorry! Enne knew about it at least, but I should have linked them.
Note
You need to
log in
before you can comment on or make changes to this bug.
Top of Page
Format For Printing
XML
Clone This Bug