aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid Neto <dneto@google.com>2016-10-20 15:08:31 -0400
committerDavid Neto <dneto@google.com>2016-10-21 09:57:22 -0400
commitfa933206ff7943ff8f58bfb1748d3a401231377c (patch)
tree6d933d97d1c843ee16ed949e6a23b8c931dd5b80
parente6b4795750f3ceb028fbfd860bd96b6aec859da1 (diff)
downloadshaderc-fa933206ff7943ff8f58bfb1748d3a401231377c.tar.gz
Add API support for compiling HLSL
Exposes the HLSL functionality in Glslang. Done in three layers: - libshaderc_util::Compiler: Add libshaderc_util::Compiler::SourceLanguage enum. Add libshaderc_util::Compiler::SetSourceLanguage method. The default language remains GLSL. libshaderc_util::Compiler passes the source language option into Glslang. - C API Add function to set source language on compiler options. - C++ API Add shaderc::CompileOptions::SetSourceLanguage
-rw-r--r--libshaderc/include/shaderc/shaderc.h10
-rw-r--r--libshaderc/include/shaderc/shaderc.hpp5
-rw-r--r--libshaderc/src/common_shaders_for_test.h3
-rw-r--r--libshaderc/src/shaderc.cc9
-rw-r--r--libshaderc/src/shaderc_cpp_test.cc28
-rw-r--r--libshaderc/src/shaderc_test.cc40
-rw-r--r--libshaderc_util/include/libshaderc_util/compiler.h17
-rw-r--r--libshaderc_util/src/compiler.cc26
-rw-r--r--libshaderc_util/src/compiler_test.cc27
9 files changed, 155 insertions, 10 deletions
diff --git a/libshaderc/include/shaderc/shaderc.h b/libshaderc/include/shaderc/shaderc.h
index 46d98b4..64d94ea 100644
--- a/libshaderc/include/shaderc/shaderc.h
+++ b/libshaderc/include/shaderc/shaderc.h
@@ -23,6 +23,12 @@ extern "C" {
#include <stddef.h>
#include <stdint.h>
+// Source language kind.
+typedef enum {
+ shaderc_source_language_glsl,
+ shaderc_source_language_hlsl,
+} shaderc_source_language;
+
typedef enum {
// Forced shader kinds. These shader kinds force the compiler to compile the
// source code as the specified kind of shader.
@@ -158,6 +164,10 @@ void shaderc_compile_options_add_macro_definition(
shaderc_compile_options_t options, const char* name, size_t name_length,
const char* value, size_t value_length);
+// Sets the source language. The default is GLSL.
+void shaderc_compile_options_set_source_language(
+ shaderc_compile_options_t options, shaderc_source_language lang);
+
// Sets the compiler mode to generate debug information in the output.
void shaderc_compile_options_set_generate_debug_info(
shaderc_compile_options_t options);
diff --git a/libshaderc/include/shaderc/shaderc.hpp b/libshaderc/include/shaderc/shaderc.hpp
index 4e5dfd7..1dc2631 100644
--- a/libshaderc/include/shaderc/shaderc.hpp
+++ b/libshaderc/include/shaderc/shaderc.hpp
@@ -221,6 +221,11 @@ class CompileOptions {
shaderc_compile_options_set_suppress_warnings(options_);
}
+ // Sets the source language. The default is GLSL.
+ void SetSourceLanguage(shaderc_source_language lang) {
+ shaderc_compile_options_set_source_language(options_, lang);
+ }
+
// Sets the target shader environment, affecting which warnings or errors will
// be issued.
// The version will be for distinguishing between different versions of the
diff --git a/libshaderc/src/common_shaders_for_test.h b/libshaderc/src/common_shaders_for_test.h
index d25c6bf..a0120a2 100644
--- a/libshaderc/src/common_shaders_for_test.h
+++ b/libshaderc/src/common_shaders_for_test.h
@@ -25,6 +25,9 @@ const char kMinimalShaderWithoutVersion[] = "void main(){}";
const char kMinimalShader[] =
"#version 140\n"
"void main(){}";
+const char kMinimalHlslShader[] =
+ "float4 EntryPoint(uint index : SV_VERTEXID) : SV_POSITION\n"
+ "{ return float4(1.0, 2.0, 3.0, 4.0); }";
const char kMinimalShaderWithMacro[] =
"#version 140\n"
"#define E main\n"
diff --git a/libshaderc/src/shaderc.cc b/libshaderc/src/shaderc.cc
index 8a2f46a..845320b 100644
--- a/libshaderc/src/shaderc.cc
+++ b/libshaderc/src/shaderc.cc
@@ -270,6 +270,15 @@ void shaderc_compile_options_add_macro_definition(
options->compiler.AddMacroDefinition(name, name_length, value, value_length);
}
+void shaderc_compile_options_set_source_language(
+ shaderc_compile_options_t options,
+ shaderc_source_language set_lang) {
+ auto lang = shaderc_util::Compiler::SourceLanguage::GLSL;
+ if (set_lang == shaderc_source_language_hlsl)
+ lang = shaderc_util::Compiler::SourceLanguage::HLSL;
+ options->compiler.SetSourceLanguage(lang);
+}
+
void shaderc_compile_options_set_generate_debug_info(
shaderc_compile_options_t options) {
options->compiler.SetGenerateDebugInfo();
diff --git a/libshaderc/src/shaderc_cpp_test.cc b/libshaderc/src/shaderc_cpp_test.cc
index 521f109..2762197 100644
--- a/libshaderc/src/shaderc_cpp_test.cc
+++ b/libshaderc/src/shaderc_cpp_test.cc
@@ -1015,4 +1015,32 @@ TEST_F(CppInterface, BeginAndEndOnPreprocessedResult) {
EXPECT_THAT(string_via_begin_end, Eq(forced_to_be_a_string));
}
+TEST_F(CppInterface, SourceLangGlslMinimalGlslVertexShaderSucceeds) {
+ options_.SetSourceLanguage(shaderc_source_language_glsl);
+ EXPECT_TRUE(CompilationSuccess(kVertexOnlyShader,
+ shaderc_glsl_vertex_shader,
+ options_));
+}
+
+TEST_F(CppInterface, SourceLangGlslMinimalHlslVertexShaderFails) {
+ options_.SetSourceLanguage(shaderc_source_language_glsl);
+ EXPECT_FALSE(CompilationSuccess(kMinimalHlslShader,
+ shaderc_glsl_vertex_shader,
+ options_));
+}
+
+TEST_F(CppInterface, SourceLangHlslMinimalGlslVertexShaderFails) {
+ options_.SetSourceLanguage(shaderc_source_language_hlsl);
+ EXPECT_FALSE(CompilationSuccess(kVertexOnlyShader,
+ shaderc_glsl_vertex_shader,
+ options_));
+}
+
+TEST_F(CppInterface, SourceLangHlslMinimalHlslVertexShaderSucceeds) {
+ options_.SetSourceLanguage(shaderc_source_language_hlsl);
+ EXPECT_TRUE(CompilationSuccess(kMinimalHlslShader,
+ shaderc_glsl_vertex_shader,
+ options_));
+}
+
} // anonymous namespace
diff --git a/libshaderc/src/shaderc_test.cc b/libshaderc/src/shaderc_test.cc
index c14b9c3..df8a5cb 100644
--- a/libshaderc/src/shaderc_test.cc
+++ b/libshaderc/src/shaderc_test.cc
@@ -1292,4 +1292,44 @@ TEST_F(CompileStringTest, NullSourceNameFailsCompilingToPreprocessedText) {
HasSubstr("Input file name string was null."));
}
+const char kGlslVertexShader[] =
+ "#version 140\nvoid main(){ gl_Position = vec4(0);}";
+
+const char kHlslVertexShader[] =
+ "float4 EntryPoint(uint index : SV_VERTEXID) : SV_POSITION\n"
+ "{ return float4(1.0, 2.0, 3.0, 4.0); }";
+
+TEST_F(CompileStringTest, LangGlslOnGlslVertexSucceeds) {
+ shaderc_compile_options_set_source_language(options_.get(),
+ shaderc_source_language_glsl);
+ EXPECT_TRUE(CompilationSuccess(kGlslVertexShader,
+ shaderc_glsl_vertex_shader,
+ options_.get()));
+}
+
+TEST_F(CompileStringTest, LangGlslOnHlslVertexFails) {
+ shaderc_compile_options_set_source_language(options_.get(),
+ shaderc_source_language_glsl);
+ EXPECT_FALSE(CompilationSuccess(kHlslVertexShader,
+ shaderc_glsl_vertex_shader,
+ options_.get()));
+}
+
+TEST_F(CompileStringTest, LangHlslOnGlslVertexFails) {
+ shaderc_compile_options_set_source_language(options_.get(),
+ shaderc_source_language_hlsl);
+ EXPECT_FALSE(CompilationSuccess(kGlslVertexShader,
+ shaderc_glsl_vertex_shader,
+ options_.get()));
+}
+
+TEST_F(CompileStringTest, LangHlslOnHlslVertexSucceeds) {
+ shaderc_compile_options_set_source_language(options_.get(),
+ shaderc_source_language_hlsl);
+ EXPECT_TRUE(CompilationSuccess(kHlslVertexShader,
+ shaderc_glsl_vertex_shader,
+ options_.get()));
+}
+
+
} // anonymous namespace
diff --git a/libshaderc_util/include/libshaderc_util/compiler.h b/libshaderc_util/include/libshaderc_util/compiler.h
index f774007..d396ca1 100644
--- a/libshaderc_util/include/libshaderc_util/compiler.h
+++ b/libshaderc_util/include/libshaderc_util/compiler.h
@@ -92,6 +92,12 @@ using MacroDictionary = std::unordered_map<std::string, std::string>;
// Holds all of the state required to compile source GLSL into SPIR-V.
class Compiler {
public:
+ // Source language
+ enum class SourceLanguage {
+ GLSL, // The default
+ HLSL,
+ };
+
// Target environment.
enum class TargetEnv {
Vulkan,
@@ -123,7 +129,8 @@ class Compiler {
suppress_warnings_(false),
generate_debug_info_(false),
enabled_opt_passes_(),
- target_env_(TargetEnv::Vulkan) {}
+ target_env_(TargetEnv::Vulkan),
+ source_language_(SourceLanguage::GLSL) {}
// Requests that the compiler place debug information into the object code,
// such as identifier names and line numbers.
@@ -149,6 +156,9 @@ class Compiler {
// Sets the target environment.
void SetTargetEnv(TargetEnv env);
+ // Sets the souce language.
+ void SetSourceLanguage(SourceLanguage lang);
+
// Forces (without any verification) the default version and profile for
// subsequent CompileShader() calls.
void SetForcedVersionProfile(int version, EProfile profile);
@@ -165,7 +175,7 @@ class Compiler {
//
// The initializer parameter must be a valid GlslangInitializer object.
// Acquire will be called on the initializer and the result will be
- // destoryed before the function ends.
+ // destroyed before the function ends.
//
// The output_type parameter determines what kind of output should be
// produced.
@@ -292,6 +302,9 @@ class Compiler {
// messages as well as the set of available builtins, as per the
// implementation of glslang.
TargetEnv target_env_;
+
+ // The source language. Defaults to GLSL.
+ SourceLanguage source_language_;
};
// Converts a string to a vector of uint32_t by copying the content of a given
diff --git a/libshaderc_util/src/compiler.cc b/libshaderc_util/src/compiler.cc
index b3c0a4f..52eb81f 100644
--- a/libshaderc_util/src/compiler.cc
+++ b/libshaderc_util/src/compiler.cc
@@ -65,19 +65,26 @@ std::pair<int, string_piece> DecodeLineDirective(string_piece directive) {
return std::make_pair(line, directive);
}
-// Gets the corresponding message rules for the given target environment.
-EShMessages GetMessageRules(shaderc_util::Compiler::TargetEnv env) {
+// Returns the Glslang message rules for the given target environment
+// and source language. We assume only valid combinations are used.
+EShMessages GetMessageRules(shaderc_util::Compiler::TargetEnv env,
+ shaderc_util::Compiler::SourceLanguage lang) {
using shaderc_util::Compiler;
+ EShMessages result = EShMsgCascadingErrors;
+ if (lang == Compiler::SourceLanguage::HLSL) {
+ result = static_cast<EShMessages>(result | EShMsgReadHlsl);
+ }
switch (env) {
case Compiler::TargetEnv::OpenGLCompat:
break;
case Compiler::TargetEnv::OpenGL:
- return static_cast<EShMessages>(EShMsgSpvRules | EShMsgCascadingErrors);
+ result = static_cast<EShMessages>(result | EShMsgSpvRules);
+ break;
case Compiler::TargetEnv::Vulkan:
- return static_cast<EShMessages>(EShMsgSpvRules | EShMsgVulkanRules |
- EShMsgCascadingErrors);
+ result = static_cast<EShMessages>(result | EShMsgSpvRules | EShMsgVulkanRules);
+ break;
}
- return EShMsgCascadingErrors;
+ return result;
}
} // anonymous namespace
@@ -177,7 +184,8 @@ std::tuple<bool, std::vector<uint32_t>, size_t> Compiler::Compile(
bool success = shader.parse(&shaderc_util::kDefaultTBuiltInResource,
default_version_, default_profile_,
force_version_profile_, kNotForwardCompatible,
- GetMessageRules(target_env_), includer);
+ GetMessageRules(target_env_, source_language_),
+ includer);
success &= PrintFilteredErrors(error_tag, error_stream, warnings_as_errors_,
suppress_warnings_, shader.getInfoLog(),
@@ -238,6 +246,8 @@ void Compiler::AddMacroDefinition(const char* macro, size_t macro_length,
void Compiler::SetTargetEnv(Compiler::TargetEnv env) { target_env_ = env; }
+void Compiler::SetSourceLanguage(Compiler::SourceLanguage lang) { source_language_ = lang; }
+
void Compiler::SetForcedVersionProfile(int version, EProfile profile) {
default_version_ = version;
default_profile_ = profile;
@@ -289,7 +299,7 @@ std::tuple<bool, std::string, std::string> Compiler::PreprocessShader(
// So combine the existing rules with the just-give-me-preprocessor-output
// flag.
const auto rules = static_cast<EShMessages>(EShMsgOnlyPreprocessor |
- GetMessageRules(target_env_));
+ GetMessageRules(target_env_, source_language_));
std::string preprocessed_shader;
const bool success = shader.preprocess(
diff --git a/libshaderc_util/src/compiler_test.cc b/libshaderc_util/src/compiler_test.cc
index 957f8f3..36931ff 100644
--- a/libshaderc_util/src/compiler_test.cc
+++ b/libshaderc_util/src/compiler_test.cc
@@ -77,6 +77,11 @@ const std::string kValuelessPredefinitionShader =
"#error\n"
"#endif";
+// An HLSL vertex shader.
+const char kHlslVertexShader[] =
+ R"(float4 EntryPoint(uint index : SV_VERTEXID) : SV_POSITION
+ { return float4(1.0, 2.0, 3.0, 4.0); })";
+
// A CountingIncluder that never returns valid content for a requested
// file inclusion.
class DummyCountingIncluder : public shaderc_util::CountingIncluder {
@@ -311,4 +316,26 @@ INSTANTIATE_TEST_CASE_P(
{"123456789", {0x34333231, 0x38373635, 0x00000039}},
}));
+TEST_F(CompilerTest, SetSourceLanguageToGLSLSucceeds) {
+ compiler_.SetSourceLanguage(Compiler::SourceLanguage::GLSL);
+ EXPECT_TRUE(SimpleCompilationSucceeds(kVulkanVertexShader, EShLangVertex));
+}
+
+TEST_F(CompilerTest, SetSourceLanguageToGLSLFailsOnHLSL) {
+ compiler_.SetSourceLanguage(Compiler::SourceLanguage::GLSL);
+ EXPECT_FALSE(SimpleCompilationSucceeds(kHlslVertexShader, EShLangVertex));
+}
+
+TEST_F(CompilerTest, SetSourceLanguageToHLSLSucceeds) {
+ compiler_.SetSourceLanguage(Compiler::SourceLanguage::HLSL);
+ EXPECT_TRUE(SimpleCompilationSucceeds(kHlslVertexShader, EShLangVertex))
+ << errors_;
+}
+
+TEST_F(CompilerTest, SetSourceLanguageToHLSLFailsOnGLSL) {
+ compiler_.SetSourceLanguage(Compiler::SourceLanguage::HLSL);
+ EXPECT_FALSE(SimpleCompilationSucceeds(kVulkanVertexShader, EShLangVertex));
+}
+
+
} // anonymous namespace