yum-mirror/slang
Making it easier to work with shaders
git clone https://git.yummers.dev/yum-mirror/slang
43d0c2100
master
1#include "core/slang-basic.h" 2#include "gfx-test-util.h" 3#include "slang-rhi.h" 4#include "unit-test/slang-unit-test.h" 5 6#include <slang-rhi/shader-cursor.h> 7 8using namespace rhi ; 9 10namespace gfx_test 11{ 12struct Shader 13{ 14ComPtr < IShaderProgram > program ; 15 slang::ProgramLayout * reflection = nullptr ; 16ComputePipelineDesc pipelineDesc = {}; 17ComPtr < IComputePipeline > pipeline ; 18}; 19 20struct Buffer 21{ 22BufferDesc desc ; 23ComPtr < IBuffer > buffer ; 24ComPtr < ITextureView > view ; 25}; 26 27ComPtr < IBuffer > createFloatBuffer ( 28IDevice * device , 29bool unorderedAccess , 30size_t elementCount , 31float * initialData = nullptr ) 32{ 33BufferDesc desc = {}; 34desc .size = elementCount * sizeof (float ); 35desc .elementSize = sizeof (float ); 36desc .format = Format ::Undefined ; 37desc .memoryType = MemoryType ::DeviceLocal ; 38desc .usage = 39BufferUsage ::ShaderResource |BufferUsage ::CopyDestination |BufferUsage ::CopySource ; 40if (unorderedAccess ) 41desc .usage |=BufferUsage ::UnorderedAccess ; 42 43ComPtr < IBuffer > buffer ; 44GFX_CHECK_CALL_ABORT (device -> createBuffer (desc , (void * )initialData ,buffer .writeRef ())); 45return buffer ; 46} 47 48void barrierTestImpl (IDevice * device ,UnitTestContext * context ) 49{ 50Shader programA ; 51Shader programB ; 52GFX_CHECK_CALL_ABORT (loadComputeProgram ( 53device , 54programA .program , 55"buffer-barrier-test" , 56"computeA" , 57programA .reflection )); 58GFX_CHECK_CALL_ABORT (loadComputeProgram ( 59device , 60programB .program , 61"buffer-barrier-test" , 62"computeB" , 63programB .reflection )); 64programA .pipelineDesc .program = programA .program .get (); 65programB .pipelineDesc .program = programB .program .get (); 66GFX_CHECK_CALL_ABORT ( 67device -> createComputePipeline (programA .pipelineDesc ,programA .pipeline .writeRef ())); 68 69GFX_CHECK_CALL_ABORT ( 70device -> createComputePipeline (programB .pipelineDesc ,programB .pipeline .writeRef ())); 71 72float initialData []= {1.0f ,2.0f ,3.0f ,4.0f }; 73ComPtr < IBuffer > inputBuffer = createFloatBuffer (device , false,4 ,initialData ); 74ComPtr < IBuffer > intermediateBuffer = createFloatBuffer (device , true,4 ,nullptr ); 75ComPtr < IBuffer > outputBuffer = createFloatBuffer (device , true,4 ,nullptr ); 76 77// We have done all the set up work, now it is time to start recording a command buffer for 78// GPU execution. 79 { 80auto queue = device -> getQueue (QueueType ::Graphics ); 81auto commandEncoder = queue -> createCommandEncoder (); 82 83// Write inputBuffer data to intermediateBuffer 84 { 85auto passEncoder = commandEncoder -> beginComputePass (); 86auto rootObject = passEncoder -> bindPipeline (programA .pipeline ); 87 88ShaderCursor cursor (rootObject -> getEntryPoint (0 )); 89cursor ["inBuffer" ].setBinding (inputBuffer ); 90cursor ["outBuffer" ].setBinding (intermediateBuffer ); 91passEncoder -> dispatchCompute (1 ,1 ,1 ); 92passEncoder -> end (); 93 } 94 95// Resource transition is automatically handled. 96 97// Write intermediateBuffer data to outputBuffer 98 99 { 100auto passEncoder = commandEncoder -> beginComputePass (); 101auto rootObject = passEncoder -> bindPipeline (programB .pipeline ); 102ShaderCursor cursor (rootObject -> getEntryPoint (0 )); 103cursor ["inBuffer" ].setBinding (intermediateBuffer ); 104cursor ["outBuffer" ].setBinding (outputBuffer ); 105passEncoder -> dispatchCompute (1 ,1 ,1 ); 106passEncoder -> end (); 107 } 108 109 110queue -> submit (commandEncoder -> finish ()); 111queue -> waitOnHost (); 112 } 113 114 115compareComputeResult (device ,outputBuffer ,makeArray < float > (11.0f ,12.0f ,13.0f ,14.0f )); 116} 117 118void barrierTestAPI (UnitTestContext * context ,DeviceType deviceType ) 119{ 120Slang ::List < const char *> searchPaths = {"" ,"../../tools/gfx-unit-test" ,"tools/gfx-unit-test" }; 121auto device = createTestingDevice (context ,deviceType ,searchPaths ); 122 123if (!device ) 124 { 125SLANG_IGNORE_TEST 126 } 127 128barrierTestImpl (device .get (),context ); 129} 130 131SLANG_UNIT_TEST (bufferBarrierVulkan ) 132{ 133barrierTestAPI (unitTestContext ,DeviceType ::Vulkan ); 134} 135 136}// namespace gfx_test