Commit c6a57cb7 by Alexis Hetu Committed by Alexis Hétu

Renderer side code to lock/unlock transform feedback data

Added variables and function calls to lock/unlock transform feedback data used for reading the selected transform feedback varying variables out of the vertex shader. Also fixed uniform buffer unlocking potential race condition. Change-Id: I98790fc36fdf8674506d924b2f21b3e68892811a Reviewed-on: https://swiftshader-review.googlesource.com/5060Tested-by: 's avatarAlexis Hétu <sugoi@google.com> Reviewed-by: 's avatarNicolas Capens <capn@google.com>
parent 6cb8c6c0
...@@ -58,6 +58,12 @@ namespace sw ...@@ -58,6 +58,12 @@ namespace sw
return memcmp(static_cast<const States*>(this), static_cast<const States*>(&state), sizeof(States)) == 0; return memcmp(static_cast<const States*>(this), static_cast<const States*>(&state), sizeof(States)) == 0;
} }
PixelProcessor::UniformBufferInfo::UniformBufferInfo()
{
buffer = nullptr;
offset = 0;
}
PixelProcessor::PixelProcessor(Context *context) : context(context) PixelProcessor::PixelProcessor(Context *context) : context(context)
{ {
setGlobalMipmapBias(0.0f); // Round to highest LOD [0.5, 1.0]: -0.5 setGlobalMipmapBias(0.0f); // Round to highest LOD [0.5, 1.0]: -0.5
...@@ -66,11 +72,6 @@ namespace sw ...@@ -66,11 +72,6 @@ namespace sw
routineCache = 0; routineCache = 0;
setRoutineCacheSize(1024); setRoutineCacheSize(1024);
for(int i = 0; i < MAX_UNIFORM_BUFFER_BINDINGS; i++)
{
uniformBuffer[i] = nullptr;
}
} }
PixelProcessor::~PixelProcessor() PixelProcessor::~PixelProcessor()
...@@ -143,27 +144,16 @@ namespace sw ...@@ -143,27 +144,16 @@ namespace sw
void PixelProcessor::setUniformBuffer(int index, sw::Resource* buffer, int offset) void PixelProcessor::setUniformBuffer(int index, sw::Resource* buffer, int offset)
{ {
uniformBuffer[index] = buffer; uniformBufferInfo[index].buffer = buffer;
uniformBufferOffset[index] = offset; uniformBufferInfo[index].offset = offset;
}
void PixelProcessor::lockUniformBuffers(byte** u)
{
for(int i = 0; i < MAX_UNIFORM_BUFFER_BINDINGS; ++i)
{
u[i] = uniformBuffer[i] ? static_cast<byte*>(uniformBuffer[i]->lock(PUBLIC, PRIVATE)) + uniformBufferOffset[i] : nullptr;
}
} }
void PixelProcessor::unlockUniformBuffers() void PixelProcessor::lockUniformBuffers(byte** u, sw::Resource* uniformBuffers[])
{ {
for(int i = 0; i < MAX_UNIFORM_BUFFER_BINDINGS; ++i) for(int i = 0; i < MAX_UNIFORM_BUFFER_BINDINGS; ++i)
{ {
if(uniformBuffer[i]) u[i] = uniformBufferInfo[i].buffer ? static_cast<byte*>(uniformBufferInfo[i].buffer->lock(PUBLIC, PRIVATE)) + uniformBufferInfo[i].offset : nullptr;
{ uniformBuffers[i] = uniformBufferInfo[i].buffer;
uniformBuffer[i]->unlock();
uniformBuffer[i] = nullptr;
}
} }
} }
......
...@@ -192,8 +192,7 @@ namespace sw ...@@ -192,8 +192,7 @@ namespace sw
virtual void setBooleanConstant(unsigned int index, int boolean); virtual void setBooleanConstant(unsigned int index, int boolean);
virtual void setUniformBuffer(int index, sw::Resource* buffer, int offset); virtual void setUniformBuffer(int index, sw::Resource* buffer, int offset);
virtual void lockUniformBuffers(byte** u); virtual void lockUniformBuffers(byte** u, sw::Resource* uniformBuffers[]);
virtual void unlockUniformBuffers();
virtual void setRenderTarget(int index, Surface *renderTarget); virtual void setRenderTarget(int index, Surface *renderTarget);
virtual void setDepthBuffer(Surface *depthBuffer); virtual void setDepthBuffer(Surface *depthBuffer);
...@@ -304,8 +303,6 @@ namespace sw ...@@ -304,8 +303,6 @@ namespace sw
float4 c[FRAGMENT_UNIFORM_VECTORS]; float4 c[FRAGMENT_UNIFORM_VECTORS];
int4 i[16]; int4 i[16];
bool b[16]; bool b[16];
Resource* uniformBuffer[MAX_UNIFORM_BUFFER_BINDINGS];
int uniformBufferOffset[MAX_UNIFORM_BUFFER_BINDINGS];
// Other semi-constants // Other semi-constants
Stencil stencil; Stencil stencil;
...@@ -314,6 +311,15 @@ namespace sw ...@@ -314,6 +311,15 @@ namespace sw
Factor factor; Factor factor;
private: private:
struct UniformBufferInfo
{
UniformBufferInfo();
Resource* buffer;
int offset;
};
UniformBufferInfo uniformBufferInfo[MAX_UNIFORM_BUFFER_BINDINGS];
void setFogRanges(float start, float end); void setFogRanges(float start, float end);
Context *const context; Context *const context;
......
...@@ -388,7 +388,14 @@ namespace sw ...@@ -388,7 +388,14 @@ namespace sw
draw->psDirtyConstB = 0; draw->psDirtyConstB = 0;
} }
PixelProcessor::lockUniformBuffers(data->ps.u); PixelProcessor::lockUniformBuffers(data->ps.u, draw->pUniformBuffers);
}
else
{
for(int i = 0; i < MAX_UNIFORM_BUFFER_BINDINGS; i++)
{
draw->pUniformBuffers[i] = nullptr;
}
} }
if(context->pixelShaderVersion() <= 0x0104) if(context->pixelShaderVersion() <= 0x0104)
...@@ -442,7 +449,8 @@ namespace sw ...@@ -442,7 +449,8 @@ namespace sw
data->instanceID = context->instanceID; data->instanceID = context->instanceID;
} }
VertexProcessor::lockUniformBuffers(data->vs.u); VertexProcessor::lockUniformBuffers(data->vs.u, draw->vUniformBuffers);
VertexProcessor::lockTransformFeedbackBuffers(data->vs.t, data->vs.reg, data->vs.row, data->vs.col, data->vs.str, draw->transformFeedbackBuffers);
} }
else else
{ {
...@@ -451,6 +459,16 @@ namespace sw ...@@ -451,6 +459,16 @@ namespace sw
draw->vsDirtyConstF = VERTEX_UNIFORM_VECTORS + 1; draw->vsDirtyConstF = VERTEX_UNIFORM_VECTORS + 1;
draw->vsDirtyConstI = 16; draw->vsDirtyConstI = 16;
draw->vsDirtyConstB = 16; draw->vsDirtyConstB = 16;
for(int i = 0; i < MAX_UNIFORM_BUFFER_BINDINGS; i++)
{
draw->vUniformBuffers[i] = nullptr;
}
for(int i = 0; i < MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS; i++)
{
draw->transformFeedbackBuffers[i] = nullptr;
}
} }
if(pixelState.stencilActive) if(pixelState.stencilActive)
...@@ -981,8 +999,25 @@ namespace sw ...@@ -981,8 +999,25 @@ namespace sw
draw.indexBuffer->unlock(); draw.indexBuffer->unlock();
} }
PixelProcessor::unlockUniformBuffers(); for(int i = 0; i < MAX_UNIFORM_BUFFER_BINDINGS; i++)
VertexProcessor::unlockUniformBuffers(); {
if(draw.pUniformBuffers[i])
{
draw.pUniformBuffers[i]->unlock();
}
if(draw.vUniformBuffers[i])
{
draw.vUniformBuffers[i]->unlock();
}
}
for(int i = 0; i < MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS; i++)
{
if(draw.transformFeedbackBuffers[i])
{
draw.transformFeedbackBuffers[i]->unlock();
}
}
draw.vertexRoutine->unbind(); draw.vertexRoutine->unbind();
draw.setupRoutine->unbind(); draw.setupRoutine->unbind();
......
...@@ -123,6 +123,11 @@ namespace sw ...@@ -123,6 +123,11 @@ namespace sw
{ {
float4 c[VERTEX_UNIFORM_VECTORS + 1]; // One extra for indices out of range, c[VERTEX_UNIFORM_VECTORS] = {0, 0, 0, 0} float4 c[VERTEX_UNIFORM_VECTORS + 1]; // One extra for indices out of range, c[VERTEX_UNIFORM_VECTORS] = {0, 0, 0, 0}
byte* u[MAX_UNIFORM_BUFFER_BINDINGS]; byte* u[MAX_UNIFORM_BUFFER_BINDINGS];
byte* t[MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS];
unsigned int reg[MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS]; // Offset used when reading from registers, in components
unsigned int row[MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS]; // Number of rows to read
unsigned int col[MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS]; // Number of columns to read
unsigned int str[MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS]; // Number of components between each varying in output buffer
int4 i[16]; int4 i[16];
bool b[16]; bool b[16];
}; };
...@@ -222,6 +227,9 @@ namespace sw ...@@ -222,6 +227,9 @@ namespace sw
Surface *depthBuffer; Surface *depthBuffer;
Surface *stencilBuffer; Surface *stencilBuffer;
Resource *texture[TOTAL_IMAGE_UNITS]; Resource *texture[TOTAL_IMAGE_UNITS];
Resource* pUniformBuffers[MAX_UNIFORM_BUFFER_BINDINGS];
Resource* vUniformBuffers[MAX_UNIFORM_BUFFER_BINDINGS];
Resource* transformFeedbackBuffers[MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS];
int vsDirtyConstF; int vsDirtyConstF;
int vsDirtyConstI; int vsDirtyConstI;
......
...@@ -63,11 +63,6 @@ namespace sw ...@@ -63,11 +63,6 @@ namespace sw
VertexProcessor::TransformFeedbackInfo::TransformFeedbackInfo() VertexProcessor::TransformFeedbackInfo::TransformFeedbackInfo()
{ {
clear();
}
void VertexProcessor::TransformFeedbackInfo::clear()
{
buffer = nullptr; buffer = nullptr;
offset = 0; offset = 0;
reg = 0; reg = 0;
...@@ -76,6 +71,12 @@ namespace sw ...@@ -76,6 +71,12 @@ namespace sw
stride = 0; stride = 0;
} }
VertexProcessor::UniformBufferInfo::UniformBufferInfo()
{
buffer = nullptr;
offset = 0;
}
VertexProcessor::VertexProcessor(Context *context) : context(context) VertexProcessor::VertexProcessor(Context *context) : context(context)
{ {
for(int i = 0; i < 12; i++) for(int i = 0; i < 12; i++)
...@@ -116,11 +117,6 @@ namespace sw ...@@ -116,11 +117,6 @@ namespace sw
routineCache = 0; routineCache = 0;
setRoutineCacheSize(1024); setRoutineCacheSize(1024);
for(int i = 0; i < MAX_UNIFORM_BUFFER_BINDINGS; i++)
{
uniformBuffer[i] = nullptr;
}
} }
VertexProcessor::~VertexProcessor() VertexProcessor::~VertexProcessor()
...@@ -179,27 +175,16 @@ namespace sw ...@@ -179,27 +175,16 @@ namespace sw
void VertexProcessor::setUniformBuffer(int index, sw::Resource* buffer, int offset) void VertexProcessor::setUniformBuffer(int index, sw::Resource* buffer, int offset)
{ {
uniformBuffer[index] = buffer; uniformBufferInfo[index].buffer = buffer;
uniformBufferOffset[index] = offset; uniformBufferInfo[index].offset = offset;
} }
void VertexProcessor::lockUniformBuffers(byte** u) void VertexProcessor::lockUniformBuffers(byte** u, sw::Resource* uniformBuffers[])
{ {
for(int i = 0; i < MAX_UNIFORM_BUFFER_BINDINGS; ++i) for(int i = 0; i < MAX_UNIFORM_BUFFER_BINDINGS; ++i)
{ {
u[i] = uniformBuffer[i] ? static_cast<byte*>(uniformBuffer[i]->lock(PUBLIC, PRIVATE)) + uniformBufferOffset[i] : nullptr; u[i] = uniformBufferInfo[i].buffer ? static_cast<byte*>(uniformBufferInfo[i].buffer->lock(PUBLIC, PRIVATE)) + uniformBufferInfo[i].offset : nullptr;
} uniformBuffers[i] = uniformBufferInfo[i].buffer;
}
void VertexProcessor::unlockUniformBuffers()
{
for(int i = 0; i < MAX_UNIFORM_BUFFER_BINDINGS; ++i)
{
if(uniformBuffer[i])
{
uniformBuffer[i]->unlock();
uniformBuffer[i] = nullptr;
}
} }
} }
...@@ -213,11 +198,12 @@ namespace sw ...@@ -213,11 +198,12 @@ namespace sw
transformFeedbackInfo[index].stride = stride; transformFeedbackInfo[index].stride = stride;
} }
void VertexProcessor::lockTransformFeedbackBuffers(byte** t, unsigned int* v, unsigned int* r, unsigned int* c, unsigned int* s) void VertexProcessor::lockTransformFeedbackBuffers(byte** t, unsigned int* v, unsigned int* r, unsigned int* c, unsigned int* s, sw::Resource* transformFeedbackBuffers[])
{ {
for(int i = 0; i < MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS; ++i) for(int i = 0; i < MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS; ++i)
{ {
t[i] = transformFeedbackInfo[i].buffer ? static_cast<byte*>(transformFeedbackInfo[i].buffer->lock(PUBLIC, PRIVATE)) + transformFeedbackInfo[i].offset : nullptr; t[i] = transformFeedbackInfo[i].buffer ? static_cast<byte*>(transformFeedbackInfo[i].buffer->lock(PUBLIC, PRIVATE)) + transformFeedbackInfo[i].offset : nullptr;
transformFeedbackBuffers[i] = transformFeedbackInfo[i].buffer;
v[i] = transformFeedbackInfo[i].reg; v[i] = transformFeedbackInfo[i].reg;
r[i] = transformFeedbackInfo[i].row; r[i] = transformFeedbackInfo[i].row;
c[i] = transformFeedbackInfo[i].col; c[i] = transformFeedbackInfo[i].col;
...@@ -225,18 +211,6 @@ namespace sw ...@@ -225,18 +211,6 @@ namespace sw
} }
} }
void VertexProcessor::unlockTransformFeedbackBuffers()
{
for(int i = 0; i < MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS; ++i)
{
if(transformFeedbackInfo[i].buffer)
{
transformFeedbackInfo[i].buffer->unlock();
}
transformFeedbackInfo[i].clear();
}
}
void VertexProcessor::setModelMatrix(const Matrix &M, int i) void VertexProcessor::setModelMatrix(const Matrix &M, int i)
{ {
if(i < 12) if(i < 12)
......
...@@ -188,12 +188,10 @@ namespace sw ...@@ -188,12 +188,10 @@ namespace sw
virtual void setBooleanConstant(unsigned int index, int boolean); virtual void setBooleanConstant(unsigned int index, int boolean);
virtual void setUniformBuffer(int index, sw::Resource* uniformBuffer, int offset); virtual void setUniformBuffer(int index, sw::Resource* uniformBuffer, int offset);
virtual void lockUniformBuffers(byte** u); virtual void lockUniformBuffers(byte** u, sw::Resource* uniformBuffers[]);
virtual void unlockUniformBuffers();
virtual void setTransformFeedbackBuffer(int index, sw::Resource* transformFeedbackBuffer, int offset, unsigned int reg, unsigned int row, unsigned int col, size_t stride); virtual void setTransformFeedbackBuffer(int index, sw::Resource* transformFeedbackBuffer, int offset, unsigned int reg, unsigned int row, unsigned int col, size_t stride);
virtual void lockTransformFeedbackBuffers(byte** t, unsigned int* v, unsigned int* r, unsigned int* c, unsigned int* s); virtual void lockTransformFeedbackBuffers(byte** t, unsigned int* v, unsigned int* r, unsigned int* c, unsigned int* s, sw::Resource* transformFeedbackBuffers[]);
virtual void unlockTransformFeedbackBuffers();
// Transformations // Transformations
virtual void setModelMatrix(const Matrix &M, int i = 0); virtual void setModelMatrix(const Matrix &M, int i = 0);
...@@ -282,18 +280,23 @@ namespace sw ...@@ -282,18 +280,23 @@ namespace sw
float4 c[VERTEX_UNIFORM_VECTORS + 1]; // One extra for indices out of range, c[VERTEX_UNIFORM_VECTORS] = {0, 0, 0, 0} float4 c[VERTEX_UNIFORM_VECTORS + 1]; // One extra for indices out of range, c[VERTEX_UNIFORM_VECTORS] = {0, 0, 0, 0}
int4 i[16]; int4 i[16];
bool b[16]; bool b[16];
Resource* uniformBuffer[MAX_UNIFORM_BUFFER_BINDINGS];
int uniformBufferOffset[MAX_UNIFORM_BUFFER_BINDINGS];
PointSprite point; PointSprite point;
FixedFunction ff; FixedFunction ff;
private: private:
void updateTransform(); struct UniformBufferInfo
{
UniformBufferInfo();
Resource* buffer;
int offset;
};
UniformBufferInfo uniformBufferInfo[MAX_UNIFORM_BUFFER_BINDINGS];
struct TransformFeedbackInfo struct TransformFeedbackInfo
{ {
TransformFeedbackInfo(); TransformFeedbackInfo();
void clear();
Resource* buffer; Resource* buffer;
int offset; int offset;
...@@ -304,6 +307,7 @@ namespace sw ...@@ -304,6 +307,7 @@ namespace sw
}; };
TransformFeedbackInfo transformFeedbackInfo[MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS]; TransformFeedbackInfo transformFeedbackInfo[MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS];
void updateTransform();
void setTransform(const Matrix &M, int i); void setTransform(const Matrix &M, int i);
void setCameraTransform(const Matrix &M, int i); void setCameraTransform(const Matrix &M, int i);
void setNormalTransform(const Matrix &M, int i); void setNormalTransform(const Matrix &M, int i);
......
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