diff --git a/src/gpu/GrContext.cpp b/src/gpu/GrContext.cpp
index 8b97a93..7952666 100644
--- a/src/gpu/GrContext.cpp
+++ b/src/gpu/GrContext.cpp
@@ -25,7 +25,6 @@
 #include "GrSurfaceProxyPriv.h"
 #include "GrTexture.h"
 #include "GrTextureContext.h"
-#include "GrTextureStripAtlas.h"
 #include "GrTracing.h"
 #include "SkAutoPixmapStorage.h"
 #include "SkDeferredDisplayList.h"
@@ -97,8 +96,6 @@
         fResourceCache->setProxyProvider(fProxyProvider);
     }
 
-    fTextureStripAtlasManager.reset(new GrTextureStripAtlasManager);
-
     fDisableGpuYUVConversion = options.fDisableGpuYUVConversion;
     fSharpenMipmappedTextures = options.fSharpenMipmappedTextures;
     fDidTestPMConversions = false;
@@ -162,7 +159,6 @@
     if (fDrawingManager) {
         fDrawingManager->cleanup();
     }
-    fTextureStripAtlasManager = nullptr;
     delete fResourceProvider;
     delete fResourceCache;
     delete fProxyProvider;
@@ -243,7 +239,6 @@
 void GrContext::abandonContext() {
     ASSERT_SINGLE_OWNER
 
-    fTextureStripAtlasManager->abandon();
     fProxyProvider->abandon();
     fResourceProvider->abandon();
 
@@ -269,7 +264,6 @@
 void GrContext::releaseResourcesAndAbandonContext() {
     ASSERT_SINGLE_OWNER
 
-    fTextureStripAtlasManager->abandon();
     fProxyProvider->abandon();
     fResourceProvider->abandon();
 
diff --git a/src/gpu/GrContextPriv.h b/src/gpu/GrContextPriv.h
index 1b90daf..f68cc83 100644
--- a/src/gpu/GrContextPriv.h
+++ b/src/gpu/GrContextPriv.h
@@ -189,10 +189,6 @@
 
     GrResourceCache* getResourceCache() { return fContext->fResourceCache; }
 
-    GrTextureStripAtlasManager* textureStripAtlasManager() {
-        return fContext->fTextureStripAtlasManager.get();
-    }
-
     GrGpu* getGpu() { return fContext->fGpu.get(); }
     const GrGpu* getGpu() const { return fContext->fGpu.get(); }
 
diff --git a/src/gpu/GrDrawingManager.cpp b/src/gpu/GrDrawingManager.cpp
index 5b0f5cb..edde1ec 100644
--- a/src/gpu/GrDrawingManager.cpp
+++ b/src/gpu/GrDrawingManager.cpp
@@ -25,7 +25,6 @@
 #include "GrTexturePriv.h"
 #include "GrTextureProxy.h"
 #include "GrTextureProxyPriv.h"
-#include "GrTextureStripAtlas.h"
 #include "GrTracing.h"
 #include "SkDeferredDisplayList.h"
 #include "SkSurface_Gpu.h"
@@ -397,9 +396,6 @@
 }
 
 void GrDrawingManager::moveOpListsToDDL(SkDeferredDisplayList* ddl) {
-    fContext->contextPriv().textureStripAtlasManager()->finish(
-                                                          fContext->contextPriv().proxyProvider());
-
     for (int i = 0; i < fOpLists.count(); ++i) {
         // no opList should receive a new command after this
         fOpLists[i]->makeClosed(*fContext->contextPriv().caps());
diff --git a/src/gpu/GrTextureStripAtlas.h b/src/gpu/GrTextureStripAtlas.h
deleted file mode 100644
index 3f4e897..0000000
--- a/src/gpu/GrTextureStripAtlas.h
+++ /dev/null
@@ -1,141 +0,0 @@
-/*
- * Copyright 2012 Google Inc.
- *
- * Use of this source code is governed by a BSD-style license that can be
- * found in the LICENSE file.
- */
-
-#ifndef GrTextureStripAtlas_DEFINED
-#define GrTextureStripAtlas_DEFINED
-
-#include "SkNoncopyable.h"
-#include "SkOpts.h"
-#include "SkRefCnt.h"
-#include "SkTDynamicHash.h"
-
-class GrContext;
-class GrProxyProvider;
-class GrTextureProxy;
-class SkBitmap;
-
-/**
- * Base class for the texture strip atlases.
- * It is ref counted because the GradientShader and TableColorFilter are given a pointer to it
- * so that they can lock and unlock rows.
- */
-class GrTextureStripAtlas : public SkRefCnt {
-public:
-    /**
-     * Descriptor struct which we'll use both to find and initialize an atlas and as a hash
-     * table key in the GrTextureStripAtlasManager.
-     */
-    struct Desc {
-        Desc() { sk_bzero(this, sizeof(*this)); }
-        SkColorType fColorType;
-        uint16_t    fWidth;
-        uint16_t    fHeight; // the max height for the DDL version, the size of the atlas for normal
-        uint16_t    fRowHeight;
-        uint16_t    fUnusedPadding;
-
-        bool operator==(const Desc& other) const {
-            return 0 == memcmp(this, &other, sizeof(Desc));
-        }
-    };
-
-    ~GrTextureStripAtlas() override {}
-
-    /**
-     * This is intended to be used when cloning a processor that already holds a lock. It is
-     * assumed that the row already has at least one lock.
-     */
-    virtual void lockRow(int row) = 0;
-
-    /**
-     * Some user of a given row is done. Release that row for reuse.
-     */
-    virtual void unlockRow(int row) = 0;
-
-    /**
-     * This returns the absolute Y location of the given row in the atlas. For atlases with
-     * 'fRowHeight' > 1, this is Y location of the topmost row of the atlas entry. It is always
-     * the middle of the row.
-     */
-    SkScalar rowToTextureY(int row) const {
-        return row * fDesc.fRowHeight + SK_ScalarHalf;
-    }
-
-    /**
-     * Get the texture proxy backing this atlas. Note that the texture proxy may be fully lazy
-     * (i.e., when recording DDLs) and, in particular, the final height may not be known.
-     */
-    virtual sk_sp<GrTextureProxy> asTextureProxyRef() const = 0;
-
-protected:
-    GrTextureStripAtlas(const Desc& desc) : fDesc(desc) {}
-
-    const Desc fDesc;
-
-private:
-    friend class GrTextureStripAtlasManager; // for addStrip, finish
-
-    /**
-     * Add a texture strip to the atlas
-     *  @param context Everyone's favorite class
-     *  @param bitmap  Bitmap data to copy into the row
-     *  @return The row index we inserted into, or -1 if we failed to find an open row. The caller
-     *      is responsible for calling unlockRow() with this row index when it's done with it.
-     */
-    virtual int addStrip(GrContext*, const SkBitmap& bitmap) = 0;
-
-    /**
-     * This method is called when an atlas needs to finish its work on the current texture.
-     * Currently it is only called in DDL mode and when either:
-     *        a given atlas has become full or,
-     *        a DDL is being snapped from a DDL recorder
-     */
-    virtual void finish(GrProxyProvider*) = 0;
-};
-
-////////////////////////////////////////////////////////////////////////////////////////////////////
-class GrTextureStripAtlasManager {
-public:
-    GrTextureStripAtlasManager() {}
-    ~GrTextureStripAtlasManager();
-
-    void abandon();
-    void finish(GrProxyProvider*);
-
-    /**
-     * Add a new texture strip to the atlas matching the descriptor. Upon failure, nullptr
-     * will be returned and 'row' will be set to -1.
-     */
-    sk_sp<GrTextureStripAtlas> addStrip(GrContext*,
-                                        const GrTextureStripAtlas::Desc&,
-                                        const SkBitmap&, int* row);
-
-private:
-    void deleteAllAtlases();
-
-    // Hash table entry for atlases
-    class AtlasEntry : public ::SkNoncopyable {
-    public:
-        AtlasEntry(sk_sp<GrTextureStripAtlas> atlas) : fAtlas(std::move(atlas)) {}
-        ~AtlasEntry() { }
-
-        // for SkTDynamicHash
-        static const GrTextureStripAtlas::Desc& GetKey(const AtlasEntry& entry) {
-            return entry.fAtlas->fDesc;
-        }
-        static uint32_t Hash(const GrTextureStripAtlas::Desc& desc) {
-            return SkOpts::hash(&desc, sizeof(GrTextureStripAtlas::Desc));
-        }
-
-        sk_sp<GrTextureStripAtlas> fAtlas;
-    };
-
-    typedef SkTDynamicHash<AtlasEntry, GrTextureStripAtlas::Desc> AtlasHash;
-
-    AtlasHash fAtlasCache;
-};
-
-#endif
diff --git a/src/gpu/effects/GrDDLTextureStripAtlas.cpp b/src/gpu/effects/GrDDLTextureStripAtlas.cpp
deleted file mode 100644
index ac22df5..0000000
--- a/src/gpu/effects/GrDDLTextureStripAtlas.cpp
+++ /dev/null
@@ -1,197 +0,0 @@
-/*
- * Copyright 2018 Google Inc.
- *
- * Use of this source code is governed by a BSD-style license that can be
- * found in the LICENSE file.
- */
-
-#include "GrDDLTextureStripAtlas.h"
-
-#include "GrContextPriv.h"
-#include "GrTexture.h"
-#include "SkGr.h"
-#include "SkTSearch.h"
-
-GrDDLTextureStripAtlas::GrDDLTextureStripAtlas(const Desc& desc)
-        : INHERITED(desc)
-        , fAtlasBitmap(nullptr)
-        , fMaxNumRows(desc.fHeight / desc.fRowHeight)
-        , fCurRow(0)
-        , fRows(new AtlasRow[fMaxNumRows]) {
-    SkASSERT(fMaxNumRows * fDesc.fRowHeight == fDesc.fHeight);
-    SkDEBUGCODE(this->validate();)
-}
-
-GrDDLTextureStripAtlas::~GrDDLTextureStripAtlas() { delete[] fRows; }
-
-// Flush the current state of the atlas.
-void GrDDLTextureStripAtlas::finish(GrProxyProvider* proxyProvider) {
-    SkDEBUGCODE(this->validate();)
-
-    if (!fCurRow) {
-        SkASSERT(!fCurProxy && !fAtlasBitmap);
-        return;
-    }
-
-    int height = fCurRow * fDesc.fRowHeight;
-    SkASSERT(height <= fDesc.fHeight);
-
-    SkImageInfo ii = SkImageInfo::Make(fDesc.fWidth, height,
-                                       fDesc.fColorType, kPremul_SkAlphaType);
-    fAtlasBitmap->allocPixels(ii);
-
-    for (int i = 0; i < fCurRow; ++i) {
-        SkASSERT(fRows[i].fBitmap.height() == fDesc.fRowHeight);
-
-        int yPos = i * fDesc.fRowHeight;
-        fAtlasBitmap->writePixels(fRows[i].fBitmap.pixmap(), 0, yPos);
-    }
-
-    GrUniqueKey key;
-    {
-        static const GrUniqueKey::Domain kTextureStripAtlasDomain = GrUniqueKey::GenerateDomain();
-        GrUniqueKey::Builder builder(&key, kTextureStripAtlasDomain, fCurRow,
-                                     "DDL Texture Strip Atlas");
-        for (int i = 0; i < fCurRow; ++i) {
-            builder[i] = fRows[i].fBitmap.getGenerationID();
-        }
-        builder.finish();
-    }
-
-    sk_sp<GrTextureProxy> interloper = proxyProvider->findProxyByUniqueKey(key,
-                                                                           fCurProxy->origin());
-    if (!interloper) {
-        // In the unlikely event that there is already a proxy with this key (i.e., it has exactly
-        // the same strips in exactly the same order) we'll just let it keep the key.
-        proxyProvider->assignUniqueKeyToProxy(key, fCurProxy.get());
-    }
-
-    // reset the state for the next aggregate texture
-    for (int i = 0; i < fCurRow; ++i) {
-        fRows[i].fBitmap.reset();
-    }
-    fCurRow = 0;
-    fCurProxy = nullptr;
-    fAtlasBitmap = nullptr;
-    fKeyTable.rewind();
-    SkDEBUGCODE(this->validate();)
-}
-
-int GrDDLTextureStripAtlas::addStrip(GrContext* context, const SkBitmap& bitmap) {
-    SkDEBUGCODE(this->validate();)
-
-    const int key = bitmap.getGenerationID();
-    int index = this->searchByKey(key);
-
-    if (fCurRow >= fMaxNumRows && index < 0) {
-        // The current atlas is full and adding another strip would make it overflow. Calve it off
-        // and allow the next block to start a new one.
-        this->finish(context->contextPriv().proxyProvider());
-        index = this->searchByKey(key); // 'finish' cleared the table
-    }
-
-    if (!fCurProxy) {
-        SkASSERT(!fAtlasBitmap);
-
-        const GrCaps* caps = context->contextPriv().caps();
-        GrPixelConfig pixelConfig = SkColorType2GrPixelConfig(fDesc.fColorType);
-        SkASSERT(kUnknown_GrPixelConfig != pixelConfig);
-
-        SkBitmap* atlasBitmap = new SkBitmap();
-
-        fCurProxy = GrProxyProvider::MakeFullyLazyProxy(
-                [atlasBitmap, pixelConfig](GrResourceProvider* provider) -> sk_sp<GrSurface> {
-                        if (!provider) {
-                            delete atlasBitmap;
-                            return sk_sp<GrSurface>();
-                        }
-                        // When this is called 'atlasBitmap' should've been filled in and be
-                        // non-empty
-                        SkASSERT(atlasBitmap->width() && atlasBitmap->height());
-                        GrSurfaceDesc desc;
-                        desc.fFlags = kNone_GrSurfaceFlags;
-                        desc.fWidth = atlasBitmap->width();
-                        desc.fHeight = atlasBitmap->height();
-                        desc.fConfig = pixelConfig;
-
-                        GrMipLevel mipLevel = { atlasBitmap->getPixels(), atlasBitmap->rowBytes() };
-
-                        return provider->createTexture(desc, SkBudgeted::kYes,
-                                                       SkBackingFit::kExact, mipLevel);
-                },
-                GrProxyProvider::Renderable::kNo, kTopLeft_GrSurfaceOrigin, pixelConfig, *caps);
-
-        fAtlasBitmap = atlasBitmap;
-    }
-
-    SkASSERT(bitmap.width() == fDesc.fWidth);
-    SkASSERT(bitmap.height() == fDesc.fRowHeight);
-    SkASSERT(!context->contextPriv().resourceProvider());  // This atlas class is DDL specific
-    SkASSERT(fCurRow < fMaxNumRows);
-
-    int rowNumber = -1;
-
-    if (index >= 0) {
-        // We already have the data in a row, so we can just return that row
-        AtlasRow* row = fKeyTable[index];
-
-        // Since all the rows are always stored in a contiguous array, we can save the memory
-        // required for storing row numbers and just compute it with some pointer arithmetic
-        rowNumber = static_cast<int>(row - fRows);
-    } else {
-        // ~index is the index where we will insert the new key to keep things sorted
-        index = ~index;
-
-        rowNumber = fCurRow;
-        fRows[fCurRow].fBitmap = bitmap;
-
-        AtlasRow* row = &fRows[rowNumber];
-        fKeyTable.insert(index, 1, &row);
-
-        ++fCurRow;
-        SkASSERT(fCurRow <= fMaxNumRows);
-    }
-
-    SkASSERT(rowNumber >= 0);
-    SkDEBUGCODE(this->validate();)
-    return rowNumber;
-}
-
-int GrDDLTextureStripAtlas::searchByKey(uint32_t generationID) {
-    static struct AtlasRowLessFunctor {
-        bool operator()(const AtlasRow* row, const uint32_t& id) const {
-            return row->fBitmap.getGenerationID() < id;
-        }
-        bool operator()(const uint32_t& id, const AtlasRow* row) const {
-            return id < row->fBitmap.getGenerationID();
-        }
-    } functor;
-
-    return SkTSearch(fKeyTable.begin(), fKeyTable.count(), generationID, sizeof(AtlasRow*),
-                     functor);
-}
-
-#ifdef SK_DEBUG
-void GrDDLTextureStripAtlas::validate() {
-    static const int kBitmapInvalidGenID = 0;
-
-    // Our key table should be sorted
-    uint32_t prev = fKeyTable.count() >= 1 ? fKeyTable[0]->fBitmap.getGenerationID() : 0;
-    for (int i = 1; i < fKeyTable.count(); ++i) {
-        AtlasRow* row = fKeyTable[i];
-        SkASSERT(prev < row->fBitmap.getGenerationID());
-        SkASSERT(row->fBitmap.getGenerationID() != kBitmapInvalidGenID);
-        prev = row->fBitmap.getGenerationID();
-    }
-
-    for (int i = 0; i < fCurRow; ++i) {
-        // These should all have a valid bitmap and be in the search table
-        SkASSERT(fRows[i].fBitmap.getGenerationID() != kBitmapInvalidGenID);
-        SkASSERT(this->searchByKey(fRows[i].fBitmap.getGenerationID()) >= 0);
-    }
-    for (int i = fCurRow; i < fMaxNumRows; ++i) {
-        // These should all be empty
-        SkASSERT(fRows[i].fBitmap.getGenerationID() == kBitmapInvalidGenID);
-    }
-}
-#endif
diff --git a/src/gpu/effects/GrDDLTextureStripAtlas.h b/src/gpu/effects/GrDDLTextureStripAtlas.h
deleted file mode 100644
index 5fb5804..0000000
--- a/src/gpu/effects/GrDDLTextureStripAtlas.h
+++ /dev/null
@@ -1,89 +0,0 @@
-/*
- * Copyright 2018 Google Inc.
- *
- * Use of this source code is governed by a BSD-style license that can be
- * found in the LICENSE file.
- */
-
-#ifndef GrDDLTextureStripAtlas_DEFINED
-#define GrDDLTextureStripAtlas_DEFINED
-
-#include "GrTextureStripAtlas.h"
-
-#include "SkBitmap.h"
-#include "SkTDArray.h"
-
-/**
- * The DDL version of the texture strip atlas consolidates individual strips into a larger texture
- * until some limit is reached, at which point a new large texture is started.
- * This can lead to the same strip being duplicated in VRAM. This can happen if a strip appears once
- * early in a rendering (that has, say, a lot of gradients) and then again later in the rendering
- * when one of the large textures has been filled. The second, probably more common, case is
- * if the same strip is used in different DDL recordings. Since the texture strip atlases aren't
- * dedupped across threads, if the same strip is used in two different DDL recordings it will
- * be duplicated in both of the DDL recorders' atlases.
- * Note, one additional feature of the DDL texture strip atlases is that, if DDL recording is ended
- * before one of the large textures is full, the large texture will be "shrunk" to fit its
- * contents.
- */
-class GrDDLTextureStripAtlas final : public GrTextureStripAtlas {
-public:
-    ~GrDDLTextureStripAtlas() final;
-
-    // Overrides from GrTextureStripAtlas
-    void lockRow(int row) final { /* The DDL version doesn't lock & unlock individual rows */}
-    void unlockRow(int row) final { /* The DDL version doesn't lock & unlock individual rows */}
-
-    // Caution: this method will only return the appropriate proxy after a successful 'addStrip'
-    // call has been made. Additionally, the proxy return will be fully lazy (i.e., its final
-    // height will be unknown).
-    sk_sp<GrTextureProxy> asTextureProxyRef() const final {
-        SkASSERT(fCurProxy);
-        return fCurProxy;
-    }
-
-private:
-    friend class GrTextureStripAtlasManager; // for ctor
-
-    // Overrides from GrTextureStripAtlas
-    int addStrip(GrContext*, const SkBitmap&) final;
-    void finish(GrProxyProvider*) final;
-
-    /**
-     * The state of a single row in our cache. For the DDL texture strip atlas we hold onto all
-     * the individual strip bitmaps and, upon finish, combine them all into a single bitmap.
-     */
-    struct AtlasRow : ::SkNoncopyable {
-        AtlasRow() {}
-
-        SkBitmap fBitmap;
-    };
-
-    /**
-     * Only the GrTextureStripAtlasManager is allowed to create GrDDLTextureStripAtlas
-     */
-    GrDDLTextureStripAtlas(const Desc& desc);
-
-    /**
-     * Searches the key table for a key and returns the index if found; if not found, it returns
-     * the bitwise not of the index at which we could insert the key to maintain a sorted list.
-     **/
-    int searchByKey(uint32_t key);
-
-    SkDEBUGCODE(void validate();)
-
-    sk_sp<GrTextureProxy> fCurProxy;    // the lazy proxy that will be split off in the finish call
-    SkBitmap*             fAtlasBitmap; // the bitmap backing 'fCurProxy'
-
-    const uint16_t        fMaxNumRows;
-    uint16_t              fCurRow;
-
-    AtlasRow*             fRows;        // We just store the source bitmap for each row.
-
-    // A list of pointers to AtlasRows that currently contain cached images, sorted by key
-    SkTDArray<AtlasRow*> fKeyTable;
-
-    typedef GrTextureStripAtlas INHERITED;
-};
-
-#endif
diff --git a/src/gpu/effects/GrDynamicTextureStripAtlas.cpp b/src/gpu/effects/GrDynamicTextureStripAtlas.cpp
deleted file mode 100644
index 04683e1..0000000
--- a/src/gpu/effects/GrDynamicTextureStripAtlas.cpp
+++ /dev/null
@@ -1,334 +0,0 @@
-/*
- * Copyright 2018 Google Inc.
- *
- * Use of this source code is governed by a BSD-style license that can be
- * found in the LICENSE file.
- */
-
-#include "GrDynamicTextureStripAtlas.h"
-
-#include "GrContextPriv.h"
-#include "SkAtomics.h"
-#include "SkGr.h"
-#include "SkTSearch.h"
-
-#ifdef SK_DEBUG
-    #define VALIDATE this->validate()
-#else
-    #define VALIDATE
-#endif
-
-uint32_t GrDynamicTextureStripAtlas::CreateUniqueID() {
-    static int32_t gUniqueID = SK_InvalidUniqueID;
-    uint32_t id;
-    // Loop in case our global wraps around, as we never want to return a 0.
-    do {
-        id = static_cast<uint32_t>(sk_atomic_inc(&gUniqueID) + 1);
-    } while (id == SK_InvalidUniqueID);
-    return id;
-}
-
-GrDynamicTextureStripAtlas::GrDynamicTextureStripAtlas(const Desc& desc)
-        : INHERITED(desc)
-        , fCacheKey(CreateUniqueID())
-        , fLockedRows(0)
-        , fNumRows(desc.fHeight / desc.fRowHeight)
-        , fRows(new AtlasRow[fNumRows])
-        , fLRUFront(nullptr)
-        , fLRUBack(nullptr) {
-    SkASSERT(fNumRows * fDesc.fRowHeight == fDesc.fHeight);
-    this->initLRU();
-    fNormalizedYHeight = SK_Scalar1 / fDesc.fHeight;
-    VALIDATE;
-}
-
-GrDynamicTextureStripAtlas::~GrDynamicTextureStripAtlas() { delete[] fRows; }
-
-void GrDynamicTextureStripAtlas::lockRow(int row) {
-    // This should only be called on a row that is already locked.
-    SkASSERT(fRows[row].fLocks);
-    fRows[row].fLocks++;
-    ++fLockedRows;
-}
-
-int GrDynamicTextureStripAtlas::addStrip(GrContext* context, const SkBitmap& bitmap) {
-    VALIDATE;
-
-    if (!context->contextPriv().resourceProvider()) {
-        // DDL TODO: For DDL we need to schedule inline & ASAP uploads. However these systems
-        // currently use the flushState which we can't use for the opList-based DDL phase.
-        // For the opList-based solution every texture strip will get its own texture proxy.
-        // We will revisit this for the flushState-based solution.
-        return -1;
-    }
-
-    if (0 == fLockedRows) {
-        this->lockTexture(context);
-        if (!fTexContext) {
-            return -1;
-        }
-    }
-
-    int key = bitmap.getGenerationID();
-    int rowNumber = -1;
-    int index = this->searchByKey(key);
-
-    if (index >= 0) {
-        // We already have the data in a row, so we can just return that row
-        AtlasRow* row = fKeyTable[index];
-        if (0 == row->fLocks) {
-            this->removeFromLRU(row);
-        }
-        ++row->fLocks;
-        ++fLockedRows;
-
-        // Since all the rows are always stored in a contiguous array, we can save the memory
-        // required for storing row numbers and just compute it with some pointer arithmetic
-        rowNumber = static_cast<int>(row - fRows);
-    } else {
-        // ~index is the index where we will insert the new key to keep things sorted
-        index = ~index;
-
-        // We don't have this data cached, so pick the least recently used row to copy into
-        AtlasRow* row = this->getLRU();
-
-        ++fLockedRows;
-
-        if (nullptr == row) {
-            // force a flush, which should unlock all the rows; then try again
-            context->contextPriv().flush(nullptr); // tighten this up?
-            row = this->getLRU();
-            if (nullptr == row) {
-                --fLockedRows;
-                return -1;
-            }
-        }
-
-        this->removeFromLRU(row);
-
-        uint32_t oldKey = row->fKey;
-
-        // If we are writing into a row that already held bitmap data, we need to remove the
-        // reference to that genID which is stored in our sorted table of key values.
-        if (oldKey != kEmptyAtlasRowKey) {
-
-            // Find the entry in the list; if it's before the index where we plan on adding the new
-            // entry, we decrement since it will shift elements ahead of it back by one.
-            int oldIndex = this->searchByKey(oldKey);
-            if (oldIndex < index) {
-                --index;
-            }
-
-            fKeyTable.remove(oldIndex);
-        }
-
-        row->fKey = key;
-        row->fLocks = 1;
-        fKeyTable.insert(index, 1, &row);
-        rowNumber = static_cast<int>(row - fRows);
-
-        SkASSERT(bitmap.width() == fDesc.fWidth);
-        SkASSERT(bitmap.height() == fDesc.fRowHeight);
-
-        // Pass in the kDontFlush flag, since we know we're writing to a part of this texture
-        // that is not currently in use
-        fTexContext->writePixels(bitmap.info(), bitmap.getPixels(), bitmap.rowBytes(),
-                                 0, rowNumber * fDesc.fRowHeight,
-                                 GrContextPriv::kDontFlush_PixelOpsFlag);
-    }
-
-    SkASSERT(rowNumber >= 0);
-    VALIDATE;
-    return rowNumber;
-}
-
-sk_sp<GrTextureProxy> GrDynamicTextureStripAtlas::asTextureProxyRef() const {
-    return fTexContext->asTextureProxyRef();
-}
-
-void GrDynamicTextureStripAtlas::unlockRow(int row) {
-    VALIDATE;
-    --fRows[row].fLocks;
-    --fLockedRows;
-    SkASSERT(fRows[row].fLocks >= 0 && fLockedRows >= 0);
-    if (0 == fRows[row].fLocks) {
-        this->appendLRU(fRows + row);
-    }
-    if (0 == fLockedRows) {
-        this->unlockTexture();
-    }
-    VALIDATE;
-}
-
-GrDynamicTextureStripAtlas::AtlasRow* GrDynamicTextureStripAtlas::getLRU() {
-    // Front is least-recently-used
-    AtlasRow* row = fLRUFront;
-    return row;
-}
-
-void GrDynamicTextureStripAtlas::lockTexture(GrContext* context) {
-
-    static const GrUniqueKey::Domain kDomain = GrUniqueKey::GenerateDomain();
-    GrUniqueKey key;
-    GrUniqueKey::Builder builder(&key, kDomain, 1);
-    builder[0] = static_cast<uint32_t>(fCacheKey);
-    builder.finish();
-
-    GrProxyProvider* proxyProvider = context->contextPriv().proxyProvider();
-
-    sk_sp<GrTextureProxy> proxy = proxyProvider->findOrCreateProxyByUniqueKey(
-                                                                key, kTopLeft_GrSurfaceOrigin);
-    if (!proxy) {
-        GrPixelConfig pixelConfig = SkColorType2GrPixelConfig(fDesc.fColorType);
-
-        GrSurfaceDesc texDesc;
-        texDesc.fWidth  = fDesc.fWidth;
-        texDesc.fHeight = fDesc.fHeight;
-        texDesc.fConfig = pixelConfig;
-
-        proxy = proxyProvider->createProxy(texDesc, kTopLeft_GrSurfaceOrigin, SkBackingFit::kExact,
-                                           SkBudgeted::kYes, GrInternalSurfaceFlags::kNoPendingIO);
-        if (!proxy) {
-            return;
-        }
-
-        SkASSERT(proxy->origin() == kTopLeft_GrSurfaceOrigin);
-        proxyProvider->assignUniqueKeyToProxy(key, proxy.get());
-        // This is a new texture, so all of our cache info is now invalid
-        this->initLRU();
-        fKeyTable.rewind();
-    }
-    SkASSERT(proxy);
-    fTexContext = context->contextPriv().makeWrappedSurfaceContext(std::move(proxy));
-}
-
-void GrDynamicTextureStripAtlas::unlockTexture() {
-    SkASSERT(fTexContext && 0 == fLockedRows);
-    fTexContext.reset();
-}
-
-void GrDynamicTextureStripAtlas::initLRU() {
-    fLRUFront = nullptr;
-    fLRUBack = nullptr;
-    // Initially all the rows are in the LRU list
-    for (int i = 0; i < fNumRows; ++i) {
-        fRows[i].fKey = kEmptyAtlasRowKey;
-        fRows[i].fNext = nullptr;
-        fRows[i].fPrev = nullptr;
-        this->appendLRU(fRows + i);
-    }
-    SkASSERT(nullptr == fLRUFront || nullptr == fLRUFront->fPrev);
-    SkASSERT(nullptr == fLRUBack || nullptr == fLRUBack->fNext);
-}
-
-void GrDynamicTextureStripAtlas::appendLRU(AtlasRow* row) {
-    SkASSERT(nullptr == row->fPrev && nullptr == row->fNext);
-    if (nullptr == fLRUFront && nullptr == fLRUBack) {
-        fLRUFront = row;
-        fLRUBack = row;
-    } else {
-        row->fPrev = fLRUBack;
-        fLRUBack->fNext = row;
-        fLRUBack = row;
-    }
-}
-
-void GrDynamicTextureStripAtlas::removeFromLRU(AtlasRow* row) {
-    SkASSERT(row);
-    if (row->fNext && row->fPrev) {
-        row->fPrev->fNext = row->fNext;
-        row->fNext->fPrev = row->fPrev;
-    } else {
-        if (nullptr == row->fNext) {
-            SkASSERT(row == fLRUBack);
-            fLRUBack = row->fPrev;
-            if (fLRUBack) {
-                fLRUBack->fNext = nullptr;
-            }
-        }
-        if (nullptr == row->fPrev) {
-            SkASSERT(row == fLRUFront);
-            fLRUFront = row->fNext;
-            if (fLRUFront) {
-                fLRUFront->fPrev = nullptr;
-            }
-        }
-    }
-    row->fNext = nullptr;
-    row->fPrev = nullptr;
-}
-
-int GrDynamicTextureStripAtlas::searchByKey(uint32_t key) {
-    AtlasRow target;
-    target.fKey = key;
-    return SkTSearch<const AtlasRow, KeyLess>((const AtlasRow**)fKeyTable.begin(),
-                                              fKeyTable.count(),
-                                              &target,
-                                              sizeof(AtlasRow*));
-}
-
-#ifdef SK_DEBUG
-void GrDynamicTextureStripAtlas::validate() {
-    // Our key table should be sorted
-    uint32_t prev = 1 > fKeyTable.count() ? 0 : fKeyTable[0]->fKey;
-    for (int i = 1; i < fKeyTable.count(); ++i) {
-        SkASSERT(prev < fKeyTable[i]->fKey);
-        SkASSERT(fKeyTable[i]->fKey != kEmptyAtlasRowKey);
-        prev = fKeyTable[i]->fKey;
-    }
-
-    int lruCount = 0;
-    // Validate LRU pointers, and count LRU entries
-    SkASSERT(nullptr == fLRUFront || nullptr == fLRUFront->fPrev);
-    SkASSERT(nullptr == fLRUBack  || nullptr == fLRUBack->fNext);
-    for (AtlasRow* r = fLRUFront; r != nullptr; r = r->fNext) {
-        if (nullptr == r->fNext) {
-            SkASSERT(r == fLRUBack);
-        } else {
-            SkASSERT(r->fNext->fPrev == r);
-        }
-        ++lruCount;
-    }
-
-    int rowLocks = 0;
-    int freeRows = 0;
-
-    for (int i = 0; i < fNumRows; ++i) {
-        rowLocks += fRows[i].fLocks;
-        if (0 == fRows[i].fLocks) {
-            ++freeRows;
-            bool inLRU = false;
-            // Step through the LRU and make sure it's present
-            for (AtlasRow* r = fLRUFront; r != nullptr; r = r->fNext) {
-                if (r == &fRows[i]) {
-                    inLRU = true;
-                    break;
-                }
-            }
-            SkASSERT(inLRU);
-        } else {
-            // If we are locked, we should have a key
-            SkASSERT(kEmptyAtlasRowKey != fRows[i].fKey);
-        }
-
-        // If we have a key != kEmptyAtlasRowKey, it should be in the key table
-        SkASSERT(fRows[i].fKey == kEmptyAtlasRowKey || this->searchByKey(fRows[i].fKey) >= 0);
-    }
-
-    // Our count of locks should equal the sum of row locks, unless we ran out of rows and flushed,
-    // in which case we'll have one more lock than recorded in the rows (to represent the pending
-    // lock of a row; which ensures we don't unlock the texture prematurely).
-    SkASSERT(rowLocks == fLockedRows || rowLocks + 1 == fLockedRows);
-
-    // We should have one lru entry for each free row
-    SkASSERT(freeRows == lruCount);
-
-    // If we have locked rows, we should have a locked texture, otherwise
-    // it should be unlocked
-    if (fLockedRows == 0) {
-        SkASSERT(!fTexContext);
-    } else {
-        SkASSERT(fTexContext);
-    }
-}
-#endif
diff --git a/src/gpu/effects/GrDynamicTextureStripAtlas.h b/src/gpu/effects/GrDynamicTextureStripAtlas.h
deleted file mode 100644
index 301617b..0000000
--- a/src/gpu/effects/GrDynamicTextureStripAtlas.h
+++ /dev/null
@@ -1,133 +0,0 @@
-/*
- * Copyright 2018 Google Inc.
- *
- * Use of this source code is governed by a BSD-style license that can be
- * found in the LICENSE file.
- */
-
-#ifndef GrDynamicTextureStripAtlas_DEFINED
-#define GrDynamicTextureStripAtlas_DEFINED
-
-#include "GrTextureStripAtlas.h"
-#include "SkTDArray.h"
-
-class GrSurfaceContext;
-
-/**
- * Maintains a single large texture whose rows store many textures of a small fixed height,
- * stored in rows across the x-axis such that we can safely wrap/repeat them horizontally.
- */
-class GrDynamicTextureStripAtlas final : public GrTextureStripAtlas {
-public:
-    ~GrDynamicTextureStripAtlas() final;
-
-    /**
-     * This is intended to be used when cloning a processor that already holds a lock. It is
-     * assumed that the row already has at least one lock.
-     */
-    void lockRow(int row) final;
-    void unlockRow(int row) final;
-
-    sk_sp<GrTextureProxy> asTextureProxyRef() const final;
-
-private:
-    friend class GrTextureStripAtlasManager; // for ctor
-
-    /**
-     * Only the GrTextureStripAtlasManager is allowed to create GrTextureStripAtlases
-     */
-    GrDynamicTextureStripAtlas(const Desc& desc);
-
-    /**
-     * Add a texture to the atlas
-     *  @param data Bitmap data to copy into the row
-     *  @return The row index we inserted into, or -1 if we failed to find an open row. The caller
-     *      is responsible for calling unlockRow() with this row index when it's done with it.
-     */
-    int addStrip(GrContext*, const SkBitmap&) final;
-
-    void finish(GrProxyProvider*) final { SkASSERT(0); }  // this is only called in DDL mode
-
-    static uint32_t CreateUniqueID();
-
-    // Key to indicate an atlas row without any meaningful data stored in it
-    const static uint32_t kEmptyAtlasRowKey = 0xffffffff;
-
-    /**
-     * The state of a single row in our cache, next/prev pointers allow these to be chained
-     * together to represent LRU status
-     */
-    struct AtlasRow : ::SkNoncopyable {
-        AtlasRow() : fKey(kEmptyAtlasRowKey), fLocks(0), fNext(nullptr), fPrev(nullptr) { }
-        // GenerationID of the bitmap that is represented by this row, 0xffffffff means "empty"
-        uint32_t fKey;
-        // How many times this has been locked (0 == unlocked)
-        int32_t fLocks;
-        // We maintain an LRU linked list between unlocked nodes with these pointers
-        AtlasRow* fNext;
-        AtlasRow* fPrev;
-    };
-
-    void lockTexture(GrContext*);
-    void unlockTexture();
-
-    /**
-     * Initialize our LRU list (if one already exists, clear it and start anew)
-     */
-    void initLRU();
-
-    /**
-     * Grabs the least recently used free row out of the LRU list, returns nullptr if no rows
-     * are free.
-     */
-    AtlasRow* getLRU();
-
-    void appendLRU(AtlasRow* row);
-    void removeFromLRU(AtlasRow* row);
-
-    /**
-     * Searches the key table for a key and returns the index if found; if not found, it returns
-     * the bitwise not of the index at which we could insert the key to maintain a sorted list.
-     **/
-    int searchByKey(uint32_t key);
-
-    /**
-     * Compare two atlas rows by key, so we can sort/search by key
-     */
-    static bool KeyLess(const AtlasRow& lhs, const AtlasRow& rhs) {
-        return lhs.fKey < rhs.fKey;
-    }
-
-#ifdef SK_DEBUG
-    void validate();
-#endif
-
-    // A unique ID for this atlas, so we can be sure that if we
-    // get a texture back from the texture cache, that it's the same one we last used.
-    const uint32_t fCacheKey;
-
-    // Total locks on all rows (when this reaches zero, we can unlock our texture)
-    int32_t fLockedRows;
-
-    const uint16_t fNumRows;
-    sk_sp<GrSurfaceContext> fTexContext;
-
-    SkScalar fNormalizedYHeight;
-
-    // Array of AtlasRows which store the state of all our rows. Stored in a contiguous array, in
-    // order that they appear in our texture, this means we can subtract this pointer from a row
-    // pointer to get its index in the texture, and can save storing a row number in AtlasRow.
-    AtlasRow* fRows;
-
-    // Head and tail for linked list of least-recently-used rows (front = least recently used).
-    // Note that when a texture is locked, it gets removed from this list until it is unlocked.
-    AtlasRow* fLRUFront;
-    AtlasRow* fLRUBack;
-
-    // A list of pointers to AtlasRows that currently contain cached images, sorted by key
-    SkTDArray<AtlasRow*> fKeyTable;
-
-    typedef GrTextureStripAtlas INHERITED;
-};
-
-#endif
diff --git a/src/gpu/effects/GrTextureStripAtlas.cpp b/src/gpu/effects/GrTextureStripAtlas.cpp
deleted file mode 100644
index 42bbf9e..0000000
--- a/src/gpu/effects/GrTextureStripAtlas.cpp
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * Copyright 2012 Google Inc.
- *
- * Use of this source code is governed by a BSD-style license that can be
- * found in the LICENSE file.
- */
-
-#include "GrTextureStripAtlas.h"
-#include "GrContext.h"
-#include "GrContextPriv.h"
-#include "GrDDLTextureStripAtlas.h"
-#include "GrDynamicTextureStripAtlas.h"
-#include "SkBitmap.h"
-
-GrTextureStripAtlasManager::~GrTextureStripAtlasManager() {
-    this->deleteAllAtlases();
-}
-
-void GrTextureStripAtlasManager::deleteAllAtlases() {
-    AtlasHash::Iter iter(&fAtlasCache);
-    while (!iter.done()) {
-        AtlasEntry* tmp = &(*iter);
-        ++iter;
-        delete tmp;
-    }
-    fAtlasCache.reset();
-}
-
-void GrTextureStripAtlasManager::abandon() {
-    this->deleteAllAtlases();
-}
-
-void GrTextureStripAtlasManager::finish(GrProxyProvider* proxyProvider) {
-    for (AtlasHash::Iter iter(&fAtlasCache); !iter.done(); ++iter) {
-        AtlasEntry* tmp = &(*iter);
-        tmp->fAtlas->finish(proxyProvider);
-    }
-}
-
-
-sk_sp<GrTextureStripAtlas> GrTextureStripAtlasManager::addStrip(
-                                                          GrContext* context,
-                                                          const GrTextureStripAtlas::Desc& desc,
-                                                          const SkBitmap& bitmap,
-                                                          int* row) {
-    SkASSERT(kPremul_SkAlphaType == bitmap.alphaType());
-
-    AtlasEntry* entry = fAtlasCache.find(desc);
-    if (!entry) {
-        sk_sp<GrTextureStripAtlas> atlas;
-
-        if (!context->contextPriv().resourceProvider()) {
-            atlas.reset(new GrDDLTextureStripAtlas(desc));
-        } else {
-            atlas.reset(new GrDynamicTextureStripAtlas(desc));
-        }
-
-        entry = new AtlasEntry(sk_sp<GrTextureStripAtlas>(std::move(atlas)));
-        fAtlasCache.add(entry);
-    }
-
-    *row = entry->fAtlas->addStrip(context, bitmap);
-    if (*row < 0) {
-        return nullptr;
-    }
-
-    return entry->fAtlas;
-}
-
diff --git a/src/shaders/gradients/SkGradientShader.cpp b/src/shaders/gradients/SkGradientShader.cpp
index 073ac18..59ed6bc 100644
--- a/src/shaders/gradients/SkGradientShader.cpp
+++ b/src/shaders/gradients/SkGradientShader.cpp
@@ -920,7 +920,6 @@
 #include "GrContextPriv.h"
 #include "GrShaderCaps.h"
 #include "GrTexture.h"
-#include "GrTextureStripAtlas.h"
 #include "gl/GrGLContext.h"
 #include "glsl/GrGLSLFragmentShaderBuilder.h"
 #include "glsl/GrGLSLProgramDataManager.h"
@@ -945,8 +944,7 @@
                                                             ge.fIntervals.count());
             break;
         case GrGradientEffect::InterpolationStrategy::kTexture:
-            fFSYUni = uniformHandler->addUniform(kFragment_GrShaderFlag, kHalf_GrSLType,
-                                                 "GradientYCoordFS");
+            // No extra uniforms
             break;
     }
 }
@@ -966,11 +964,7 @@
                          reinterpret_cast<const float*>(e.fIntervals.begin()));
             break;
         case GrGradientEffect::InterpolationStrategy::kTexture:
-            if (e.fYCoord != fCachedYCoord) {
-                SkScalar yDelta = 1.0f / e.fTextureSampler.peekTexture()->height();
-                pdman.set1f(fFSYUni, e.fYCoord * yDelta);
-                fCachedYCoord = e.fYCoord;
-            }
+            // No additional uniform data beyond what is already managed by the samplers
             break;
     }
 }
@@ -1111,9 +1105,7 @@
         return;
     }
 
-    const char* fsyuni = uniformHandler->getUniformCStr(fFSYUni);
-
-    fragBuilder->codeAppendf("half2 coord = half2(%s, %s);", gradientTValue, fsyuni);
+    fragBuilder->codeAppendf("half2 coord = half2(%s, 0.5);", gradientTValue);
     fragBuilder->codeAppendf("%s = ", outputColor);
     fragBuilder->appendTextureLookupAndModulate(inputColor, texSamplers[0], "coord",
                                                 kFloat2_GrSLType);
@@ -1155,7 +1147,6 @@
 GrGradientEffect::GrGradientEffect(ClassID classID, const CreateArgs& args, bool isOpaque)
     : INHERITED(classID, OptFlags(isOpaque))
     , fWrapMode(args.fWrapMode)
-    , fRow(-1)
     , fIsOpaque(args.fShader->isOpaque())
     , fStrategy(InterpolationStrategy::kTexture)
     , fThreshold(0) {
@@ -1251,60 +1242,35 @@
         SkASSERT(kPremul_SkAlphaType == bitmap.alphaType());
         SkASSERT(bitmap.isImmutable());
 
-        auto atlasManager = args.fContext->contextPriv().textureStripAtlasManager();
-
-        GrTextureStripAtlas::Desc desc;
-        desc.fWidth  = bitmap.width();
-        desc.fHeight = 32;
-        desc.fRowHeight = bitmap.height(); // always 1 here
-        desc.fColorType = bitmap.colorType();
-
-        int row;
-        fAtlas = atlasManager->addStrip(args.fContext, desc, bitmap, &row);
-        if (!args.fContext->contextPriv().resourceProvider()) {
-            // In DDL mode we should always be able to atlas
-            SkASSERT(fAtlas && row >= 0);
-        }
-
         // We always filter the gradient table. Each table is one row of a texture, always
         // y-clamp.
         GrSamplerState samplerState(args.fWrapMode, GrSamplerState::Filter::kBilerp);
 
-        if (-1 != fRow) {
-            SkASSERT(fAtlas);
+        // We know the samplerState state is:
+        //   clampY, bilerp
+        // and the proxy is:
+        //   exact fit, power of two in both dimensions
+        // Only the x-tileMode is unknown. However, given all the other knowns we know
+        // that GrMakeCachedImageProxy is sufficient (i.e., it won't need to be
+        // extracted to a subset or mipmapped).
 
-            fYCoord = fAtlas->rowToTextureY(fRow);
-            // This is 1/2 places where auto-normalization is disabled bc the gradient T is 0..1
-            fCoordTransform.reset(*args.fMatrix, fAtlas->asTextureProxyRef().get(), false);
-            fTextureSampler.reset(fAtlas->asTextureProxyRef(), samplerState);
-        } else {
-            // In this instance we know the samplerState state is:
-            //   clampY, bilerp
-            // and the proxy is:
-            //   exact fit, power of two in both dimensions
-            // Only the x-tileMode is unknown. However, given all the other knowns we know
-            // that GrMakeCachedImageProxy is sufficient (i.e., it won't need to be
-            // extracted to a subset or mipmapped).
-
-            sk_sp<SkImage> srcImage = SkImage::MakeFromBitmap(bitmap);
-            if (!srcImage) {
-                return;
-            }
-
-            sk_sp<GrTextureProxy> proxy = GrMakeCachedImageProxy(
-                                                     args.fContext->contextPriv().proxyProvider(),
-                                                     std::move(srcImage));
-            if (!proxy) {
-                SkDebugf("Gradient won't draw. Could not create texture.");
-                return;
-            }
-            // This is 2/2 places where auto-normalization is disabled because the graient T is 0..1
-            fCoordTransform.reset(*args.fMatrix, proxy.get(), false);
-            fTextureSampler.reset(std::move(proxy), samplerState);
-            SkASSERT(1 == bitmap.height());
-            fYCoord = SK_ScalarHalf;
+        sk_sp<SkImage> srcImage = SkImage::MakeFromBitmap(bitmap);
+        if (!srcImage) {
+            return;
         }
 
+        sk_sp<GrTextureProxy> proxy = GrMakeCachedImageProxy(
+                                                 args.fContext->contextPriv().proxyProvider(),
+                                                 std::move(srcImage));
+        if (!proxy) {
+            SkDebugf("Gradient won't draw. Could not create texture.");
+            return;
+        }
+        // Auto-normalization is disabled because the gradient T is 0..1
+        fCoordTransform.reset(*args.fMatrix, proxy.get(), false);
+        fTextureSampler.reset(std::move(proxy), samplerState);
+        SkASSERT(1 == bitmap.height());
+
         this->setTextureSamplerCnt(1);
     }
 
@@ -1317,9 +1283,6 @@
         , fWrapMode(that.fWrapMode)
         , fCoordTransform(that.fCoordTransform)
         , fTextureSampler(that.fTextureSampler)
-        , fYCoord(that.fYCoord)
-        , fAtlas(that.fAtlas)
-        , fRow(that.fRow)
         , fIsOpaque(that.fIsOpaque)
         , fStrategy(that.fStrategy)
         , fThreshold(that.fThreshold)
@@ -1328,15 +1291,6 @@
     if (fStrategy == InterpolationStrategy::kTexture) {
         this->setTextureSamplerCnt(1);
     }
-    if (this->useAtlas()) {
-        fAtlas->lockRow(fRow);
-    }
-}
-
-GrGradientEffect::~GrGradientEffect() {
-    if (this->useAtlas()) {
-        fAtlas->unlockRow(fRow);
-    }
 }
 
 bool GrGradientEffect::onIsEqual(const GrFragmentProcessor& processor) const {
@@ -1346,9 +1300,8 @@
         return false;
     }
 
-    SkASSERT(this->useAtlas() == ge.useAtlas());
     if (fStrategy == InterpolationStrategy::kTexture) {
-        if (fYCoord != ge.fYCoord) {
+        if (fTextureSampler != ge.fTextureSampler) {
             return false;
         }
     } else {
diff --git a/src/shaders/gradients/SkGradientShaderPriv.h b/src/shaders/gradients/SkGradientShaderPriv.h
index f3e10d0..2c7a5e4 100644
--- a/src/shaders/gradients/SkGradientShaderPriv.h
+++ b/src/shaders/gradients/SkGradientShaderPriv.h
@@ -231,10 +231,6 @@
 
     class GLSLProcessor;
 
-    ~GrGradientEffect() override;
-
-    bool useAtlas() const { return SkToBool(-1 != fRow); }
-
     // Controls the implementation strategy for this effect.
     // NB: all entries need to be reflected in the key.
     enum class InterpolationStrategy : uint8_t {
@@ -313,9 +309,6 @@
 
     GrCoordTransform fCoordTransform;
     TextureSampler fTextureSampler;
-    SkScalar fYCoord;
-    sk_sp<GrTextureStripAtlas> fAtlas;
-    int fRow;
     bool fIsOpaque;
 
     InterpolationStrategy fStrategy;
@@ -333,10 +326,6 @@
 // Base class for GL gradient effects
 class GrGradientEffect::GLSLProcessor : public GrGLSLFragmentProcessor {
 public:
-    GLSLProcessor() {
-        fCachedYCoord = SK_ScalarMax;
-    }
-
     static uint32_t GenBaseGradientKey(const GrProcessor&);
 
 protected:
@@ -368,10 +357,8 @@
                              const char* outputColor,
                              const char* inputColor);
 
-    SkScalar fCachedYCoord;
     GrGLSLProgramDataManager::UniformHandle fIntervalsUni;
     GrGLSLProgramDataManager::UniformHandle fThresholdUni;
-    GrGLSLProgramDataManager::UniformHandle fFSYUni;
 
     typedef GrGLSLFragmentProcessor INHERITED;
 };
