void GrGLProgram::generateMipmaps(const GrResourceIOProcessor& processor, bool allowSRGBInputs) {
    for (int i = 0; i < processor.numTextureSamplers(); ++i) {
        const GrResourceIOProcessor::TextureSampler& sampler = processor.textureSampler(i);
        fGpu->generateMipmaps(sampler.params(), allowSRGBInputs,
                              static_cast<GrGLTexture*>(sampler.texture()));
    }
}
void GrGLProgram::bindTextures(const GrResourceIOProcessor& processor,
                               bool allowSRGBInputs,
                               int* nextTexSamplerIdx,
                               int* nextTexelBufferIdx) {
    for (int i = 0; i < processor.numTextureSamplers(); ++i) {
        const GrResourceIOProcessor::TextureSampler& sampler = processor.textureSampler(i);
        fGpu->bindTexture((*nextTexSamplerIdx)++, sampler.samplerState(), allowSRGBInputs,
                          static_cast<GrGLTexture*>(sampler.peekTexture()),
                          sampler.proxy()->origin());
    }
    for (int i = 0; i < processor.numBuffers(); ++i) {
        const GrResourceIOProcessor::BufferAccess& access = processor.bufferAccess(i);
        fGpu->bindTexelBuffer((*nextTexelBufferIdx)++, access.texelConfig(),
                              static_cast<GrGLBuffer*>(access.buffer()));
    }
}
void GrGLProgram::bindTextures(const GrResourceIOProcessor& processor,
                               bool allowSRGBInputs,
                               int* nextSamplerIdx) {
    for (int i = 0; i < processor.numTextureSamplers(); ++i) {
        const GrResourceIOProcessor::TextureSampler& sampler = processor.textureSampler(i);
        fGpu->bindTexture((*nextSamplerIdx)++, sampler.params(),
                          allowSRGBInputs, static_cast<GrGLTexture*>(sampler.texture()));
    }
    for (int i = 0; i < processor.numBuffers(); ++i) {
        const GrResourceIOProcessor::BufferAccess& access = processor.bufferAccess(i);
        fGpu->bindTexelBuffer((*nextSamplerIdx)++, access.texelConfig(),
                              static_cast<GrGLBuffer*>(access.buffer()));
    }
    for (int i = 0; i < processor.numImageStorages(); ++i) {
        const GrResourceIOProcessor::ImageStorageAccess& access = processor.imageStorageAccess(i);
        fGpu->bindImageStorage((*nextSamplerIdx)++, access.ioType(),
                               static_cast<GrGLTexture *>(access.texture()));
    }
}
bool GrResourceIOProcessor::hasSameSamplersAndAccesses(const GrResourceIOProcessor& that) const {
    if (this->numTextureSamplers() != that.numTextureSamplers() ||
        this->numBuffers() != that.numBuffers() ||
        this->numImageStorages() != that.numImageStorages()) {
        return false;
    }
    for (int i = 0; i < this->numTextureSamplers(); ++i) {
        if (this->textureSampler(i) != that.textureSampler(i)) {
            return false;
        }
    }
    for (int i = 0; i < this->numBuffers(); ++i) {
        if (this->bufferAccess(i) != that.bufferAccess(i)) {
            return false;
        }
    }
    for (int i = 0; i < this->numImageStorages(); ++i) {
        if (this->imageStorageAccess(i) != that.imageStorageAccess(i)) {
            return false;
        }
    }
    return true;
}