Files
2025-09-28 07:26:30 +01:00

113 lines
4.2 KiB
Python

import renderdoc as rd
import struct
import rdtest
class Groupshared(rdtest.TestCase):
internal = True
demos_test_name = None
def check_compute_thread_result(self, test, action, x, y, z, expected):
try:
workgroup = (0, 0, 0)
trace = self.controller.DebugThread(workgroup, (x, y, z))
_, variables = self.process_trace(trace)
if trace.debugger is None:
raise rdtest.TestFailureException(f"Test {test} at {action.eventId} got no debug result at {x},{y},{z}")
# Find the source variable 'outval' at the highest instruction index
name = 'outval'
debugged = None
countInst = len(trace.instInfo)
for inst in range(countInst):
sourceVars = trace.instInfo[countInst-1-inst].sourceVars
try:
dataVars = [v for v in sourceVars if v.name == name]
if len(dataVars) == 0:
continue
debugged = self.evaluate_source_var(dataVars[0], variables)
except KeyError as ex:
continue
except rdtest.TestFailureException as ex:
continue
break
if debugged is None:
raise rdtest.TestFailureException(f"Couldn't find source variable {name} at {x},{y},{z}")
debuggedValue = list(debugged.value.f32v[0:4])
if not rdtest.value_compare(expected, debuggedValue, eps=5.0E-06):
raise rdtest.TestFailureException(f"EID:{action.eventId} TID:{x},{y},{z} debugged thread value {debuggedValue} does not match output {expected}")
except rdtest.TestFailureException as ex:
rdtest.log.error(f"Test {test} failed {ex}")
return False
except Exception as ex:
rdtest.log.error(f"Test {test} exception {ex}")
return False
finally:
self.controller.FreeTrace(trace)
return True
def check_compute_tests(self, action):
overallFailed = False
tests = [a for a in action.children if a.flags & rd.ActionFlags.Dispatch]
for test, action in enumerate(tests):
failed = False
self.controller.SetFrameEvent(action.eventId, False)
pipe = self.controller.GetPipelineState()
csrefl = pipe.GetShaderReflection(rd.ShaderStage.Compute)
dim = csrefl.dispatchThreadsDimension
rw = pipe.GetReadWriteResources(rd.ShaderStage.Compute)
if len(rw) != 2:
rdtest.log.error(f"Unexpected number of RW resources {len(rw)}")
return False
outBuf = rw[1].descriptor.resource
# each test writes up to one vec4 per thread * up to 64 threads
maxThreads = 64
dataPerThread = 4 * 4
dataPerTest = dataPerThread * maxThreads
bufdata = self.controller.GetBufferData(outBuf, 0, dataPerTest)
for x in range(dim[0]):
y = 0
z = 0
expected = struct.unpack_from("4f", bufdata, 16*x)
# Test 2 is a special case with hard coded results
if test == 2:
expected = [x, 1.25, 1.25, 1.25]
if not self.check_compute_thread_result(test, action, x, y, z, expected):
failed = True
overallFailed |= failed
if not failed:
rdtest.log.success(f"Tests at EID {action.eventId} successful")
else:
rdtest.log.error(f"Tests at EID {action.eventId} failed")
return overallFailed
def check_compute_section_tests(self, sectionAction):
sectionName = sectionAction.customName
rdtest.log.begin_section(sectionName)
failed = self.check_compute_tests(sectionAction)
rdtest.log.end_section(sectionName)
if failed:
raise rdtest.TestFailureException("Some tests were not as expected")
def check_capture(self):
action = self.find_action("Compute Tests")
self.check_compute_section_tests(action)
self.check_renderdoc_log_asserts()
rdtest.log.success("All tests matched")