diff --git a/libs/hwui/Android.mk b/libs/hwui/Android.mk
index 1618110..06e658d 100644
--- a/libs/hwui/Android.mk
+++ b/libs/hwui/Android.mk
@@ -34,7 +34,6 @@
 		ProgramCache.cpp \
 		RenderBufferCache.cpp \
 		ResourceCache.cpp \
-		ShapeCache.cpp \
 		SkiaColorFilter.cpp \
 		SkiaShader.cpp \
 		Snapshot.cpp \
diff --git a/libs/hwui/Caches.cpp b/libs/hwui/Caches.cpp
index 4642a4f..dc3a4e2 100644
--- a/libs/hwui/Caches.cpp
+++ b/libs/hwui/Caches.cpp
@@ -224,16 +224,6 @@
             gradientCache.getSize(), gradientCache.getMaxSize());
     log.appendFormat("  PathCache            %8d / %8d\n",
             pathCache.getSize(), pathCache.getMaxSize());
-    log.appendFormat("  CircleShapeCache     %8d / %8d\n",
-            circleShapeCache.getSize(), circleShapeCache.getMaxSize());
-    log.appendFormat("  OvalShapeCache       %8d / %8d\n",
-            ovalShapeCache.getSize(), ovalShapeCache.getMaxSize());
-    log.appendFormat("  RoundRectShapeCache  %8d / %8d\n",
-            roundRectShapeCache.getSize(), roundRectShapeCache.getMaxSize());
-    log.appendFormat("  RectShapeCache       %8d / %8d\n",
-            rectShapeCache.getSize(), rectShapeCache.getMaxSize());
-    log.appendFormat("  ArcShapeCache        %8d / %8d\n",
-            arcShapeCache.getSize(), arcShapeCache.getMaxSize());
     log.appendFormat("  TextDropShadowCache  %8d / %8d\n", dropShadowCache.getSize(),
             dropShadowCache.getMaxSize());
     for (uint32_t i = 0; i < fontRenderer->getFontRendererCount(); i++) {
@@ -253,11 +243,6 @@
     total += gradientCache.getSize();
     total += pathCache.getSize();
     total += dropShadowCache.getSize();
-    total += roundRectShapeCache.getSize();
-    total += circleShapeCache.getSize();
-    total += ovalShapeCache.getSize();
-    total += rectShapeCache.getSize();
-    total += arcShapeCache.getSize();
     for (uint32_t i = 0; i < fontRenderer->getFontRendererCount(); i++) {
         total += fontRenderer->getFontRendererSize(i);
     }
@@ -325,11 +310,6 @@
             fontRenderer->flush();
             textureCache.flush();
             pathCache.clear();
-            roundRectShapeCache.clear();
-            circleShapeCache.clear();
-            ovalShapeCache.clear();
-            rectShapeCache.clear();
-            arcShapeCache.clear();
             // fall through
         case kFlushMode_Layers:
             layerCache.clear();
diff --git a/libs/hwui/Caches.h b/libs/hwui/Caches.h
index dc32a7e..63836c1 100644
--- a/libs/hwui/Caches.h
+++ b/libs/hwui/Caches.h
@@ -36,7 +36,6 @@
 #include "GradientCache.h"
 #include "PatchCache.h"
 #include "ProgramCache.h"
-#include "ShapeCache.h"
 #include "PathCache.h"
 #include "TextDropShadowCache.h"
 #include "FboCache.h"
@@ -269,11 +268,6 @@
     GradientCache gradientCache;
     ProgramCache programCache;
     PathCache pathCache;
-    RoundRectShapeCache roundRectShapeCache;
-    CircleShapeCache circleShapeCache;
-    OvalShapeCache ovalShapeCache;
-    RectShapeCache rectShapeCache;
-    ArcShapeCache arcShapeCache;
     PatchCache patchCache;
     TextDropShadowCache dropShadowCache;
     FboCache fboCache;
diff --git a/libs/hwui/Debug.h b/libs/hwui/Debug.h
index 773fe82..46beb94 100644
--- a/libs/hwui/Debug.h
+++ b/libs/hwui/Debug.h
@@ -64,7 +64,7 @@
 #define DEBUG_PATCHES_EMPTY_VERTICES 0
 
 // Turn on to display debug info about shapes
-#define DEBUG_SHAPES 0
+#define DEBUG_PATHS 0
 
 // Turn on to display debug info about textures
 #define DEBUG_TEXTURES 0
diff --git a/libs/hwui/DeferredDisplayList.cpp b/libs/hwui/DeferredDisplayList.cpp
index 8455545..5c5bf45 100644
--- a/libs/hwui/DeferredDisplayList.cpp
+++ b/libs/hwui/DeferredDisplayList.cpp
@@ -17,6 +17,8 @@
 #define LOG_TAG "OpenGLRenderer"
 #define ATRACE_TAG ATRACE_TAG_VIEW
 
+#include <SkCanvas.h>
+
 #include <utils/Trace.h>
 
 #include "Debug.h"
diff --git a/libs/hwui/DisplayList.cpp b/libs/hwui/DisplayList.cpp
index 4743f58..4944fe8 100644
--- a/libs/hwui/DisplayList.cpp
+++ b/libs/hwui/DisplayList.cpp
@@ -14,6 +14,8 @@
  * limitations under the License.
  */
 
+#include <SkCanvas.h>
+
 #include "Debug.h"
 #include "DisplayList.h"
 #include "DisplayListOp.h"
@@ -121,9 +123,7 @@
     }
 
     for (size_t i = 0; i < mPaths.size(); i++) {
-        SkPath* path = mPaths.itemAt(i);
-        caches.pathCache.remove(path);
-        delete path;
+        delete mPaths.itemAt(i);
     }
 
     for (size_t i = 0; i < mMatrices.size(); i++) {
diff --git a/libs/hwui/DisplayListRenderer.cpp b/libs/hwui/DisplayListRenderer.cpp
index 11a655e..8b5b54c 100644
--- a/libs/hwui/DisplayListRenderer.cpp
+++ b/libs/hwui/DisplayListRenderer.cpp
@@ -17,6 +17,7 @@
 #define LOG_TAG "OpenGLRenderer"
 
 #include <SkCamera.h>
+#include <SkCanvas.h>
 
 #include <private/hwui/DrawGlInfo.h>
 
diff --git a/libs/hwui/OpenGLRenderer.cpp b/libs/hwui/OpenGLRenderer.cpp
index e576f76..c310c4c 100644
--- a/libs/hwui/OpenGLRenderer.cpp
+++ b/libs/hwui/OpenGLRenderer.cpp
@@ -2257,9 +2257,11 @@
     // TODO: try clipping large paths to viewport
     PathTessellator::tessellatePath(path, paint, mSnapshot->transform, vertexBuffer);
 
-    SkRect bounds = path.getBounds();
-    PathTessellator::expandBoundsForStroke(bounds, paint, false);
-    dirtyLayer(bounds.fLeft, bounds.fTop, bounds.fRight, bounds.fBottom, currentTransform());
+    if (hasLayer()) {
+        SkRect bounds = path.getBounds();
+        PathTessellator::expandBoundsForStroke(bounds, paint, false);
+        dirtyLayer(bounds.fLeft, bounds.fTop, bounds.fRight, bounds.fBottom, currentTransform());
+    }
 
     return drawVertexBuffer(vertexBuffer, paint);
 }
@@ -2389,7 +2391,7 @@
 
     if (p->getPathEffect() != 0) {
         mCaches.activeTexture(0);
-        const PathTexture* texture = mCaches.roundRectShapeCache.getRoundRect(
+        const PathTexture* texture = mCaches.pathCache.getRoundRect(
                 right - left, bottom - top, rx, ry, p);
         return drawShape(left, top, texture, p);
     }
@@ -2413,7 +2415,7 @@
     }
     if (p->getPathEffect() != 0) {
         mCaches.activeTexture(0);
-        const PathTexture* texture = mCaches.circleShapeCache.getCircle(radius, p);
+        const PathTexture* texture = mCaches.pathCache.getCircle(radius, p);
         return drawShape(x - radius, y - radius, texture, p);
     }
 
@@ -2434,7 +2436,7 @@
 
     if (p->getPathEffect() != 0) {
         mCaches.activeTexture(0);
-        const PathTexture* texture = mCaches.ovalShapeCache.getOval(right - left, bottom - top, p);
+        const PathTexture* texture = mCaches.pathCache.getOval(right - left, bottom - top, p);
         return drawShape(left, top, texture, p);
     }
 
@@ -2460,7 +2462,7 @@
     // TODO: support fills (accounting for concavity if useCenter && sweepAngle > 180)
     if (p->getStyle() != SkPaint::kStroke_Style || p->getPathEffect() != 0 || useCenter) {
         mCaches.activeTexture(0);
-        const PathTexture* texture = mCaches.arcShapeCache.getArc(right - left, bottom - top,
+        const PathTexture* texture = mCaches.pathCache.getArc(right - left, bottom - top,
                 startAngle, sweepAngle, useCenter, p);
         return drawShape(left, top, texture, p);
     }
@@ -2495,7 +2497,7 @@
                 p->getStrokeMiter() != SkPaintDefaults_MiterLimit) {
             mCaches.activeTexture(0);
             const PathTexture* texture =
-                    mCaches.rectShapeCache.getRect(right - left, bottom - top, p);
+                    mCaches.pathCache.getRect(right - left, bottom - top, p);
             return drawShape(left, top, texture, p);
         }
 
diff --git a/libs/hwui/PathCache.cpp b/libs/hwui/PathCache.cpp
index fb687cd..490c22a 100644
--- a/libs/hwui/PathCache.cpp
+++ b/libs/hwui/PathCache.cpp
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2010 The Android Open Source Project
+ * Copyright (C) 2013 The Android Open Source Project
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
@@ -15,19 +15,301 @@
  */
 
 #define LOG_TAG "OpenGLRenderer"
+#define ATRACE_TAG ATRACE_TAG_VIEW
 
-#include <utils/Mutex.h>
+#include <SkBitmap.h>
+#include <SkCanvas.h>
+#include <SkPaint.h>
+#include <SkPath.h>
+#include <SkRect.h>
 
-#include <sys/sysinfo.h>
+#include <utils/JenkinsHash.h>
+#include <utils/Trace.h>
 
 #include "Caches.h"
 #include "PathCache.h"
-#include "Properties.h"
+
+#include "thread/Signal.h"
+#include "thread/Task.h"
+#include "thread/TaskProcessor.h"
 
 namespace android {
 namespace uirenderer {
 
 ///////////////////////////////////////////////////////////////////////////////
+// Cache entries
+///////////////////////////////////////////////////////////////////////////////
+
+PathDescription::PathDescription():
+        type(kShapeNone),
+        join(SkPaint::kDefault_Join),
+        cap(SkPaint::kDefault_Cap),
+        style(SkPaint::kFill_Style),
+        miter(4.0f),
+        strokeWidth(1.0f),
+        pathEffect(NULL) {
+    memset(&shape, 0, sizeof(Shape));
+}
+
+PathDescription::PathDescription(ShapeType type, SkPaint* paint):
+        type(type),
+        join(paint->getStrokeJoin()),
+        cap(paint->getStrokeCap()),
+        style(paint->getStyle()),
+        miter(paint->getStrokeMiter()),
+        strokeWidth(paint->getStrokeWidth()),
+        pathEffect(paint->getPathEffect()) {
+    memset(&shape, 0, sizeof(Shape));
+}
+
+hash_t PathDescription::hash() const {
+    uint32_t hash = JenkinsHashMix(0, type);
+    hash = JenkinsHashMix(hash, join);
+    hash = JenkinsHashMix(hash, cap);
+    hash = JenkinsHashMix(hash, style);
+    hash = JenkinsHashMix(hash, android::hash_type(miter));
+    hash = JenkinsHashMix(hash, android::hash_type(strokeWidth));
+    hash = JenkinsHashMix(hash, android::hash_type(pathEffect));
+    hash = JenkinsHashMixBytes(hash, (uint8_t*) &shape, sizeof(Shape));
+    return JenkinsHashWhiten(hash);
+}
+
+int PathDescription::compare(const PathDescription& rhs) const {
+    return memcmp(this, &rhs, sizeof(PathDescription));
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// Utilities
+///////////////////////////////////////////////////////////////////////////////
+
+bool PathCache::canDrawAsConvexPath(SkPath* path, SkPaint* paint) {
+    // NOTE: This should only be used after PathTessellator handles joins properly
+    return paint->getPathEffect() == NULL && path->getConvexity() == SkPath::kConvex_Convexity;
+}
+
+void PathCache::computePathBounds(const SkPath* path, const SkPaint* paint,
+        float& left, float& top, float& offset, uint32_t& width, uint32_t& height) {
+    const SkRect& bounds = path->getBounds();
+    PathCache::computeBounds(bounds, paint, left, top, offset, width, height);
+}
+
+void PathCache::computeBounds(const SkRect& bounds, const SkPaint* paint,
+        float& left, float& top, float& offset, uint32_t& width, uint32_t& height) {
+    const float pathWidth = fmax(bounds.width(), 1.0f);
+    const float pathHeight = fmax(bounds.height(), 1.0f);
+
+    left = bounds.fLeft;
+    top = bounds.fTop;
+
+    offset = (int) floorf(fmax(paint->getStrokeWidth(), 1.0f) * 1.5f + 0.5f);
+
+    width = uint32_t(pathWidth + offset * 2.0 + 0.5);
+    height = uint32_t(pathHeight + offset * 2.0 + 0.5);
+}
+
+static void initBitmap(SkBitmap& bitmap, uint32_t width, uint32_t height) {
+    bitmap.setConfig(SkBitmap::kA8_Config, width, height);
+    bitmap.allocPixels();
+    bitmap.eraseColor(0);
+}
+
+static void initPaint(SkPaint& paint) {
+    // Make sure the paint is opaque, color, alpha, filter, etc.
+    // will be applied later when compositing the alpha8 texture
+    paint.setColor(0xff000000);
+    paint.setAlpha(255);
+    paint.setColorFilter(NULL);
+    paint.setMaskFilter(NULL);
+    paint.setShader(NULL);
+    SkXfermode* mode = SkXfermode::Create(SkXfermode::kSrc_Mode);
+    SkSafeUnref(paint.setXfermode(mode));
+}
+
+static void drawPath(const SkPath *path, const SkPaint* paint, SkBitmap& bitmap,
+        float left, float top, float offset, uint32_t width, uint32_t height) {
+    initBitmap(bitmap, width, height);
+
+    SkPaint pathPaint(*paint);
+    initPaint(pathPaint);
+
+    SkCanvas canvas(bitmap);
+    canvas.translate(-left + offset, -top + offset);
+    canvas.drawPath(*path, pathPaint);
+}
+
+static PathTexture* createTexture(float left, float top, float offset,
+        uint32_t width, uint32_t height, uint32_t id) {
+    PathTexture* texture = new PathTexture();
+    texture->left = left;
+    texture->top = top;
+    texture->offset = offset;
+    texture->width = width;
+    texture->height = height;
+    texture->generation = id;
+    return texture;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// Cache constructor/destructor
+///////////////////////////////////////////////////////////////////////////////
+
+PathCache::PathCache():
+        mCache(LruCache<PathDescription, PathTexture*>::kUnlimitedCapacity),
+        mSize(0), mMaxSize(MB(DEFAULT_PATH_CACHE_SIZE)) {
+    char property[PROPERTY_VALUE_MAX];
+    if (property_get(PROPERTY_PATH_CACHE_SIZE, property, NULL) > 0) {
+        INIT_LOGD("  Setting %s cache size to %sMB", name, property);
+        setMaxSize(MB(atof(property)));
+    } else {
+        INIT_LOGD("  Using default %s cache size of %.2fMB", name, DEFAULT_PATH_CACHE_SIZE);
+    }
+    init();
+}
+
+PathCache::~PathCache() {
+    mCache.clear();
+}
+
+void PathCache::init() {
+    mCache.setOnEntryRemovedListener(this);
+
+    GLint maxTextureSize;
+    glGetIntegerv(GL_MAX_TEXTURE_SIZE, &maxTextureSize);
+    mMaxTextureSize = maxTextureSize;
+
+    mDebugEnabled = readDebugLevel() & kDebugCaches;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// Size management
+///////////////////////////////////////////////////////////////////////////////
+
+uint32_t PathCache::getSize() {
+    return mSize;
+}
+
+uint32_t PathCache::getMaxSize() {
+    return mMaxSize;
+}
+
+void PathCache::setMaxSize(uint32_t maxSize) {
+    mMaxSize = maxSize;
+    while (mSize > mMaxSize) {
+        mCache.removeOldest();
+    }
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// Callbacks
+///////////////////////////////////////////////////////////////////////////////
+
+void PathCache::operator()(PathDescription& entry, PathTexture*& texture) {
+    removeTexture(texture);
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// Caching
+///////////////////////////////////////////////////////////////////////////////
+
+void PathCache::removeTexture(PathTexture* texture) {
+    if (texture) {
+        const uint32_t size = texture->width * texture->height;
+        mSize -= size;
+
+        PATH_LOGD("PathCache::delete name, size, mSize = %d, %d, %d",
+                texture->id, size, mSize);
+        if (mDebugEnabled) {
+            ALOGD("Shape deleted, size = %d", size);
+        }
+
+        if (texture->id) {
+            glDeleteTextures(1, &texture->id);
+        }
+        delete texture;
+    }
+}
+
+void PathCache::purgeCache(uint32_t width, uint32_t height) {
+    const uint32_t size = width * height;
+    // Don't even try to cache a bitmap that's bigger than the cache
+    if (size < mMaxSize) {
+        while (mSize + size > mMaxSize) {
+            mCache.removeOldest();
+        }
+    }
+}
+
+void PathCache::trim() {
+    while (mSize > mMaxSize) {
+        mCache.removeOldest();
+    }
+}
+
+PathTexture* PathCache::addTexture(const PathDescription& entry, const SkPath *path,
+        const SkPaint* paint) {
+    ATRACE_CALL();
+
+    float left, top, offset;
+    uint32_t width, height;
+    computePathBounds(path, paint, left, top, offset, width, height);
+
+    if (!checkTextureSize(width, height)) return NULL;
+
+    purgeCache(width, height);
+
+    SkBitmap bitmap;
+    drawPath(path, paint, bitmap, left, top, offset, width, height);
+
+    PathTexture* texture = createTexture(left, top, offset, width, height,
+            path->getGenerationID());
+    addTexture(entry, &bitmap, texture);
+
+    return texture;
+}
+
+void PathCache::addTexture(const PathDescription& entry, SkBitmap* bitmap, PathTexture* texture) {
+    generateTexture(*bitmap, texture);
+
+    uint32_t size = texture->width * texture->height;
+    if (size < mMaxSize) {
+        mSize += size;
+        PATH_LOGD("PathCache::get/create: name, size, mSize = %d, %d, %d",
+                texture->id, size, mSize);
+        if (mDebugEnabled) {
+            ALOGD("Shape created, size = %d", size);
+        }
+        mCache.put(entry, texture);
+    } else {
+        texture->cleanup = true;
+    }
+}
+
+void PathCache::clear() {
+    mCache.clear();
+}
+
+void PathCache::generateTexture(SkBitmap& bitmap, Texture* texture) {
+    SkAutoLockPixels alp(bitmap);
+    if (!bitmap.readyToDraw()) {
+        ALOGE("Cannot generate texture from bitmap");
+        return;
+    }
+
+    glGenTextures(1, &texture->id);
+
+    glBindTexture(GL_TEXTURE_2D, texture->id);
+    // Textures are Alpha8
+    glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
+
+    texture->blend = true;
+    glTexImage2D(GL_TEXTURE_2D, 0, GL_ALPHA, texture->width, texture->height, 0,
+            GL_ALPHA, GL_UNSIGNED_BYTE, bitmap.getPixels());
+
+    texture->setFilter(GL_LINEAR);
+    texture->setWrap(GL_CLAMP_TO_EDGE);
+}
+
+///////////////////////////////////////////////////////////////////////////////
 // Path precaching
 ///////////////////////////////////////////////////////////////////////////////
 
@@ -52,7 +334,7 @@
 
     if (width <= mMaxTextureSize && height <= mMaxTextureSize) {
         SkBitmap* bitmap = new SkBitmap();
-        PathCache::drawPath(t->path, t->paint, *bitmap, left, top, offset, width, height);
+        drawPath(t->path, t->paint, *bitmap, left, top, offset, width, height);
         t->setResult(bitmap);
     } else {
         texture->width = 0;
@@ -62,23 +344,17 @@
 }
 
 ///////////////////////////////////////////////////////////////////////////////
-// Path cache
+// Paths
 ///////////////////////////////////////////////////////////////////////////////
 
-PathCache::PathCache(): ShapeCache<PathCacheEntry>("path",
-        PROPERTY_PATH_CACHE_SIZE, DEFAULT_PATH_CACHE_SIZE) {
-}
-
-PathCache::~PathCache() {
-}
-
 void PathCache::remove(SkPath* path) {
-    Vector<PathCacheEntry> pathsToRemove;
-    LruCache<PathCacheEntry, PathTexture*>::Iterator i(mCache);
+    Vector<PathDescription> pathsToRemove;
+    LruCache<PathDescription, PathTexture*>::Iterator i(mCache);
 
     while (i.next()) {
-        const PathCacheEntry& key = i.key();
-        if (key.path == path || key.path == path->getSourcePath()) {
+        const PathDescription& key = i.key();
+        if (key.type == kShapePath &&
+                (key.shape.path.mPath == path || key.shape.path.mPath == path->getSourcePath())) {
             pathsToRemove.push(key);
         }
     }
@@ -121,7 +397,9 @@
 PathTexture* PathCache::get(SkPath* path, SkPaint* paint) {
     path = getSourcePath(path);
 
-    PathCacheEntry entry(path, paint);
+    PathDescription entry(kShapePath, paint);
+    entry.shape.path.mPath = path;
+
     PathTexture* texture = mCache.get(entry);
 
     if (!texture) {
@@ -159,7 +437,9 @@
 
     path = getSourcePath(path);
 
-    PathCacheEntry entry(path, paint);
+    PathDescription entry(kShapePath, paint);
+    entry.shape.path.mPath = path;
+
     PathTexture* texture = mCache.get(entry);
 
     bool generate = false;
@@ -193,5 +473,130 @@
     }
 }
 
+///////////////////////////////////////////////////////////////////////////////
+// Rounded rects
+///////////////////////////////////////////////////////////////////////////////
+
+PathTexture* PathCache::getRoundRect(float width, float height,
+        float rx, float ry, SkPaint* paint) {
+    PathDescription entry(kShapeRoundRect, paint);
+    entry.shape.roundRect.mWidth = width;
+    entry.shape.roundRect.mHeight = height;
+    entry.shape.roundRect.mRx = rx;
+    entry.shape.roundRect.mRy = ry;
+
+    PathTexture* texture = get(entry);
+
+    if (!texture) {
+        SkPath path;
+        SkRect r;
+        r.set(0.0f, 0.0f, width, height);
+        path.addRoundRect(r, rx, ry, SkPath::kCW_Direction);
+
+        texture = addTexture(entry, &path, paint);
+    }
+
+    return texture;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// Circles
+///////////////////////////////////////////////////////////////////////////////
+
+PathTexture* PathCache::getCircle(float radius, SkPaint* paint) {
+    PathDescription entry(kShapeCircle, paint);
+    entry.shape.circle.mRadius = radius;
+
+    PathTexture* texture = get(entry);
+
+    if (!texture) {
+        SkPath path;
+        path.addCircle(radius, radius, radius, SkPath::kCW_Direction);
+
+        texture = addTexture(entry, &path, paint);
+    }
+
+    return texture;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// Ovals
+///////////////////////////////////////////////////////////////////////////////
+
+PathTexture* PathCache::getOval(float width, float height, SkPaint* paint) {
+    PathDescription entry(kShapeOval, paint);
+    entry.shape.oval.mWidth = width;
+    entry.shape.oval.mHeight = height;
+
+    PathTexture* texture = get(entry);
+
+    if (!texture) {
+        SkPath path;
+        SkRect r;
+        r.set(0.0f, 0.0f, width, height);
+        path.addOval(r, SkPath::kCW_Direction);
+
+        texture = addTexture(entry, &path, paint);
+    }
+
+    return texture;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// Rects
+///////////////////////////////////////////////////////////////////////////////
+
+PathTexture* PathCache::getRect(float width, float height, SkPaint* paint) {
+    PathDescription entry(kShapeRect, paint);
+    entry.shape.rect.mWidth = width;
+    entry.shape.rect.mHeight = height;
+
+    PathTexture* texture = get(entry);
+
+    if (!texture) {
+        SkPath path;
+        SkRect r;
+        r.set(0.0f, 0.0f, width, height);
+        path.addRect(r, SkPath::kCW_Direction);
+
+        texture = addTexture(entry, &path, paint);
+    }
+
+    return texture;
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// Arcs
+///////////////////////////////////////////////////////////////////////////////
+
+PathTexture* PathCache::getArc(float width, float height,
+        float startAngle, float sweepAngle, bool useCenter, SkPaint* paint) {
+    PathDescription entry(kShapeArc, paint);
+    entry.shape.arc.mWidth = width;
+    entry.shape.arc.mHeight = height;
+    entry.shape.arc.mStartAngle = startAngle;
+    entry.shape.arc.mSweepAngle = sweepAngle;
+    entry.shape.arc.mUseCenter = useCenter;
+
+    PathTexture* texture = get(entry);
+
+    if (!texture) {
+        SkPath path;
+        SkRect r;
+        r.set(0.0f, 0.0f, width, height);
+        if (useCenter) {
+            path.moveTo(r.centerX(), r.centerY());
+        }
+        path.arcTo(r, startAngle, sweepAngle, !useCenter);
+        if (useCenter) {
+            path.close();
+        }
+
+        texture = addTexture(entry, &path, paint);
+    }
+
+    return texture;
+}
+
 }; // namespace uirenderer
 }; // namespace android
diff --git a/libs/hwui/PathCache.h b/libs/hwui/PathCache.h
index 27031a5..e6d92df 100644
--- a/libs/hwui/PathCache.h
+++ b/libs/hwui/PathCache.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2010 The Android Open Source Project
+ * Copyright (C) 2013 The Android Open Source Project
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
@@ -17,17 +17,21 @@
 #ifndef ANDROID_HWUI_PATH_CACHE_H
 #define ANDROID_HWUI_PATH_CACHE_H
 
-#include <utils/Thread.h>
+#include <GLES2/gl2.h>
+
+#include <utils/LruCache.h>
+#include <utils/Mutex.h>
 #include <utils/Vector.h>
 
 #include "Debug.h"
-#include "ShapeCache.h"
-#include "thread/Signal.h"
-#include "thread/Task.h"
-#include "thread/TaskProcessor.h"
+#include "Properties.h"
+#include "Texture.h"
 
+class SkBitmap;
+class SkCanvas;
 class SkPaint;
 class SkPath;
+class SkRect;
 
 namespace android {
 namespace uirenderer {
@@ -35,56 +39,181 @@
 class Caches;
 
 ///////////////////////////////////////////////////////////////////////////////
+// Defines
+///////////////////////////////////////////////////////////////////////////////
+
+// Debug
+#if DEBUG_PATHS
+    #define PATH_LOGD(...) ALOGD(__VA_ARGS__)
+#else
+    #define PATH_LOGD(...)
+#endif
+
+///////////////////////////////////////////////////////////////////////////////
 // Classes
 ///////////////////////////////////////////////////////////////////////////////
 
-struct PathCacheEntry: public ShapeCacheEntry {
-    PathCacheEntry(SkPath* path, SkPaint* paint):
-            ShapeCacheEntry(ShapeCacheEntry::kShapePath, paint) {
-        this->path = path;
+/**
+ * Alpha texture used to represent a path.
+ */
+struct PathTexture: public Texture {
+    PathTexture(): Texture() {
     }
 
-    PathCacheEntry(): ShapeCacheEntry() {
-        path = NULL;
+    ~PathTexture() {
+        clearTask();
     }
 
-    hash_t hash() const {
-        uint32_t hash = ShapeCacheEntry::hash();
-        hash = JenkinsHashMix(hash, android::hash_type(path));
-        return JenkinsHashWhiten(hash);
+    /**
+     * Left coordinate of the path bounds.
+     */
+    float left;
+    /**
+     * Top coordinate of the path bounds.
+     */
+    float top;
+    /**
+     * Offset to draw the path at the correct origin.
+     */
+    float offset;
+
+    sp<Task<SkBitmap*> > task() const {
+        return mTask;
     }
 
-    int compare(const ShapeCacheEntry& r) const {
-        int deltaInt = ShapeCacheEntry::compare(r);
-        if (deltaInt != 0) return deltaInt;
-
-        const PathCacheEntry& rhs = (const PathCacheEntry&) r;
-        return path - rhs.path;
+    void setTask(const sp<Task<SkBitmap*> >& task) {
+        mTask = task;
     }
 
-    SkPath* path;
+    void clearTask() {
+        if (mTask != NULL) {
+            mTask.clear();
+        }
+    }
 
-}; // PathCacheEntry
+private:
+    sp<Task<SkBitmap*> > mTask;
+}; // struct PathTexture
 
-inline hash_t hash_type(const PathCacheEntry& entry) {
-    return entry.hash();
-}
+enum ShapeType {
+    kShapeNone,
+    kShapeRect,
+    kShapeRoundRect,
+    kShapeCircle,
+    kShapeOval,
+    kShapeArc,
+    kShapePath
+};
+
+struct PathDescription {
+    ShapeType type;
+    SkPaint::Join join;
+    SkPaint::Cap cap;
+    SkPaint::Style style;
+    float miter;
+    float strokeWidth;
+    SkPathEffect* pathEffect;
+    union Shape {
+        struct Path {
+            SkPath* mPath;
+        } path;
+        struct RoundRect {
+            float mWidth;
+            float mHeight;
+            float mRx;
+            float mRy;
+        } roundRect;
+        struct Circle {
+            float mRadius;
+        } circle;
+        struct Oval {
+            float mWidth;
+            float mHeight;
+        } oval;
+        struct Rect {
+            float mWidth;
+            float mHeight;
+        } rect;
+        struct Arc {
+            float mWidth;
+            float mHeight;
+            float mStartAngle;
+            float mSweepAngle;
+            bool mUseCenter;
+        } arc;
+    } shape;
+
+    PathDescription();
+    PathDescription(ShapeType shapeType, SkPaint* paint);
+
+    hash_t hash() const;
+
+    int compare(const PathDescription& rhs) const;
+
+    bool operator==(const PathDescription& other) const {
+        return compare(other) == 0;
+    }
+
+    bool operator!=(const PathDescription& other) const {
+        return compare(other) != 0;
+    }
+
+    friend inline int strictly_order_type(
+            const PathDescription& lhs, const PathDescription& rhs) {
+        return lhs.compare(rhs) < 0;
+    }
+
+    friend inline int compare_type(const PathDescription& lhs, const PathDescription& rhs) {
+        return lhs.compare(rhs);
+    }
+
+    friend inline hash_t hash_type(const PathDescription& entry) {
+        return entry.hash();
+    }
+};
 
 /**
- * A simple LRU path cache. The cache has a maximum size expressed in bytes.
+ * A simple LRU shape cache. The cache has a maximum size expressed in bytes.
  * Any texture added to the cache causing the cache to grow beyond the maximum
  * allowed size will also cause the oldest texture to be kicked out.
  */
-class PathCache: public ShapeCache<PathCacheEntry> {
+class PathCache: public OnEntryRemoved<PathDescription, PathTexture*> {
 public:
     PathCache();
     ~PathCache();
 
     /**
-     * Returns the texture associated with the specified path. If the texture
-     * cannot be found in the cache, a new texture is generated.
+     * Used as a callback when an entry is removed from the cache.
+     * Do not invoke directly.
      */
+    void operator()(PathDescription& path, PathTexture*& texture);
+
+    /**
+     * Clears the cache. This causes all textures to be deleted.
+     */
+    void clear();
+
+    /**
+     * Sets the maximum size of the cache in bytes.
+     */
+    void setMaxSize(uint32_t maxSize);
+    /**
+     * Returns the maximum size of the cache in bytes.
+     */
+    uint32_t getMaxSize();
+    /**
+     * Returns the current size of the cache in bytes.
+     */
+    uint32_t getSize();
+
+    PathTexture* getRoundRect(float width, float height, float rx, float ry, SkPaint* paint);
+    PathTexture* getCircle(float radius, SkPaint* paint);
+    PathTexture* getOval(float width, float height, SkPaint* paint);
+    PathTexture* getRect(float width, float height, SkPaint* paint);
+    PathTexture* getArc(float width, float height, float startAngle, float sweepAngle,
+            bool useCenter, SkPaint* paint);
     PathTexture* get(SkPath* path, SkPaint* paint);
+
     /**
      * Removes an entry.
      */
@@ -98,10 +227,63 @@
      * Process deferred removals.
      */
     void clearGarbage();
+    /**
+     * Trims the contents of the cache, removing items until it's under its
+     * specified limit.
+     *
+     * Trimming is used for caches that support pre-caching from a worker
+     * thread. During pre-caching the maximum limit of the cache can be
+     * exceeded for the duration of the frame. It is therefore required to
+     * trim the cache at the end of the frame to keep the total amount of
+     * memory used under control.
+     */
+    void trim();
 
+    /**
+     * Precaches the specified path using background threads.
+     */
     void precache(SkPath* path, SkPaint* paint);
 
+    static bool canDrawAsConvexPath(SkPath* path, SkPaint* paint);
+    static void computePathBounds(const SkPath* path, const SkPaint* paint,
+            float& left, float& top, float& offset, uint32_t& width, uint32_t& height);
+    static void computeBounds(const SkRect& bounds, const SkPaint* paint,
+            float& left, float& top, float& offset, uint32_t& width, uint32_t& height);
+
 private:
+    PathTexture* addTexture(const PathDescription& entry,
+            const SkPath *path, const SkPaint* paint);
+    PathTexture* addTexture(const PathDescription& entry, SkBitmap* bitmap);
+    void addTexture(const PathDescription& entry, SkBitmap* bitmap, PathTexture* texture);
+
+    PathTexture* get(const PathDescription& entry) {
+        return mCache.get(entry);
+    }
+
+    /**
+     * Ensures there is enough space in the cache for a texture of the specified
+     * dimensions.
+     */
+    void purgeCache(uint32_t width, uint32_t height);
+
+    void removeTexture(PathTexture* texture);
+
+    bool checkTextureSize(uint32_t width, uint32_t height) {
+        if (width > mMaxTextureSize || height > mMaxTextureSize) {
+            ALOGW("Shape too large to be rendered into a texture (%dx%d, max=%dx%d)",
+                    width, height, mMaxTextureSize, mMaxTextureSize);
+            return false;
+        }
+        return true;
+    }
+
+    /**
+     * Generates the texture from a bitmap into the specified texture structure.
+     */
+    void generateTexture(SkBitmap& bitmap, Texture* texture);
+
+    void init();
+
     class PathTask: public Task<SkBitmap*> {
     public:
         PathTask(SkPath* path, SkPaint* paint, PathTexture* texture):
@@ -128,6 +310,13 @@
         uint32_t mMaxTextureSize;
     };
 
+    LruCache<PathDescription, PathTexture*> mCache;
+    uint32_t mSize;
+    uint32_t mMaxSize;
+    GLuint mMaxTextureSize;
+
+    bool mDebugEnabled;
+
     sp<PathProcessor> mProcessor;
     Vector<SkPath*> mGarbage;
     mutable Mutex mLock;
diff --git a/libs/hwui/Properties.h b/libs/hwui/Properties.h
index b8559bc..5f39abf 100644
--- a/libs/hwui/Properties.h
+++ b/libs/hwui/Properties.h
@@ -115,7 +115,6 @@
 #define PROPERTY_RENDER_BUFFER_CACHE_SIZE "ro.hwui.r_buffer_cache_size"
 #define PROPERTY_GRADIENT_CACHE_SIZE "ro.hwui.gradient_cache_size"
 #define PROPERTY_PATH_CACHE_SIZE "ro.hwui.path_cache_size"
-#define PROPERTY_SHAPE_CACHE_SIZE "ro.hwui.shape_cache_size"
 #define PROPERTY_DROP_SHADOW_CACHE_SIZE "ro.hwui.drop_shadow_cache_size"
 #define PROPERTY_FBO_CACHE_SIZE "ro.hwui.fbo_cache_size"
 
@@ -159,8 +158,7 @@
 #define DEFAULT_TEXTURE_CACHE_SIZE 24.0f
 #define DEFAULT_LAYER_CACHE_SIZE 16.0f
 #define DEFAULT_RENDER_BUFFER_CACHE_SIZE 2.0f
-#define DEFAULT_PATH_CACHE_SIZE 4.0f
-#define DEFAULT_SHAPE_CACHE_SIZE 1.0f
+#define DEFAULT_PATH_CACHE_SIZE 10.0f
 #define DEFAULT_PATCH_CACHE_SIZE 512
 #define DEFAULT_GRADIENT_CACHE_SIZE 0.5f
 #define DEFAULT_DROP_SHADOW_CACHE_SIZE 2.0f
diff --git a/libs/hwui/ShapeCache.cpp b/libs/hwui/ShapeCache.cpp
deleted file mode 100644
index 5a23235..0000000
--- a/libs/hwui/ShapeCache.cpp
+++ /dev/null
@@ -1,168 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "OpenGLRenderer"
-
-#include "ShapeCache.h"
-
-namespace android {
-namespace uirenderer {
-
-///////////////////////////////////////////////////////////////////////////////
-// Rounded rects
-///////////////////////////////////////////////////////////////////////////////
-
-RoundRectShapeCache::RoundRectShapeCache(): ShapeCache<RoundRectShapeCacheEntry>(
-        "round rect", PROPERTY_SHAPE_CACHE_SIZE, DEFAULT_SHAPE_CACHE_SIZE) {
-}
-
-PathTexture* RoundRectShapeCache::getRoundRect(float width, float height,
-        float rx, float ry, SkPaint* paint) {
-    RoundRectShapeCacheEntry entry(width, height, rx, ry, paint);
-    PathTexture* texture = get(entry);
-
-    if (!texture) {
-        SkPath path;
-        SkRect r;
-        r.set(0.0f, 0.0f, width, height);
-        path.addRoundRect(r, rx, ry, SkPath::kCW_Direction);
-
-        texture = addTexture(entry, &path, paint);
-    }
-
-    return texture;
-}
-
-///////////////////////////////////////////////////////////////////////////////
-// Circles
-///////////////////////////////////////////////////////////////////////////////
-
-CircleShapeCache::CircleShapeCache(): ShapeCache<CircleShapeCacheEntry>(
-        "circle", PROPERTY_SHAPE_CACHE_SIZE, DEFAULT_SHAPE_CACHE_SIZE) {
-}
-
-PathTexture* CircleShapeCache::getCircle(float radius, SkPaint* paint) {
-    CircleShapeCacheEntry entry(radius, paint);
-    PathTexture* texture = get(entry);
-
-    if (!texture) {
-        SkPath path;
-        path.addCircle(radius, radius, radius, SkPath::kCW_Direction);
-
-        texture = addTexture(entry, &path, paint);
-    }
-
-    return texture;
-}
-
-///////////////////////////////////////////////////////////////////////////////
-// Ovals
-///////////////////////////////////////////////////////////////////////////////
-
-OvalShapeCache::OvalShapeCache(): ShapeCache<OvalShapeCacheEntry>(
-        "oval", PROPERTY_SHAPE_CACHE_SIZE, DEFAULT_SHAPE_CACHE_SIZE) {
-}
-
-PathTexture* OvalShapeCache::getOval(float width, float height, SkPaint* paint) {
-    OvalShapeCacheEntry entry(width, height, paint);
-    PathTexture* texture = get(entry);
-
-    if (!texture) {
-        SkPath path;
-        SkRect r;
-        r.set(0.0f, 0.0f, width, height);
-        path.addOval(r, SkPath::kCW_Direction);
-
-        texture = addTexture(entry, &path, paint);
-    }
-
-    return texture;
-}
-
-///////////////////////////////////////////////////////////////////////////////
-// Rects
-///////////////////////////////////////////////////////////////////////////////
-
-RectShapeCache::RectShapeCache(): ShapeCache<RectShapeCacheEntry>(
-        "rect", PROPERTY_SHAPE_CACHE_SIZE, DEFAULT_SHAPE_CACHE_SIZE) {
-}
-
-PathTexture* RectShapeCache::getRect(float width, float height, SkPaint* paint) {
-    RectShapeCacheEntry entry(width, height, paint);
-    PathTexture* texture = get(entry);
-
-    if (!texture) {
-        SkRect bounds;
-        bounds.set(0.0f, 0.0f, width, height);
-
-        float left, top, offset;
-        uint32_t rectWidth, rectHeight;
-        computeBounds(bounds, paint, left, top, offset, rectWidth, rectHeight);
-
-        if (!checkTextureSize(rectWidth, rectHeight)) return NULL;
-
-        purgeCache(rectWidth, rectHeight);
-
-        SkBitmap bitmap;
-        initBitmap(bitmap, rectWidth, rectHeight);
-
-        SkPaint pathPaint(*paint);
-        initPaint(pathPaint);
-
-        SkCanvas canvas(bitmap);
-        canvas.translate(-left + offset, -top + offset);
-        canvas.drawRect(bounds, pathPaint);
-
-        texture = createTexture(0, 0, offset, rectWidth, rectHeight, 0);
-        addTexture(entry, &bitmap, texture);
-    }
-
-    return texture;
-}
-
-///////////////////////////////////////////////////////////////////////////////
-// Arcs
-///////////////////////////////////////////////////////////////////////////////
-
-ArcShapeCache::ArcShapeCache(): ShapeCache<ArcShapeCacheEntry>(
-        "arc", PROPERTY_SHAPE_CACHE_SIZE, DEFAULT_SHAPE_CACHE_SIZE) {
-}
-
-PathTexture* ArcShapeCache::getArc(float width, float height,
-        float startAngle, float sweepAngle, bool useCenter, SkPaint* paint) {
-    ArcShapeCacheEntry entry(width, height, startAngle, sweepAngle, useCenter, paint);
-    PathTexture* texture = get(entry);
-
-    if (!texture) {
-        SkPath path;
-        SkRect r;
-        r.set(0.0f, 0.0f, width, height);
-        if (useCenter) {
-            path.moveTo(r.centerX(), r.centerY());
-        }
-        path.arcTo(r, startAngle, sweepAngle, !useCenter);
-        if (useCenter) {
-            path.close();
-        }
-
-        texture = addTexture(entry, &path, paint);
-    }
-
-    return texture;
-}
-
-}; // namespace uirenderer
-}; // namespace android
diff --git a/libs/hwui/ShapeCache.h b/libs/hwui/ShapeCache.h
deleted file mode 100644
index 92314b0..0000000
--- a/libs/hwui/ShapeCache.h
+++ /dev/null
@@ -1,816 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef ANDROID_HWUI_SHAPE_CACHE_H
-#define ANDROID_HWUI_SHAPE_CACHE_H
-
-#define ATRACE_TAG ATRACE_TAG_VIEW
-
-#include <GLES2/gl2.h>
-
-#include <SkBitmap.h>
-#include <SkCanvas.h>
-#include <SkPaint.h>
-#include <SkPath.h>
-#include <SkRect.h>
-
-#include <utils/JenkinsHash.h>
-#include <utils/LruCache.h>
-#include <utils/Trace.h>
-
-#include "Debug.h"
-#include "Properties.h"
-#include "Texture.h"
-#include "thread/Task.h"
-
-namespace android {
-namespace uirenderer {
-
-///////////////////////////////////////////////////////////////////////////////
-// Defines
-///////////////////////////////////////////////////////////////////////////////
-
-// Debug
-#if DEBUG_SHAPES
-    #define SHAPE_LOGD(...) ALOGD(__VA_ARGS__)
-#else
-    #define SHAPE_LOGD(...)
-#endif
-
-///////////////////////////////////////////////////////////////////////////////
-// Classes
-///////////////////////////////////////////////////////////////////////////////
-
-/**
- * Alpha texture used to represent a path.
- */
-struct PathTexture: public Texture {
-    PathTexture(): Texture() {
-    }
-
-    ~PathTexture() {
-        clearTask();
-    }
-
-    /**
-     * Left coordinate of the path bounds.
-     */
-    float left;
-    /**
-     * Top coordinate of the path bounds.
-     */
-    float top;
-    /**
-     * Offset to draw the path at the correct origin.
-     */
-    float offset;
-
-    sp<Task<SkBitmap*> > task() const {
-        return mTask;
-    }
-
-    void setTask(const sp<Task<SkBitmap*> >& task) {
-        mTask = task;
-    }
-
-    void clearTask() {
-        if (mTask != NULL) {
-            mTask.clear();
-        }
-    }
-
-private:
-    sp<Task<SkBitmap*> > mTask;
-}; // struct PathTexture
-
-/**
- * Describe a shape in the shape cache.
- */
-struct ShapeCacheEntry {
-    enum ShapeType {
-        kShapeNone,
-        kShapeRect,
-        kShapeRoundRect,
-        kShapeCircle,
-        kShapeOval,
-        kShapeArc,
-        kShapePath
-    };
-
-    ShapeCacheEntry() {
-        shapeType = kShapeNone;
-        join = SkPaint::kDefault_Join;
-        cap = SkPaint::kDefault_Cap;
-        style = SkPaint::kFill_Style;
-        miter = 4.0f;
-        strokeWidth = 1.0f;
-        pathEffect = NULL;
-    }
-
-    ShapeCacheEntry(ShapeType type, SkPaint* paint) {
-        shapeType = type;
-        join = paint->getStrokeJoin();
-        cap = paint->getStrokeCap();
-        miter = paint->getStrokeMiter();
-        strokeWidth = paint->getStrokeWidth();
-        style = paint->getStyle();
-        pathEffect = paint->getPathEffect();
-    }
-
-    virtual ~ShapeCacheEntry() {
-    }
-
-    virtual hash_t hash() const {
-        uint32_t hash = JenkinsHashMix(0, shapeType);
-        hash = JenkinsHashMix(hash, join);
-        hash = JenkinsHashMix(hash, cap);
-        hash = JenkinsHashMix(hash, style);
-        hash = JenkinsHashMix(hash, android::hash_type(miter));
-        hash = JenkinsHashMix(hash, android::hash_type(strokeWidth));
-        hash = JenkinsHashMix(hash, android::hash_type(pathEffect));
-        return JenkinsHashWhiten(hash);
-    }
-
-    virtual int compare(const ShapeCacheEntry& rhs) const {
-        int deltaInt = shapeType - rhs.shapeType;
-        if (deltaInt != 0) return deltaInt;
-
-        deltaInt = join - rhs.join;
-        if (deltaInt != 0) return deltaInt;
-
-        deltaInt = cap - rhs.cap;
-        if (deltaInt != 0) return deltaInt;
-
-        deltaInt = style - rhs.style;
-        if (deltaInt != 0) return deltaInt;
-
-        if (miter < rhs.miter) return -1;
-        if (miter > rhs.miter) return +1;
-
-        if (strokeWidth < rhs.strokeWidth) return -1;
-        if (strokeWidth > rhs.strokeWidth) return +1;
-
-        if (pathEffect < rhs.pathEffect) return -1;
-        if (pathEffect > rhs.pathEffect) return +1;
-
-        return 0;
-    }
-
-    bool operator==(const ShapeCacheEntry& other) const {
-        return compare(other) == 0;
-    }
-
-    bool operator!=(const ShapeCacheEntry& other) const {
-        return compare(other) != 0;
-    }
-
-    ShapeType shapeType;
-    SkPaint::Join join;
-    SkPaint::Cap cap;
-    SkPaint::Style style;
-    float miter;
-    float strokeWidth;
-    SkPathEffect* pathEffect;
-}; // struct ShapeCacheEntry
-
-// Cache support
-
-inline int strictly_order_type(const ShapeCacheEntry& lhs, const ShapeCacheEntry& rhs) {
-    return lhs.compare(rhs) < 0;
-}
-
-inline int compare_type(const ShapeCacheEntry& lhs, const ShapeCacheEntry& rhs) {
-    return lhs.compare(rhs);
-}
-
-inline hash_t hash_type(const ShapeCacheEntry& entry) {
-    return entry.hash();
-}
-
-struct RoundRectShapeCacheEntry: public ShapeCacheEntry {
-    RoundRectShapeCacheEntry(float width, float height, float rx, float ry, SkPaint* paint):
-            ShapeCacheEntry(ShapeCacheEntry::kShapeRoundRect, paint) {
-        mWidth = width;
-        mHeight = height;
-        mRx = rx;
-        mRy = ry;
-    }
-
-    RoundRectShapeCacheEntry(): ShapeCacheEntry() {
-        mWidth = 0;
-        mHeight = 0;
-        mRx = 0;
-        mRy = 0;
-    }
-
-    hash_t hash() const {
-        uint32_t hash = ShapeCacheEntry::hash();
-        hash = JenkinsHashMix(hash, android::hash_type(mWidth));
-        hash = JenkinsHashMix(hash, android::hash_type(mHeight));
-        hash = JenkinsHashMix(hash, android::hash_type(mRx));
-        hash = JenkinsHashMix(hash, android::hash_type(mRy));
-        return JenkinsHashWhiten(hash);
-    }
-
-    int compare(const ShapeCacheEntry& r) const {
-        int deltaInt = ShapeCacheEntry::compare(r);
-        if (deltaInt != 0) return deltaInt;
-
-        const RoundRectShapeCacheEntry& rhs = (const RoundRectShapeCacheEntry&) r;
-
-        if (mWidth < rhs.mWidth) return -1;
-        if (mWidth > rhs.mWidth) return +1;
-
-        if (mHeight < rhs.mHeight) return -1;
-        if (mHeight > rhs.mHeight) return +1;
-
-        if (mRx < rhs.mRx) return -1;
-        if (mRx > rhs.mRx) return +1;
-
-        if (mRy < rhs.mRy) return -1;
-        if (mRy > rhs.mRy) return +1;
-
-        return 0;
-    }
-
-private:
-    float mWidth;
-    float mHeight;
-    float mRx;
-    float mRy;
-}; // RoundRectShapeCacheEntry
-
-inline hash_t hash_type(const RoundRectShapeCacheEntry& entry) {
-    return entry.hash();
-}
-
-struct CircleShapeCacheEntry: public ShapeCacheEntry {
-    CircleShapeCacheEntry(float radius, SkPaint* paint):
-            ShapeCacheEntry(ShapeCacheEntry::kShapeCircle, paint) {
-        mRadius = radius;
-    }
-
-    CircleShapeCacheEntry(): ShapeCacheEntry() {
-        mRadius = 0;
-    }
-
-    hash_t hash() const {
-        uint32_t hash = ShapeCacheEntry::hash();
-        hash = JenkinsHashMix(hash, android::hash_type(mRadius));
-        return JenkinsHashWhiten(hash);
-    }
-
-    int compare(const ShapeCacheEntry& r) const {
-        int deltaInt = ShapeCacheEntry::compare(r);
-        if (deltaInt != 0) return deltaInt;
-
-        const CircleShapeCacheEntry& rhs = (const CircleShapeCacheEntry&) r;
-
-        if (mRadius < rhs.mRadius) return -1;
-        if (mRadius > rhs.mRadius) return +1;
-
-        return 0;
-    }
-
-private:
-    float mRadius;
-}; // CircleShapeCacheEntry
-
-inline hash_t hash_type(const CircleShapeCacheEntry& entry) {
-    return entry.hash();
-}
-
-struct OvalShapeCacheEntry: public ShapeCacheEntry {
-    OvalShapeCacheEntry(float width, float height, SkPaint* paint):
-            ShapeCacheEntry(ShapeCacheEntry::kShapeOval, paint) {
-        mWidth = width;
-        mHeight = height;
-    }
-
-    OvalShapeCacheEntry(): ShapeCacheEntry() {
-        mWidth = mHeight = 0;
-    }
-
-    hash_t hash() const {
-        uint32_t hash = ShapeCacheEntry::hash();
-        hash = JenkinsHashMix(hash, android::hash_type(mWidth));
-        hash = JenkinsHashMix(hash, android::hash_type(mHeight));
-        return JenkinsHashWhiten(hash);
-    }
-
-    int compare(const ShapeCacheEntry& r) const {
-        int deltaInt = ShapeCacheEntry::compare(r);
-        if (deltaInt != 0) return deltaInt;
-
-        const OvalShapeCacheEntry& rhs = (const OvalShapeCacheEntry&) r;
-
-        if (mWidth < rhs.mWidth) return -1;
-        if (mWidth > rhs.mWidth) return +1;
-
-        if (mHeight < rhs.mHeight) return -1;
-        if (mHeight > rhs.mHeight) return +1;
-
-        return 0;
-    }
-
-private:
-    float mWidth;
-    float mHeight;
-}; // OvalShapeCacheEntry
-
-inline hash_t hash_type(const OvalShapeCacheEntry& entry) {
-    return entry.hash();
-}
-
-struct RectShapeCacheEntry: public ShapeCacheEntry {
-    RectShapeCacheEntry(float width, float height, SkPaint* paint):
-            ShapeCacheEntry(ShapeCacheEntry::kShapeRect, paint) {
-        mWidth = width;
-        mHeight = height;
-    }
-
-    RectShapeCacheEntry(): ShapeCacheEntry() {
-        mWidth = mHeight = 0;
-    }
-
-    hash_t hash() const {
-        uint32_t hash = ShapeCacheEntry::hash();
-        hash = JenkinsHashMix(hash, android::hash_type(mWidth));
-        hash = JenkinsHashMix(hash, android::hash_type(mHeight));
-        return JenkinsHashWhiten(hash);
-    }
-
-    int compare(const ShapeCacheEntry& r) const {
-        int deltaInt = ShapeCacheEntry::compare(r);
-        if (deltaInt != 0) return deltaInt;
-
-        const RectShapeCacheEntry& rhs = (const RectShapeCacheEntry&) r;
-
-        if (mWidth < rhs.mWidth) return -1;
-        if (mWidth > rhs.mWidth) return +1;
-
-        if (mHeight < rhs.mHeight) return -1;
-        if (mHeight > rhs.mHeight) return +1;
-
-        return 0;
-    }
-
-private:
-    float mWidth;
-    float mHeight;
-}; // RectShapeCacheEntry
-
-inline hash_t hash_type(const RectShapeCacheEntry& entry) {
-    return entry.hash();
-}
-
-struct ArcShapeCacheEntry: public ShapeCacheEntry {
-    ArcShapeCacheEntry(float width, float height, float startAngle, float sweepAngle,
-            bool useCenter, SkPaint* paint):
-            ShapeCacheEntry(ShapeCacheEntry::kShapeArc, paint) {
-        mWidth = width;
-        mHeight = height;
-        mStartAngle = startAngle;
-        mSweepAngle = sweepAngle;
-        mUseCenter = useCenter ? 1 : 0;
-    }
-
-    ArcShapeCacheEntry(): ShapeCacheEntry() {
-        mWidth = 0;
-        mHeight = 0;
-        mStartAngle = 0;
-        mSweepAngle = 0;
-        mUseCenter = 0;
-    }
-
-    hash_t hash() const {
-        uint32_t hash = ShapeCacheEntry::hash();
-        hash = JenkinsHashMix(hash, android::hash_type(mWidth));
-        hash = JenkinsHashMix(hash, android::hash_type(mHeight));
-        hash = JenkinsHashMix(hash, android::hash_type(mStartAngle));
-        hash = JenkinsHashMix(hash, android::hash_type(mSweepAngle));
-        hash = JenkinsHashMix(hash, mUseCenter);
-        return JenkinsHashWhiten(hash);
-    }
-
-    int compare(const ShapeCacheEntry& r) const {
-        int deltaInt = ShapeCacheEntry::compare(r);
-        if (deltaInt != 0) return deltaInt;
-
-        const ArcShapeCacheEntry& rhs = (const ArcShapeCacheEntry&) r;
-
-        if (mWidth < rhs.mWidth) return -1;
-        if (mWidth > rhs.mWidth) return +1;
-
-        if (mHeight < rhs.mHeight) return -1;
-        if (mHeight > rhs.mHeight) return +1;
-
-        if (mStartAngle < rhs.mStartAngle) return -1;
-        if (mStartAngle > rhs.mStartAngle) return +1;
-
-        if (mSweepAngle < rhs.mSweepAngle) return -1;
-        if (mSweepAngle > rhs.mSweepAngle) return +1;
-
-        return mUseCenter - rhs.mUseCenter;
-    }
-
-private:
-    float mWidth;
-    float mHeight;
-    float mStartAngle;
-    float mSweepAngle;
-    uint32_t mUseCenter;
-}; // ArcShapeCacheEntry
-
-inline hash_t hash_type(const ArcShapeCacheEntry& entry) {
-    return entry.hash();
-}
-
-/**
- * A simple LRU shape cache. The cache has a maximum size expressed in bytes.
- * Any texture added to the cache causing the cache to grow beyond the maximum
- * allowed size will also cause the oldest texture to be kicked out.
- */
-template<typename Entry>
-class ShapeCache: public OnEntryRemoved<Entry, PathTexture*> {
-public:
-    ShapeCache(const char* name, const char* propertyName, float defaultSize);
-    ~ShapeCache();
-
-    /**
-     * Used as a callback when an entry is removed from the cache.
-     * Do not invoke directly.
-     */
-    void operator()(Entry& path, PathTexture*& texture);
-
-    /**
-     * Clears the cache. This causes all textures to be deleted.
-     */
-    void clear();
-
-    /**
-     * Sets the maximum size of the cache in bytes.
-     */
-    void setMaxSize(uint32_t maxSize);
-    /**
-     * Returns the maximum size of the cache in bytes.
-     */
-    uint32_t getMaxSize();
-    /**
-     * Returns the current size of the cache in bytes.
-     */
-    uint32_t getSize();
-
-    /**
-     * Trims the contents of the cache, removing items until it's under its
-     * specified limit.
-     *
-     * Trimming is used for caches that support pre-caching from a worker
-     * thread. During pre-caching the maximum limit of the cache can be
-     * exceeded for the duration of the frame. It is therefore required to
-     * trim the cache at the end of the frame to keep the total amount of
-     * memory used under control.
-     *
-     * Only the PathCache currently supports pre-caching.
-     */
-    void trim();
-
-    static void computePathBounds(const SkPath* path, const SkPaint* paint,
-            float& left, float& top, float& offset, uint32_t& width, uint32_t& height) {
-        const SkRect& bounds = path->getBounds();
-        computeBounds(bounds, paint, left, top, offset, width, height);
-    }
-
-    static void computeBounds(const SkRect& bounds, const SkPaint* paint,
-            float& left, float& top, float& offset, uint32_t& width, uint32_t& height) {
-        const float pathWidth = fmax(bounds.width(), 1.0f);
-        const float pathHeight = fmax(bounds.height(), 1.0f);
-
-        left = bounds.fLeft;
-        top = bounds.fTop;
-
-        offset = (int) floorf(fmax(paint->getStrokeWidth(), 1.0f) * 1.5f + 0.5f);
-
-        width = uint32_t(pathWidth + offset * 2.0 + 0.5);
-        height = uint32_t(pathHeight + offset * 2.0 + 0.5);
-    }
-
-    static void drawPath(const SkPath *path, const SkPaint* paint, SkBitmap& bitmap,
-            float left, float top, float offset, uint32_t width, uint32_t height) {
-        initBitmap(bitmap, width, height);
-
-        SkPaint pathPaint(*paint);
-        initPaint(pathPaint);
-
-        SkCanvas canvas(bitmap);
-        canvas.translate(-left + offset, -top + offset);
-        canvas.drawPath(*path, pathPaint);
-    }
-
-protected:
-    PathTexture* addTexture(const Entry& entry, const SkPath *path, const SkPaint* paint);
-    PathTexture* addTexture(const Entry& entry, SkBitmap* bitmap);
-    void addTexture(const Entry& entry, SkBitmap* bitmap, PathTexture* texture);
-
-    /**
-     * Ensures there is enough space in the cache for a texture of the specified
-     * dimensions.
-     */
-    void purgeCache(uint32_t width, uint32_t height);
-
-    PathTexture* get(Entry entry) {
-        return mCache.get(entry);
-    }
-
-    void removeTexture(PathTexture* texture);
-
-    bool checkTextureSize(uint32_t width, uint32_t height) {
-        if (width > mMaxTextureSize || height > mMaxTextureSize) {
-            ALOGW("Shape %s too large to be rendered into a texture (%dx%d, max=%dx%d)",
-                    mName, width, height, mMaxTextureSize, mMaxTextureSize);
-            return false;
-        }
-        return true;
-    }
-
-    static PathTexture* createTexture(float left, float top, float offset,
-            uint32_t width, uint32_t height, uint32_t id) {
-        PathTexture* texture = new PathTexture();
-        texture->left = left;
-        texture->top = top;
-        texture->offset = offset;
-        texture->width = width;
-        texture->height = height;
-        texture->generation = id;
-        return texture;
-    }
-
-    static void initBitmap(SkBitmap& bitmap, uint32_t width, uint32_t height) {
-        bitmap.setConfig(SkBitmap::kA8_Config, width, height);
-        bitmap.allocPixels();
-        bitmap.eraseColor(0);
-    }
-
-    static void initPaint(SkPaint& paint) {
-        // Make sure the paint is opaque, color, alpha, filter, etc.
-        // will be applied later when compositing the alpha8 texture
-        paint.setColor(0xff000000);
-        paint.setAlpha(255);
-        paint.setColorFilter(NULL);
-        paint.setMaskFilter(NULL);
-        paint.setShader(NULL);
-        SkXfermode* mode = SkXfermode::Create(SkXfermode::kSrc_Mode);
-        SkSafeUnref(paint.setXfermode(mode));
-    }
-
-    LruCache<Entry, PathTexture*> mCache;
-    uint32_t mSize;
-    uint32_t mMaxSize;
-    GLuint mMaxTextureSize;
-
-    char* mName;
-    bool mDebugEnabled;
-
-private:
-    /**
-     * Generates the texture from a bitmap into the specified texture structure.
-     */
-    void generateTexture(SkBitmap& bitmap, Texture* texture);
-
-    void init();
-}; // class ShapeCache
-
-class RoundRectShapeCache: public ShapeCache<RoundRectShapeCacheEntry> {
-public:
-    RoundRectShapeCache();
-
-    PathTexture* getRoundRect(float width, float height, float rx, float ry, SkPaint* paint);
-}; // class RoundRectShapeCache
-
-class CircleShapeCache: public ShapeCache<CircleShapeCacheEntry> {
-public:
-    CircleShapeCache();
-
-    PathTexture* getCircle(float radius, SkPaint* paint);
-}; // class CircleShapeCache
-
-class OvalShapeCache: public ShapeCache<OvalShapeCacheEntry> {
-public:
-    OvalShapeCache();
-
-    PathTexture* getOval(float width, float height, SkPaint* paint);
-}; // class OvalShapeCache
-
-class RectShapeCache: public ShapeCache<RectShapeCacheEntry> {
-public:
-    RectShapeCache();
-
-    PathTexture* getRect(float width, float height, SkPaint* paint);
-}; // class RectShapeCache
-
-class ArcShapeCache: public ShapeCache<ArcShapeCacheEntry> {
-public:
-    ArcShapeCache();
-
-    PathTexture* getArc(float width, float height, float startAngle, float sweepAngle,
-            bool useCenter, SkPaint* paint);
-}; // class ArcShapeCache
-
-///////////////////////////////////////////////////////////////////////////////
-// Constructors/destructor
-///////////////////////////////////////////////////////////////////////////////
-
-template<class Entry>
-ShapeCache<Entry>::ShapeCache(const char* name, const char* propertyName, float defaultSize):
-        mCache(LruCache<ShapeCacheEntry, PathTexture*>::kUnlimitedCapacity),
-        mSize(0), mMaxSize(MB(defaultSize)) {
-    char property[PROPERTY_VALUE_MAX];
-    if (property_get(propertyName, property, NULL) > 0) {
-        INIT_LOGD("  Setting %s cache size to %sMB", name, property);
-        setMaxSize(MB(atof(property)));
-    } else {
-        INIT_LOGD("  Using default %s cache size of %.2fMB", name, defaultSize);
-    }
-
-    size_t len = strlen(name);
-    mName = new char[len + 1];
-    strcpy(mName, name);
-    mName[len] = '\0';
-
-    init();
-}
-
-template<class Entry>
-ShapeCache<Entry>::~ShapeCache() {
-    mCache.clear();
-    delete[] mName;
-}
-
-template<class Entry>
-void ShapeCache<Entry>::init() {
-    mCache.setOnEntryRemovedListener(this);
-
-    GLint maxTextureSize;
-    glGetIntegerv(GL_MAX_TEXTURE_SIZE, &maxTextureSize);
-    mMaxTextureSize = maxTextureSize;
-
-    mDebugEnabled = readDebugLevel() & kDebugCaches;
-}
-
-///////////////////////////////////////////////////////////////////////////////
-// Size management
-///////////////////////////////////////////////////////////////////////////////
-
-template<class Entry>
-uint32_t ShapeCache<Entry>::getSize() {
-    return mSize;
-}
-
-template<class Entry>
-uint32_t ShapeCache<Entry>::getMaxSize() {
-    return mMaxSize;
-}
-
-template<class Entry>
-void ShapeCache<Entry>::setMaxSize(uint32_t maxSize) {
-    mMaxSize = maxSize;
-    while (mSize > mMaxSize) {
-        mCache.removeOldest();
-    }
-}
-
-///////////////////////////////////////////////////////////////////////////////
-// Callbacks
-///////////////////////////////////////////////////////////////////////////////
-
-template<class Entry>
-void ShapeCache<Entry>::operator()(Entry& path, PathTexture*& texture) {
-    removeTexture(texture);
-}
-
-///////////////////////////////////////////////////////////////////////////////
-// Caching
-///////////////////////////////////////////////////////////////////////////////
-
-template<class Entry>
-void ShapeCache<Entry>::removeTexture(PathTexture* texture) {
-    if (texture) {
-        const uint32_t size = texture->width * texture->height;
-        mSize -= size;
-
-        SHAPE_LOGD("ShapeCache::callback: delete %s: name, size, mSize = %d, %d, %d",
-                mName, texture->id, size, mSize);
-        if (mDebugEnabled) {
-            ALOGD("Shape %s deleted, size = %d", mName, size);
-        }
-
-        if (texture->id) {
-            glDeleteTextures(1, &texture->id);
-        }
-        delete texture;
-    }
-}
-
-template<class Entry>
-void ShapeCache<Entry>::purgeCache(uint32_t width, uint32_t height) {
-    const uint32_t size = width * height;
-    // Don't even try to cache a bitmap that's bigger than the cache
-    if (size < mMaxSize) {
-        while (mSize + size > mMaxSize) {
-            mCache.removeOldest();
-        }
-    }
-}
-
-template<class Entry>
-void ShapeCache<Entry>::trim() {
-    while (mSize > mMaxSize) {
-        mCache.removeOldest();
-    }
-}
-
-template<class Entry>
-PathTexture* ShapeCache<Entry>::addTexture(const Entry& entry, const SkPath *path,
-        const SkPaint* paint) {
-    ATRACE_CALL();
-
-    float left, top, offset;
-    uint32_t width, height;
-    computePathBounds(path, paint, left, top, offset, width, height);
-
-    if (!checkTextureSize(width, height)) return NULL;
-
-    purgeCache(width, height);
-
-    SkBitmap bitmap;
-    drawPath(path, paint, bitmap, left, top, offset, width, height);
-
-    PathTexture* texture = createTexture(left, top, offset, width, height,
-            path->getGenerationID());
-    addTexture(entry, &bitmap, texture);
-
-    return texture;
-}
-
-template<class Entry>
-void ShapeCache<Entry>::addTexture(const Entry& entry, SkBitmap* bitmap, PathTexture* texture) {
-    generateTexture(*bitmap, texture);
-
-    uint32_t size = texture->width * texture->height;
-    if (size < mMaxSize) {
-        mSize += size;
-        SHAPE_LOGD("ShapeCache::get: create %s: name, size, mSize = %d, %d, %d",
-                mName, texture->id, size, mSize);
-        if (mDebugEnabled) {
-            ALOGD("Shape %s created, size = %d", mName, size);
-        }
-        mCache.put(entry, texture);
-    } else {
-        texture->cleanup = true;
-    }
-}
-
-template<class Entry>
-void ShapeCache<Entry>::clear() {
-    mCache.clear();
-}
-
-template<class Entry>
-void ShapeCache<Entry>::generateTexture(SkBitmap& bitmap, Texture* texture) {
-    SkAutoLockPixels alp(bitmap);
-    if (!bitmap.readyToDraw()) {
-        ALOGE("Cannot generate texture from bitmap");
-        return;
-    }
-
-    glGenTextures(1, &texture->id);
-
-    glBindTexture(GL_TEXTURE_2D, texture->id);
-    // Textures are Alpha8
-    glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
-
-    texture->blend = true;
-    glTexImage2D(GL_TEXTURE_2D, 0, GL_ALPHA, texture->width, texture->height, 0,
-            GL_ALPHA, GL_UNSIGNED_BYTE, bitmap.getPixels());
-
-    texture->setFilter(GL_LINEAR);
-    texture->setWrap(GL_CLAMP_TO_EDGE);
-}
-
-}; // namespace uirenderer
-}; // namespace android
-
-#endif // ANDROID_HWUI_SHAPE_CACHE_H
