SkNormalSource::Provider* SkNormalMapSourceImpl::asProvider(const SkShaderBase::ContextRec &rec,
                                                            SkArenaAlloc* alloc) const {
    SkMatrix normTotalInv;
    if (!this->computeNormTotalInverse(rec, &normTotalInv)) {
        return nullptr;
    }

    // Overriding paint's alpha because we need the normal map's RGB channels to be unpremul'd
    SkPaint overridePaint {*(rec.fPaint)};
    overridePaint.setAlpha(0xFF);
    SkShaderBase::ContextRec overrideRec(overridePaint, *(rec.fMatrix), rec.fLocalMatrix,
                                         rec.fPreferredDstType, rec.fDstColorSpace);

    auto* context = as_SB(fMapShader)->makeContext(overrideRec, alloc);
    if (!context) {
        return nullptr;
    }

    return alloc->make<Provider>(*this, context);
}
SkNormalSource::Provider* SkNormalMapSourceImpl::asProvider(const SkShader::ContextRec &rec,
                                                            void *storage) const {
    SkMatrix normTotalInv;
    if (!this->computeNormTotalInverse(rec, &normTotalInv)) {
        return nullptr;
    }

    // Overriding paint's alpha because we need the normal map's RGB channels to be unpremul'd
    void* paintStorage = (char*)storage + sizeof(Provider);
    SkPaint* overridePaint = new (paintStorage) SkPaint(*(rec.fPaint));
    overridePaint->setAlpha(0xFF);
    SkShader::ContextRec overrideRec(*overridePaint, *(rec.fMatrix), rec.fLocalMatrix,
                                     rec.fPreferredDstType);

    void* mapContextStorage = (char*) paintStorage + sizeof(SkPaint);
    SkShader::Context* context = fMapShader->createContext(overrideRec, mapContextStorage);
    if (!context) {
        return nullptr;
    }

    return new (storage) Provider(*this, context, overridePaint);
}