Why are instruction in my HLSL Compute Shader being skipped

1

Here is a short Compute Shader I wrote :

struct CSEdgeVertexDetection_Part_02_Type
{
    float3 position;
    bool isEdgeVertex;
};

ByteAddressBuffer byteBuffer : register(t0);

Texture2D<float4> prevBackBuffer : register(t1);

RWStructuredBuffer<CSEdgeVertexDetection_Part_02_Type> vertexData : register(u1);



[numthreads(64, 1, 1)]
void main(uint3 groupId : SV_GroupID,
             uint groupIndex : SV_GroupIndex)
{
    uint index;
    float4 position;
    float4 inputPosition;

    index = (groupId.x * 64) + groupIndex;
    inputPosition = float4(vertexData[index].position, 1.0f);

    // Multiply Vertex modelSpace position with worldSpace matrix
    position.x = mul(inputPosition, asfloat(byteBuffer.Load4(0)));
    position.y = mul(inputPosition, asfloat(byteBuffer.Load4(16)));
    position.z = mul(inputPosition, asfloat(byteBuffer.Load4(32)));
    position.w = mul(inputPosition, asfloat(byteBuffer.Load4(48)));

    // Multiply Vertex worldSpace position with viewSpace matrix
    position.x = mul(inputPosition, asfloat(byteBuffer.Load4(64)));
    position.y = mul(inputPosition, asfloat(byteBuffer.Load4(80)));
    position.z = mul(inputPosition, asfloat(byteBuffer.Load4(96)));
    position.w = mul(inputPosition, asfloat(byteBuffer.Load4(112)));

    // Multiply Vertex viewSpace position with projectionSpace matrix
    position.x = mul(inputPosition, asfloat(byteBuffer.Load4(128)));
    position.y = mul(inputPosition, asfloat(byteBuffer.Load4(144)));
    position.z = mul(inputPosition, asfloat(byteBuffer.Load4(160)));
    position.w = mul(inputPosition, asfloat(byteBuffer.Load4(176)));

    // We will use inputPosition as destinations from now on since we don't need it anymore
    inputPosition.x = position.x / position.w / 2.0f + 0.5f;
    inputPosition.y = -position.y / position.w / 2.0f + 0.5f;

    inputPosition.x = inputPosition.x * 800.0f;
    inputPosition.y = inputPosition.y * 600.0f;

    inputPosition.x = round(inputPosition.x);
    inputPosition.y = round(inputPosition.y);

    inputPosition.y = 600.0f - inputPosition.y - 1.0f;


    //inputPosition.z = asfloat((prevBackBuffer.Load(int3(asint(inputPosition.x), asint(inputPosition.y), 0)) & 0x000000ff));
    inputPosition.z = prevBackBuffer.Load(int3(asint(inputPosition.x), asin(inputPosition.y), 0)).x;

    vertexData[index].isEdgeVertex = step(inputPosition.z, 1.0f);
}

I'm trying to read vertex data from a UAV, apply world, view, and perspective transformations on it. And then based on it's screen position read a color from the back buffer in order to do stuff with it.

For some reason all 4 lines of instructions for both the

// Multiply Vertex modelSpace position with worldSpace matrix

and the

// Multiply Vertex worldSpace position with viewSpace matrix

are being skipped and do not appear in the assembly at all

and furthermore only 3 lines from

// Multiply Vertex viewSpace position with projectionSpace matrix

are present in the the assembly and they don't even execute in order. Like the shader goes on to do later on stuff that require the position to be calculated before it's done.

Why is any of this happening. I have absolutely no leads

debugging
graphics
directx
hlsl
compute-shader
asked on Stack Overflow Aug 1, 2019 by StRaToX

1 Answer

1

You basically write the variable inputPosition.x, and then you overwrite the value after a few lines, without ever reading that variable back. As such, the compiler assumes that writing the value is a waste of time, and skips the instruction. This is the reason why the first and second blocks of instructions are stripped.

In the third block, you write all 4 components of inputPosition but you never use inputPositon.z, so there's no need of that and the instruction is stripped.

answered on Stack Overflow Aug 2, 2019 by kefren • edited Aug 2, 2019 by kefren

User contributions licensed under CC BY-SA 3.0