Fix leak of SkPathRefs
bug:15939479
SkPath objects owned by DisplayListOps weren't being torn down, and
thus weren't releasing their SkPathRef innards.
Change-Id: I2581e124600a93a399ef3251f456c02ab52839a8
diff --git a/libs/hwui/RenderNode.cpp b/libs/hwui/RenderNode.cpp
index f48b774..23940ee 100644
--- a/libs/hwui/RenderNode.cpp
+++ b/libs/hwui/RenderNode.cpp
@@ -534,6 +534,7 @@
inline void endMark() {}
inline int level() { return mLevel; }
inline int replayFlags() { return mDeferStruct.mReplayFlags; }
+ inline SkPath* allocPathForFrame() { return mDeferStruct.allocPathForFrame(); }
private:
DeferStateStruct& mDeferStruct;
@@ -564,6 +565,7 @@
}
inline int level() { return mLevel; }
inline int replayFlags() { return mReplayStruct.mReplayFlags; }
+ inline SkPath* allocPathForFrame() { return mReplayStruct.allocPathForFrame(); }
private:
ReplayStateStruct& mReplayStruct;
@@ -612,14 +614,24 @@
mat4 shadowMatrixZ(transformFromParent);
applyViewPropertyTransforms(shadowMatrixZ, true);
- const SkPath* outlinePath = properties().getOutline().getPath();
+ const SkPath* casterOutlinePath = properties().getOutline().getPath();
const SkPath* revealClipPath = properties().getRevealClip().getPath();
if (revealClipPath && revealClipPath->isEmpty()) return;
float casterAlpha = properties().getAlpha() * properties().getOutline().getAlpha();
+
+ const SkPath* outlinePath = casterOutlinePath;
+ if (revealClipPath) {
+ // if we can't simply use the caster's path directly, create a temporary one
+ SkPath* frameAllocatedPath = handler.allocPathForFrame();
+
+ // intersect the outline with the convex reveal clip
+ Op(*casterOutlinePath, *revealClipPath, kIntersect_PathOp, frameAllocatedPath);
+ outlinePath = frameAllocatedPath;
+ }
+
DisplayListOp* shadowOp = new (handler.allocator()) DrawShadowOp(
- shadowMatrixXY, shadowMatrixZ, casterAlpha,
- outlinePath, revealClipPath);
+ shadowMatrixXY, shadowMatrixZ, casterAlpha, outlinePath);
handler(shadowOp, PROPERTY_SAVECOUNT, properties().getClipToBounds());
}