Merge "In Vk DeferredLayerUpdater make sure we releause buffers to foreign queue." into sc-dev
This commit is contained in:
committed by
Android (Google) Code Review
commit
433ba6df07
@@ -89,5 +89,27 @@ void AutoBackendTextureRelease::newBufferContent(GrDirectContext* context) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void AutoBackendTextureRelease::releaseQueueOwnership(GrDirectContext* context) {
|
||||||
|
if (!context) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
LOG_ALWAYS_FATAL_IF(Properties::getRenderPipelineType() != RenderPipelineType::SkiaVulkan);
|
||||||
|
if (mBackendTexture.isValid()) {
|
||||||
|
// Passing in VK_IMAGE_LAYOUT_UNDEFINED means we keep the old layout.
|
||||||
|
GrBackendSurfaceMutableState newState(VK_IMAGE_LAYOUT_UNDEFINED,
|
||||||
|
VK_QUEUE_FAMILY_FOREIGN_EXT);
|
||||||
|
|
||||||
|
// The unref for this ref happens in the releaseProc passed into setBackendTextureState. The
|
||||||
|
// releaseProc callback will be made when the work to set the new state has finished on the
|
||||||
|
// gpu.
|
||||||
|
ref();
|
||||||
|
// Note that we don't have an explicit call to set the backend texture back onto the
|
||||||
|
// graphics queue when we use the VkImage again. Internally, Skia will notice that the image
|
||||||
|
// is not on the graphics queue and will do the transition automatically.
|
||||||
|
context->setBackendTextureState(mBackendTexture, newState, nullptr, releaseProc, this);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
} /* namespace uirenderer */
|
} /* namespace uirenderer */
|
||||||
} /* namespace android */
|
} /* namespace android */
|
||||||
|
|||||||
@@ -49,6 +49,8 @@ public:
|
|||||||
|
|
||||||
void newBufferContent(GrDirectContext* context);
|
void newBufferContent(GrDirectContext* context);
|
||||||
|
|
||||||
|
void releaseQueueOwnership(GrDirectContext* context);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
// The only way to invoke dtor is with unref, when mUsageCount is 0.
|
// The only way to invoke dtor is with unref, when mUsageCount is 0.
|
||||||
~AutoBackendTextureRelease() {}
|
~AutoBackendTextureRelease() {}
|
||||||
|
|||||||
@@ -76,6 +76,9 @@ void DeferredLayerUpdater::destroyLayer() {
|
|||||||
|
|
||||||
mLayer = nullptr;
|
mLayer = nullptr;
|
||||||
|
|
||||||
|
for (auto& [index, slot] : mImageSlots) {
|
||||||
|
slot.clear(mRenderState.getRenderThread().getGrContext());
|
||||||
|
}
|
||||||
mImageSlots.clear();
|
mImageSlots.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -89,31 +92,39 @@ void DeferredLayerUpdater::setPaint(const SkPaint* paint) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static status_t createReleaseFence(bool useFenceSync, EGLSyncKHR* eglFence, EGLDisplay* display,
|
status_t DeferredLayerUpdater::createReleaseFence(bool useFenceSync, EGLSyncKHR* eglFence,
|
||||||
int* releaseFence, void* handle) {
|
EGLDisplay* display, int* releaseFence,
|
||||||
|
void* handle) {
|
||||||
*display = EGL_NO_DISPLAY;
|
*display = EGL_NO_DISPLAY;
|
||||||
RenderState* renderState = (RenderState*)handle;
|
DeferredLayerUpdater* dlu = (DeferredLayerUpdater*)handle;
|
||||||
|
RenderState& renderState = dlu->mRenderState;
|
||||||
status_t err;
|
status_t err;
|
||||||
if (Properties::getRenderPipelineType() == RenderPipelineType::SkiaGL) {
|
if (Properties::getRenderPipelineType() == RenderPipelineType::SkiaGL) {
|
||||||
EglManager& eglManager = renderState->getRenderThread().eglManager();
|
EglManager& eglManager = renderState.getRenderThread().eglManager();
|
||||||
*display = eglManager.eglDisplay();
|
*display = eglManager.eglDisplay();
|
||||||
err = eglManager.createReleaseFence(useFenceSync, eglFence, releaseFence);
|
err = eglManager.createReleaseFence(useFenceSync, eglFence, releaseFence);
|
||||||
} else {
|
} else {
|
||||||
err = renderState->getRenderThread().vulkanManager().createReleaseFence(
|
int previousSlot = dlu->mCurrentSlot;
|
||||||
releaseFence, renderState->getRenderThread().getGrContext());
|
if (previousSlot != -1) {
|
||||||
|
dlu->mImageSlots[previousSlot].releaseQueueOwnership(
|
||||||
|
renderState.getRenderThread().getGrContext());
|
||||||
|
}
|
||||||
|
err = renderState.getRenderThread().vulkanManager().createReleaseFence(
|
||||||
|
releaseFence, renderState.getRenderThread().getGrContext());
|
||||||
}
|
}
|
||||||
return err;
|
return err;
|
||||||
}
|
}
|
||||||
|
|
||||||
static status_t fenceWait(int fence, void* handle) {
|
status_t DeferredLayerUpdater::fenceWait(int fence, void* handle) {
|
||||||
// Wait on the producer fence for the buffer to be ready.
|
// Wait on the producer fence for the buffer to be ready.
|
||||||
status_t err;
|
status_t err;
|
||||||
RenderState* renderState = (RenderState*)handle;
|
DeferredLayerUpdater* dlu = (DeferredLayerUpdater*)handle;
|
||||||
|
RenderState& renderState = dlu->mRenderState;
|
||||||
if (Properties::getRenderPipelineType() == RenderPipelineType::SkiaGL) {
|
if (Properties::getRenderPipelineType() == RenderPipelineType::SkiaGL) {
|
||||||
err = renderState->getRenderThread().eglManager().fenceWait(fence);
|
err = renderState.getRenderThread().eglManager().fenceWait(fence);
|
||||||
} else {
|
} else {
|
||||||
err = renderState->getRenderThread().vulkanManager().fenceWait(
|
err = renderState.getRenderThread().vulkanManager().fenceWait(
|
||||||
fence, renderState->getRenderThread().getGrContext());
|
fence, renderState.getRenderThread().getGrContext());
|
||||||
}
|
}
|
||||||
return err;
|
return err;
|
||||||
}
|
}
|
||||||
@@ -143,9 +154,10 @@ void DeferredLayerUpdater::apply() {
|
|||||||
// cannot tell which mode it is in.
|
// cannot tell which mode it is in.
|
||||||
AHardwareBuffer* hardwareBuffer = ASurfaceTexture_dequeueBuffer(
|
AHardwareBuffer* hardwareBuffer = ASurfaceTexture_dequeueBuffer(
|
||||||
mSurfaceTexture.get(), &slot, &dataspace, transformMatrix, &newContent,
|
mSurfaceTexture.get(), &slot, &dataspace, transformMatrix, &newContent,
|
||||||
createReleaseFence, fenceWait, &mRenderState);
|
createReleaseFence, fenceWait, this);
|
||||||
|
|
||||||
if (hardwareBuffer) {
|
if (hardwareBuffer) {
|
||||||
|
mCurrentSlot = slot;
|
||||||
sk_sp<SkImage> layerImage = mImageSlots[slot].createIfNeeded(
|
sk_sp<SkImage> layerImage = mImageSlots[slot].createIfNeeded(
|
||||||
hardwareBuffer, dataspace, newContent,
|
hardwareBuffer, dataspace, newContent,
|
||||||
mRenderState.getRenderThread().getGrContext());
|
mRenderState.getRenderThread().getGrContext());
|
||||||
@@ -193,7 +205,7 @@ sk_sp<SkImage> DeferredLayerUpdater::ImageSlot::createIfNeeded(AHardwareBuffer*
|
|||||||
if (!mTextureRelease || !mTextureRelease->getImage().get() || dataspace != mDataspace ||
|
if (!mTextureRelease || !mTextureRelease->getImage().get() || dataspace != mDataspace ||
|
||||||
forceCreate || mBuffer != buffer) {
|
forceCreate || mBuffer != buffer) {
|
||||||
if (buffer != mBuffer) {
|
if (buffer != mBuffer) {
|
||||||
clear();
|
clear(context);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!buffer) {
|
if (!buffer) {
|
||||||
@@ -213,8 +225,11 @@ sk_sp<SkImage> DeferredLayerUpdater::ImageSlot::createIfNeeded(AHardwareBuffer*
|
|||||||
return mTextureRelease ? mTextureRelease->getImage() : nullptr;
|
return mTextureRelease ? mTextureRelease->getImage() : nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
void DeferredLayerUpdater::ImageSlot::clear() {
|
void DeferredLayerUpdater::ImageSlot::clear(GrDirectContext* context) {
|
||||||
if (mTextureRelease) {
|
if (mTextureRelease) {
|
||||||
|
if (Properties::getRenderPipelineType() == RenderPipelineType::SkiaVulkan) {
|
||||||
|
this->releaseQueueOwnership(context);
|
||||||
|
}
|
||||||
// The following unref counteracts the initial mUsageCount of 1, set by default initializer.
|
// The following unref counteracts the initial mUsageCount of 1, set by default initializer.
|
||||||
mTextureRelease->unref(true);
|
mTextureRelease->unref(true);
|
||||||
mTextureRelease = nullptr;
|
mTextureRelease = nullptr;
|
||||||
@@ -223,5 +238,12 @@ void DeferredLayerUpdater::ImageSlot::clear() {
|
|||||||
mBuffer = nullptr;
|
mBuffer = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void DeferredLayerUpdater::ImageSlot::releaseQueueOwnership(GrDirectContext* context) {
|
||||||
|
LOG_ALWAYS_FATAL_IF(Properties::getRenderPipelineType() != RenderPipelineType::SkiaVulkan);
|
||||||
|
if (mTextureRelease) {
|
||||||
|
mTextureRelease->releaseQueueOwnership(context);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
} /* namespace uirenderer */
|
} /* namespace uirenderer */
|
||||||
} /* namespace android */
|
} /* namespace android */
|
||||||
|
|||||||
@@ -20,9 +20,12 @@
|
|||||||
#include <SkImage.h>
|
#include <SkImage.h>
|
||||||
#include <SkMatrix.h>
|
#include <SkMatrix.h>
|
||||||
#include <android/hardware_buffer.h>
|
#include <android/hardware_buffer.h>
|
||||||
#include <cutils/compiler.h>
|
|
||||||
#include <android/surface_texture.h>
|
#include <android/surface_texture.h>
|
||||||
|
#include <cutils/compiler.h>
|
||||||
|
#include <utils/Errors.h>
|
||||||
|
|
||||||
|
#include <EGL/egl.h>
|
||||||
|
#include <EGL/eglext.h>
|
||||||
#include <map>
|
#include <map>
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
|
||||||
@@ -103,13 +106,16 @@ private:
|
|||||||
*/
|
*/
|
||||||
class ImageSlot {
|
class ImageSlot {
|
||||||
public:
|
public:
|
||||||
~ImageSlot() { clear(); }
|
~ImageSlot() {}
|
||||||
|
|
||||||
sk_sp<SkImage> createIfNeeded(AHardwareBuffer* buffer, android_dataspace dataspace,
|
sk_sp<SkImage> createIfNeeded(AHardwareBuffer* buffer, android_dataspace dataspace,
|
||||||
bool forceCreate, GrDirectContext* context);
|
bool forceCreate, GrDirectContext* context);
|
||||||
|
|
||||||
|
void releaseQueueOwnership(GrDirectContext* context);
|
||||||
|
|
||||||
|
void clear(GrDirectContext* context);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void clear();
|
|
||||||
|
|
||||||
// the dataspace associated with the current image
|
// the dataspace associated with the current image
|
||||||
android_dataspace mDataspace = HAL_DATASPACE_UNKNOWN;
|
android_dataspace mDataspace = HAL_DATASPACE_UNKNOWN;
|
||||||
@@ -123,6 +129,10 @@ private:
|
|||||||
AutoBackendTextureRelease* mTextureRelease = nullptr;
|
AutoBackendTextureRelease* mTextureRelease = nullptr;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static status_t createReleaseFence(bool useFenceSync, EGLSyncKHR* eglFence, EGLDisplay* display,
|
||||||
|
int* releaseFence, void* handle);
|
||||||
|
static status_t fenceWait(int fence, void* handle);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* DeferredLayerUpdater stores the SkImages that have been allocated by the BufferQueue
|
* DeferredLayerUpdater stores the SkImages that have been allocated by the BufferQueue
|
||||||
* for each buffer slot.
|
* for each buffer slot.
|
||||||
@@ -142,6 +152,7 @@ private:
|
|||||||
SkMatrix* mTransform;
|
SkMatrix* mTransform;
|
||||||
bool mGLContextAttached;
|
bool mGLContextAttached;
|
||||||
bool mUpdateTexImage;
|
bool mUpdateTexImage;
|
||||||
|
int mCurrentSlot = -1;
|
||||||
|
|
||||||
Layer* mLayer;
|
Layer* mLayer;
|
||||||
};
|
};
|
||||||
|
|||||||
Reference in New Issue
Block a user