Commit 90404218 by Alexis Hetu Committed by Alexis Hétu

Fixed synchronization issue on MacOS

Because of the way SwiftShader is integrated into Chromium on MacOS, a synchronization issue exists when Chromium attempts to use an IOSurface before SwiftShader is done rendering into it. In order to solve this, all draw calls that end up rendering into an IOSurface must be synchronized within SwiftShader and can't yield to Chromium until rendering is complete. Bug chromium:847094 Change-Id: If2dba4fa998e7437ec414d3b4aff9e8b19ecc128 Reviewed-on: https://swiftshader-review.googlesource.com/19188Tested-by: 's avatarAlexis Hétu <sugoi@google.com> Reviewed-by: 's avatarNicolas Capens <nicolascapens@google.com>
parent 48456333
......@@ -1332,6 +1332,15 @@ namespace egl
#endif
}
bool ClientBuffer::targetRequiresSync() const
{
#if defined(__APPLE__)
return true;
#else
return false;
#endif
}
class ClientBufferImage : public egl::Image
{
public:
......@@ -1422,6 +1431,11 @@ namespace egl
sw::Surface::unlockExternal();
}
bool targetRequiresSync() const override
{
return clientBuffer.targetRequiresSync();
}
void release() override
{
Image::release();
......
......@@ -224,6 +224,7 @@ namespace sw
int ss = context->getSuperSampleCount();
int ms = context->getMultiSampleCount();
bool targetRequiresSync = false;
for(int q = 0; q < ss; q++)
{
......@@ -607,6 +608,7 @@ namespace sw
if(draw->renderTarget[index])
{
unsigned int layer = context->renderTargetLayer[index];
targetRequiresSync |= context->renderTarget[index]->targetRequiresSync();
data->colorBuffer[index] = (unsigned int*)context->renderTarget[index]->lockInternal(0, 0, layer, LOCK_READWRITE, MANAGED);
data->colorBuffer[index] += q * ms * context->renderTarget[index]->getSliceB(true);
data->colorPitchB[index] = context->renderTarget[index]->getInternalPitchB();
......@@ -620,6 +622,7 @@ namespace sw
if(draw->depthBuffer)
{
unsigned int layer = context->depthBufferLayer;
targetRequiresSync |= context->depthBuffer->targetRequiresSync();
data->depthBuffer = (float*)context->depthBuffer->lockInternal(0, 0, layer, LOCK_READWRITE, MANAGED);
data->depthBuffer += q * ms * context->depthBuffer->getSliceB(true);
data->depthPitchB = context->depthBuffer->getInternalPitchB();
......@@ -629,6 +632,7 @@ namespace sw
if(draw->stencilBuffer)
{
unsigned int layer = context->stencilBufferLayer;
targetRequiresSync |= context->stencilBuffer->targetRequiresSync();
data->stencilBuffer = (unsigned char*)context->stencilBuffer->lockStencil(0, 0, layer, MANAGED);
data->stencilBuffer += q * ms * context->stencilBuffer->getSliceB(true);
data->stencilPitchB = context->stencilBuffer->getStencilPitchB();
......@@ -675,6 +679,12 @@ namespace sw
}
}
}
// TODO(sugoi): This is a temporary brute-force workaround to ensure IOSurface synchronization.
if(targetRequiresSync)
{
synchronize();
}
}
void Renderer::clear(void *value, Format format, Surface *dest, const Rect &clearRect, unsigned int rgbaMask)
......
......@@ -321,6 +321,7 @@ namespace sw
inline int getStencilSliceB() const;
void sync(); // Wait for lock(s) to be released.
virtual bool targetRequiresSync() const { return false; }
inline bool isUnlocked() const; // Only reliable after sync().
inline int getSamples() const;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment