Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Reflection compiler option #5507

Merged
merged 12 commits into from
Nov 11, 2024
Binary file modified docs/command-line-slangc-reference.md
Binary file not shown.
5 changes: 5 additions & 0 deletions include/slang-deprecated.h
Original file line number Diff line number Diff line change
Expand Up @@ -853,6 +853,11 @@ extern "C"

// Shader Reflection

SLANG_API SlangResult spReflection_ToJson(
SlangReflection* reflection,
SlangCompileRequest* request,
ISlangBlob** outBlob);

SLANG_API unsigned spReflection_GetParameterCount(SlangReflection* reflection);
SLANG_API SlangReflectionParameter* spReflection_GetParameterByIndex(
SlangReflection* reflection,
Expand Down
2 changes: 2 additions & 0 deletions include/slang.h
Original file line number Diff line number Diff line change
Expand Up @@ -1003,6 +1003,8 @@ typedef uint32_t SlangSizeT;
// Add this new option to the end of the list to avoid breaking ABI as much as possible.
// Setting of EmitSpirvDirectly or EmitSpirvViaGLSL will turn into this option internally.
EmitSpirvMethod, // enum SlangEmitSpirvMethod

EmitReflectionJSON, // bool
CountOf,
};

Expand Down
85 changes: 85 additions & 0 deletions source/compiler-core/slang-pretty-writer.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
#include "slang-pretty-writer.h"

#include "../core/slang-string-escape-util.h"

namespace Slang
{

void PrettyWriter::writeRaw(char const* begin, char const* end)
{
SLANG_ASSERT(end >= begin);
writeRaw(UnownedStringSlice(begin, end));
}

void PrettyWriter::adjust()
{
// Only indent if at start of a line
if (m_startOfLine)
{
// Output current indentation
m_builder.appendRepeatedChar(' ', m_indent * 4);
m_startOfLine = false;
}
}

void PrettyWriter::dedent()
{
SLANG_ASSERT(m_indent > 0);
m_indent--;
}

void PrettyWriter::write(const UnownedStringSlice& slice)
{
const auto end = slice.end();
auto start = slice.begin();

while (start < end)
{
const char* cur = start;

// Search for \n if there is one
while (cur < end && *cur != '\n')
cur++;

// If there were some chars, adjust and write
if (cur > start)
{
adjust();
writeRaw(UnownedStringSlice(start, cur));
}

if (cur < end && *cur == '\n')
{
writeRawChar('\n');
// Skip the CR
cur++;
// Mark we are at the start of a line
m_startOfLine = true;
}

start = cur;
}
}

void PrettyWriter::writeEscapedString(const UnownedStringSlice& slice)
{
adjust();
auto handler = StringEscapeUtil::getHandler(StringEscapeUtil::Style::Cpp);
StringEscapeUtil::appendQuoted(handler, slice, m_builder);
}

void PrettyWriter::maybeComma()
{
if (auto state = m_commaState)
{
if (!state->needComma)
{
state->needComma = true;
return;
}
}

write(toSlice(",\n"));
}

} // namespace Slang
122 changes: 122 additions & 0 deletions source/compiler-core/slang-pretty-writer.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,122 @@
#ifndef SLANG_CORE_PRETTY_WRITER_H
#define SLANG_CORE_PRETTY_WRITER_H


#include "../core/slang-char-util.h"
#include "../core/slang-string-util.h"
#include "../core/slang-string.h"

namespace Slang
{

struct PrettyWriter
{
typedef PrettyWriter ThisType;

friend struct CommaTrackerRAII;

struct CommaState
{
bool needComma = false;
};

void writeRaw(const UnownedStringSlice& slice) { m_builder.append(slice); }
void writeRaw(char const* begin, char const* end);
void writeRaw(char const* begin) { writeRaw(UnownedStringSlice(begin)); }

void writeRawChar(int c) { m_builder.appendChar(char(c)); }

void writeHexChar(int c) { writeRawChar(CharUtil::getHexChar(Index(c))); }

/// Adjusts indentation if at start of a line
void adjust();

/// Increase indentation
void indent() { m_indent++; }
/// Decreate indentation
void dedent();

/// Write taking into account any CR that might be in a slice
void write(const UnownedStringSlice& slice);
void write(char const* text) { write(UnownedStringSlice(text)); }
void write(char const* text, size_t length) { write(UnownedStringSlice(text, length)); }

/// Write the slice as an escaped string
void writeEscapedString(const UnownedStringSlice& slice);

/// Call before items in a comma-separated JSON list to emit the comma if/when needed
void maybeComma();

/// Get the builder the result is being constructed in
StringBuilder& getBuilder() { return m_builder; }

ThisType& operator<<(const UnownedStringSlice& slice)
{
write(slice);
return *this;
}
ThisType& operator<<(const char* text)
{
write(text);
return *this;
}
ThisType& operator<<(uint64_t val)
{
adjust();
m_builder << val;
return *this;
}
ThisType& operator<<(int64_t val)
{
adjust();
m_builder << val;
return *this;
}
ThisType& operator<<(int32_t val)
{
adjust();
m_builder << val;
return *this;
}
ThisType& operator<<(uint32_t val)
{
adjust();
m_builder << val;
return *this;
}
ThisType& operator<<(float val)
{
adjust();
// We want to use a specific format, so we use the StringUtil to specify format, and not
// just use <<
StringUtil::appendFormat(m_builder, "%f", val);
return *this;
}

bool m_startOfLine = true;
int m_indent = 0;
CommaState* m_commaState = nullptr;
StringBuilder m_builder;
};

/// Type for tracking whether a comma is needed in a comma-separated JSON list
struct CommaTrackerRAII
{
CommaTrackerRAII(PrettyWriter& writer)
: m_writer(&writer), m_previousState(writer.m_commaState)
{
writer.m_commaState = &m_state;
}

~CommaTrackerRAII() { m_writer->m_commaState = m_previousState; }

private:
PrettyWriter::CommaState m_state;
PrettyWriter* m_writer;
PrettyWriter::CommaState* m_previousState;
};

} // namespace Slang


#endif
13 changes: 13 additions & 0 deletions source/slang/slang-options.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -524,8 +524,13 @@ void initCommandOptions(CommandOptions& options)
nullptr,
"Preserve all resource parameters in the output code, even if they are not used by the "
"shader."},
{OptionKind::EmitReflectionJSON,
"-reflection-json",
"reflection-json <path>",
"Emit reflection data in JSON format to a file."},
};


_addOptions(makeConstArrayView(generalOpts), options);

/* !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! Target !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! */
Expand Down Expand Up @@ -2663,6 +2668,14 @@ SlangResult OptionsParser::_parse(int argc, char const* const* argv)
addOutputPath(outputPath.value.getBuffer());
break;
}
case OptionKind::EmitReflectionJSON:
{
CommandLineArg outputPath;
SLANG_RETURN_ON_FAIL(m_reader.expectArg(outputPath));

linkage->m_optionSet.set(CompilerOptionName::EmitReflectionJSON, outputPath.value);
break;
}
case OptionKind::DepFile:
{
CommandLineArg dependencyPath;
Expand Down
Loading
Loading