Skip to content
/ spvm Public

Tiny C++ SPIR-V virtual machine (interpreter), can be used for shader debugging. Spvm-ShaderToy simulated the runtime environment of shadertoy, and execute shader code using SPVM.

License

Notifications You must be signed in to change notification settings

keith2018/spvm

Repository files navigation

SPVM

Tiny C++ SPIR-V virtual machine (interpreter), you can use it to debug shaders: first compile your shader code(GLSL/HLSL) to SPIR-V binary file (using tools such as glslangValidator), then decode and execute entry point function main with SPVM, and check the output.

License CMake Linux CMake MacOS CMake Windows

Specifications that the project follows is:

Limits

TODO

  • 64-bit float/integer support
  • Performance optimizations
    • SIMD
    • JIT/AOT

The project is still working in progress ...

Spvm-ShaderToy

Spvm-ShaderToy simulated the runtime environment of shadertoy, and execute shader code using SPVM (may very slow 😀).

Gallery

Example

GLSL fragment shader (see example/shaders/simple.frag)

#version 450

layout (location = 0) in vec3 inColor;
layout (location = 0) out vec4 outFragColor;

void main()
{
    outFragColor = vec4(inColor.yxz, 1.0f);
}

run with spvm (see example/main.cpp)

#define HEAP_SIZE 128 * 1024
const char *SPV_PATH = "shaders/simple.frag.spv";

SPVM::SpvmModule module;
SPVM::Runtime runtime;

// decode spir-v file
bool success = SPVM::Decoder::decodeFile(SPV_PATH, &module);
if (!success) {
  std::cout << "error decode spir-v file";
  return -1;
}

// init runtime
success = runtime.initWithModule(&module, HEAP_SIZE);
if (!success) {
  std::cout << "error init module";
  return -1;
}

// get uniform locations
SPVM::SpvmWord inColorLoc = runtime.getLocationByName("inColor");
SPVM::SpvmWord outFragColorLoc = runtime.getLocationByName("outFragColor");

// write input
float inColor[3]{0.2f, 0.3f, 0.4f};
runtime.writeInput(inColor, inColorLoc);

// execute shader entry function 'main'
success = runtime.execEntryPoint();
if (!success) {
  std::cout << "error exec entrypoint function";
  return -1;
}

// read output
float outFragColor[4];
runtime.readOutput(outFragColor, outFragColorLoc);

std::cout << "outFragColor[0]: " << outFragColor[0] << std::endl;
std::cout << "outFragColor[1]: " << outFragColor[1] << std::endl;
std::cout << "outFragColor[2]: " << outFragColor[2] << std::endl;
std::cout << "outFragColor[3]: " << outFragColor[3] << std::endl;

Clone

git clone --recursive https://github.com/keith2018/spvm
cd spvm

Build

mkdir build
cmake -B ./build -DCMAKE_BUILD_TYPE=Release
cmake --build ./build --config Release

Test

cd build
ctest

License

This code is licensed under the MIT License (see LICENSE).

About

Tiny C++ SPIR-V virtual machine (interpreter), can be used for shader debugging. Spvm-ShaderToy simulated the runtime environment of shadertoy, and execute shader code using SPVM.

Topics

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published