<feed xmlns='http://www.w3.org/2005/Atom'>
<title>slang.git/tools/render-test/slang-support.h, branch master</title>
<subtitle>Making it easier to work with shaders</subtitle>
<id>https://git.yummers.dev/slang.git/atom?h=master</id>
<link rel='self' href='https://git.yummers.dev/slang.git/atom?h=master'/>
<link rel='alternate' type='text/html' href='https://git.yummers.dev/slang.git/'/>
<updated>2025-07-31T21:32:02+00:00</updated>
<entry>
<title>Handle debug-layer messages in a separate channel (#7988)</title>
<updated>2025-07-31T21:32:02+00:00</updated>
<author>
<name>Jay Kwak</name>
<email>82421531+jkwak-work@users.noreply.github.com</email>
</author>
<published>2025-07-31T21:32:02+00:00</published>
<link rel='alternate' type='text/html' href='https://git.yummers.dev/slang.git/commit/?id=aefd1e3e0dbe4e77f8d7dbbfa04e15c2db615394'/>
<id>urn:sha1:aefd1e3e0dbe4e77f8d7dbbfa04e15c2db615394</id>
<content type='text'>
* Handle debug-layer messages in a separate channel

The Problem (Issue #7343)

The issue was that Vulkan Validation Layer error messages were being mixed into regular test output, causing
potential false positives or negatives. When using -enable-debug-layers true, validation messages would appear in
the same output stream as test results, potentially matching //CHECK: patterns incorrectly.

Example Problem:
- Test expects: //CHECK: 1
- Validation layer prints: VALIDATION ERROR: 1 invalid buffer binding
- Test incorrectly matches the "1" in the error message instead of the actual output

Slang Test Communication Architecture

Execution Modes

Slang has 3 different execution modes controlled by SpawnType:

enum class SpawnType {
    UseSharedLibrary,              // In-process execution
    UseTestServer,                 // Out-of-process via persistent server
    UseFullyIsolatedTestServer,    // Out-of-process via isolated server
    UseExe                         // Direct executable spawn
}

1. In-Process Mode (UseSharedLibrary)

┌─────────────────────────────────────────┐
│              slang-test                 │
│  ┌─────────────┐    ┌─────────────────┐ │
│  │render-test  │    │gfx-unit-test    │ │
│  │unit-test    │    │slangc library   │ │
│  └─────────────┘    └─────────────────┘ │
│           │                   │         │
│           └───► StdWriters ◄──┘         │
│                 (shared)                │
└─────────────────────────────────────────┘
- Communication: Direct function calls, shared memory
- Debug callbacks: Single callback instance in StdWriters
- Used when: Default mode for most tests

2. Out-of-Process Mode (UseTestServer)

┌──────────────────┐    JSON-RPC     ┌──────────────────┐
│   slang-test     │◄──over pipes────┤ test-server.exe  │
│                  │                 │                  │
│  ┌─────────────┐ │                 │ ┌─────────────┐  │
│  │StdWriters   │ │                 │ │render-test  │  │
│  │+debug       │ │                 │ │gfx-unit-test│  │
│  │callback     │ │                 │ │+debug       │  │
│  └─────────────┘ │                 │ │callback     │  │
└──────────────────┘                 │ └─────────────┘  │
                                     └──────────────────┘
- Communication: JSON-RPC over stdin/stdout pipes
- Debug callbacks: Separate instances in each process
- Used when: CI/CD, multi-threaded testing, crash isolation

3. Direct Executable Mode (UseExe)

┌──────────────────┐    pipes       ┌──────────────────┐
│   slang-test     │◄───────────────┤  slangc.exe      │
│                  │                │  other tools     │
└──────────────────┘                └──────────────────┘
- Communication: Standard process pipes (stdout/stderr)
- Debug callbacks: None (external executables)
- Used when: Testing external tools

Communication Mechanisms Deep Dive

JSON-RPC Protocol Over Pipes

The test-server.exe communicates with slang-test using JSON-RPC over stdin/stdout pipes:

// Parent process (slang-test) creates child with pipes
Process* testServerProcess = /* spawn test-server.exe */;

// JSONRPCConnection wraps the pipe communication
JSONRPCConnection connection;
connection.initWithStdStreams(); // Uses stdin/stdout pipes

// Send RPC call
TestServerProtocol::ExecutionResult result;
connection.sendCall("executeTool", &amp;args, &amp;result);

Key Point: The pipes carry structured JSON messages, not raw stdout/stderr. This is what enables clean separation
of different data channels.

Protocol Structure

Your changes extend the ExecutionResult protocol:

struct ExecutionResult {
    String stdOut;      // Regular program output
    String stdError;    // Error messages
    String debugLayer;  // NEW: Debug/validation messages
    int32_t result;
    int32_t returnCode;
};

Your Debug Layer Solution

The Challenge

Memory pointers cannot cross process boundaries. A debugCallback pointer in the parent process is meaningless in
the child process.

The Solution: String-Based Serialization

You solved this by using string capture and serialization:

1. Debug Callback Interface (slang-std-writers.h)

class IDebugCallback {
    virtual void handleMessage(
        DebugMessageType type,
        DebugMessageSource source,
        const char* message) = 0;
};

2. String-Capturing Implementation (slang-support.h)

class CoreDebugCallback : public Slang::IDebugCallback {
    StringBuilder m_buf;  // Captures messages as strings

    void handleMessage(DebugMessageType type, DebugMessageSource source, const char* message) {
        if (type == DebugMessageType::Error) {
            m_buf &lt;&lt; message &lt;&lt; '\n';  // Serialize to string
        }
    }

    String getString() { return m_buf.toString(); }  // Extract accumulated messages
};

3. Bridge Between RHI and Core (slang-support.h)

class CoreToRHIDebugBridge : public rhi::IDebugCallback {
    Slang::IDebugCallback* m_coreCallback;

    void handleMessage(rhi::DebugMessageType type, rhi::DebugMessageSource source, const char* message) {
        // Convert RHI types to core types and forward
        m_coreCallback-&gt;handleMessage(convertType(type), convertSource(source), message);
    }
};

Data Flow: Debug Messages End-to-End

In-Process Mode Flow

GPU Driver → RHI Debug Callback → Core Debug Callback → String Buffer → Test Output

Out-of-Process Mode Flow

Child Process:
GPU Driver → RHI Debug Callback → Core Debug Callback → String Buffer
                                                              ↓
Parent Process:                                    JSON-RPC Serialization
Test Output ← String Processing ← ExecutionResult.debugLayer ←┘

Step-by-Step Example

1. Test Execution Starts
// In test-server process
CoreDebugCallback debugCallback;
CoreToRHIDebugBridge bridge;
bridge.setCoreCallback(&amp;debugCallback);

// Set up graphics device with debug layers
deviceDesc.debugCallback = &amp;bridge;
2. Graphics API Call Triggers Validation Error
// Inside Vulkan driver (external code)
// Validation layer detects error and calls our callback
bridge.handleMessage(RHI_ERROR, RHI_LAYER, "Invalid buffer binding");
3. Message Capture
// In CoreDebugCallback::handleMessage
m_buf &lt;&lt; "Invalid buffer binding\n";  // Stored in string buffer
4. Test Completion &amp; Serialization
// Back in test-server
TestServerProtocol::ExecutionResult result;
result.debugLayer = debugCallback.getString();  // "Invalid buffer binding\n"
result.stdOut = "1";  // Regular test output

// Send via JSON-RPC
connection.sendResult(&amp;result);
5. Parent Process Receives &amp; Separates Output
// In slang-test process
String output = buildTestOutput(result);
// Results in clean separation:
// standard output = {
// 1
// }
// debug layer = {
// Invalid buffer binding
// }

Why This Solution Works

1. Process Isolation: Each process has its own callback objects, no shared pointers
2. String Serialization: Debug messages converted to strings that can cross process boundaries
3. Protocol Extension: Uses existing JSON-RPC infrastructure, just adds new field
4. Clean Separation: Debug messages never mix with stdout/stderr
5. Backward Compatibility: Existing tests unaffected, debug layer field optional

Key Benefits

- Eliminates False Positives: Debug messages can't interfere with //CHECK: patterns
- Better Debugging: Debug messages clearly separated and labeled
- Robust Architecture: Works across all execution modes
- Minimal Changes: Leverages existing communication infrastructure

This elegant solution transforms a fundamental cross-process communication challenge into a simple string
serialization problem, using the existing test server architecture to cleanly separate validation layer messages
from test results.

* Cover the missing slang-test execution path

* format code (#82)

Co-authored-by: slangbot &lt;186143334+slangbot@users.noreply.github.com&gt;

---------

Co-authored-by: slangbot &lt;ellieh+slangbot@nvidia.com&gt;
Co-authored-by: slangbot &lt;186143334+slangbot@users.noreply.github.com&gt;</content>
</entry>
<entry>
<title>Migrate render-test away from deprecated compile request API (#6514)</title>
<updated>2025-03-12T11:44:57+00:00</updated>
<author>
<name>Anders Leino</name>
<email>aleino@nvidia.com</email>
</author>
<published>2025-03-12T11:44:57+00:00</published>
<link rel='alternate' type='text/html' href='https://git.yummers.dev/slang.git/commit/?id=f4d5372d3354e62770b076b47892b5172223e98a'/>
<id>urn:sha1:f4d5372d3354e62770b076b47892b5172223e98a</id>
<content type='text'>
* Add a simple interface parameter test

Since there's no documentation, it's nice to have a simple test case in order to
experiment with this feature of the testing framework.

* Add shader entry point attributes to tests

* Fix specialization arguments for tests

- Add some missing arguments
- Rremove one extraneous argument.

* Stop using deprecated compile request in render-test

Use a session object instead of the deprecated compile request object.
This closes issue #4760.</content>
</entry>
<entry>
<title>Prepare for render test api migration (#6498)</title>
<updated>2025-02-28T14:12:03+00:00</updated>
<author>
<name>Anders Leino</name>
<email>aleino@nvidia.com</email>
</author>
<published>2025-02-28T14:12:03+00:00</published>
<link rel='alternate' type='text/html' href='https://git.yummers.dev/slang.git/commit/?id=e4b960024972420dfc96a758bfc35e8fcbf28273'/>
<id>urn:sha1:e4b960024972420dfc96a758bfc35e8fcbf28273</id>
<content type='text'>
* Remove tests/compute/dump-repro

The -load-repro option is no longer maintained.

This helps to address issue #4760.

* Rename ShaderCompilerUtil::Output::session to globalSession

* Remove the load-repro codepath

* Lifetime bugfix</content>
</entry>
<entry>
<title>Cleanups for render-api (#6360)</title>
<updated>2025-02-19T07:55:16+00:00</updated>
<author>
<name>Anders Leino</name>
<email>aleino@nvidia.com</email>
</author>
<published>2025-02-19T07:55:16+00:00</published>
<link rel='alternate' type='text/html' href='https://git.yummers.dev/slang.git/commit/?id=e9a63b2b3822bbc533130ead0ab8ee03b4a4250a'/>
<id>urn:sha1:e9a63b2b3822bbc533130ead0ab8ee03b4a4250a</id>
<content type='text'>
* Clean up unused code

* Clean up support interface

* Rename the compile output requests to mark them DEPRECATED

---------

Co-authored-by: Yong He &lt;yonghe@outlook.com&gt;</content>
</entry>
<entry>
<title>Update Slang-RHI and enable any debug layers up-front (#6226)</title>
<updated>2025-02-01T05:14:17+00:00</updated>
<author>
<name>Anders Leino</name>
<email>aleino@nvidia.com</email>
</author>
<published>2025-02-01T05:14:17+00:00</published>
<link rel='alternate' type='text/html' href='https://git.yummers.dev/slang.git/commit/?id=2949b786a7f04ad31c113b622039fb5b72bc8622'/>
<id>urn:sha1:2949b786a7f04ad31c113b622039fb5b72bc8622</id>
<content type='text'>
* Update Slang-RHI and enable any debug layers up-front

As [1] shows, creating a D3D12 device and then enabling debug layers causes future device
creation to fail.
That means enabling debug layers is a process-wide decision that should be done at
startup, and not just before creating an individual device.
Previously, Slang-RHI enabled debug layers as part of device creation.
The new Slang-RHI revision doesn't do that anymore, but instead allows the user to enable
debug layers earlier, with a separate API.
This change calls the mentioned API before creating any device.

This closes #6172.

* Compile fixes needed after updating slang-rhi

---------

Co-authored-by: Yong He &lt;yonghe@outlook.com&gt;</content>
</entry>
<entry>
<title>format</title>
<updated>2024-10-29T06:49:26+00:00</updated>
<author>
<name>Ellie Hermaszewska</name>
<email>ellieh@nvidia.com</email>
</author>
<published>2024-10-29T06:49:26+00:00</published>
<link rel='alternate' type='text/html' href='https://git.yummers.dev/slang.git/commit/?id=f65d756bff8d4c5cbc15bd0322a2ae8e6b896a21'/>
<id>urn:sha1:f65d756bff8d4c5cbc15bd0322a2ae8e6b896a21</id>
<content type='text'>
* format

* Minor test fixes

* enable checking cpp format in ci</content>
</entry>
<entry>
<title>refactor render test to use latest slang-rhi (#5119)</title>
<updated>2024-09-19T15:16:48+00:00</updated>
<author>
<name>Simon Kallweit</name>
<email>64953474+skallweitNV@users.noreply.github.com</email>
</author>
<published>2024-09-19T15:16:48+00:00</published>
<link rel='alternate' type='text/html' href='https://git.yummers.dev/slang.git/commit/?id=3861be7ce5bd3ffc1bc60f2c3f7f41647145d575'/>
<id>urn:sha1:3861be7ce5bd3ffc1bc60f2c3f7f41647145d575</id>
<content type='text'>
* refactor render test to use latest slang-rhi

* update slang-rhi

* update slang-rhi

* update slang-rhi

* update slang-rhi</content>
</entry>
<entry>
<title>Draft: integrate slang-rhi (#4970)</title>
<updated>2024-08-30T16:50:19+00:00</updated>
<author>
<name>Simon Kallweit</name>
<email>64953474+skallweitNV@users.noreply.github.com</email>
</author>
<published>2024-08-30T16:50:19+00:00</published>
<link rel='alternate' type='text/html' href='https://git.yummers.dev/slang.git/commit/?id=f428a058ea48535a323c32d206ebc7e551c3c3e9'/>
<id>urn:sha1:f428a058ea48535a323c32d206ebc7e551c3c3e9</id>
<content type='text'>
* add slang-rhi submodule

* refactor render-test to use slang-rhi and remove OpenGL support

* remove -vk -glsl tests

* remove gl test

* disable failing test

* allow recursive submodules in github actions

* update slang-rhi

* update slang-rhi

---------

Co-authored-by: Yong He &lt;yonghe@outlook.com&gt;</content>
</entry>
<entry>
<title>Move the file public header files to `include` dir (#4636)</title>
<updated>2024-07-17T17:53:19+00:00</updated>
<author>
<name>kaizhangNV</name>
<email>149626564+kaizhangNV@users.noreply.github.com</email>
</author>
<published>2024-07-17T17:53:19+00:00</published>
<link rel='alternate' type='text/html' href='https://git.yummers.dev/slang.git/commit/?id=2db15080085856ed9b5f20642dbb354aac59a888'/>
<id>urn:sha1:2db15080085856ed9b5f20642dbb354aac59a888</id>
<content type='text'>
* Move the file public header files to `include` dir

Close the issue (#4635).

Move the following headers files to a `include` dir
located at root dir of slang repo:

 slang-com-helper.h -&gt; include/slang-com-helper.h
 slang-com-ptr.h -&gt; include/slang-com-ptr.h
 slang-gfx.h -&gt; include/slang-gfx.h
 slang.h -&gt; include/slang.h

Change cmake/SlangTarget.cmake to add include path to
every target, and change the source file to use
"#include &lt;slang.h&gt;" to include the public headers.

The source code update is by the script like follow:

```
fileNames_slang=$(grep -r "\".*slang\.h\"" source/ -l)

for fileName in "${fileNames_slang[@]}"
do
    echo "$fileName"
    sed -i "s/\".*slang\.h\"/\"slang\.h\"/" $fileName
done
```

* Fix the test issues

* Fix cpu test issues by adding include seach path

* Update cmake to not add include path for every target

Also change "#include &lt;slang.h&gt;" to "include "slang.h" " to
make the coding style consistent with other slang code.

* Change public include to private include for unit-test and slang-glslang</content>
</entry>
<entry>
<title>Refactor compiler option representations. (#3598)</title>
<updated>2024-02-20T20:24:00+00:00</updated>
<author>
<name>Yong He</name>
<email>yonghe@outlook.com</email>
</author>
<published>2024-02-20T20:24:00+00:00</published>
<link rel='alternate' type='text/html' href='https://git.yummers.dev/slang.git/commit/?id=4d20fd329956ac89408b1628a8291fea01bc9a6d'/>
<id>urn:sha1:4d20fd329956ac89408b1628a8291fea01bc9a6d</id>
<content type='text'>
* Refactor compiler option representation.

* Fix binary compatibility.

* Add a test for specifying compiler options at link time.

* Fix binary compatibility.

* Fix binary compatibility.

* Fix backward compatibility on matrix layout.

* Fix.

* Fix.

* Fix.

* Fix gfx.

* Fix gfx.

* Fix dynamic dispatch.

* Polish.</content>
</entry>
</feed>
