From b72353ec3fe529237828cacbe710233d31eb4837 Mon Sep 17 00:00:00 2001 From: Yong He Date: Thu, 24 Sep 2020 14:30:12 -0700 Subject: Enable default cpp prelude. (#1560) * Enable default cpp prelude. * Print the "#include" line as a normal source if the file does not exist. * Bug fix * Fix. * Fix c++ prelude header. * Remove unnecessary fopen call. --- .gitignore | 1 + prelude/slang-cpp-prelude.h | 6 +- prelude/slang-cpp-scalar-intrinsics.h | 6 +- prelude/slang-cpp-types.h | 46 ++++++++- premake5.lua | 3 +- slang.h | 4 +- source/slang/run-generators.vcxproj | 30 +----- source/slang/run-generators.vcxproj.filters | 14 +-- source/slang/slang.cpp | 10 +- source/slang/slang.vcxproj | 1 + source/slang/slang.vcxproj.filters | 3 + tools/slang-embed/slang-embed.cpp | 152 ++++++++++++++++++---------- 12 files changed, 176 insertions(+), 100 deletions(-) diff --git a/.gitignore b/.gitignore index c25e68b15..f03caafb7 100644 --- a/.gitignore +++ b/.gitignore @@ -42,3 +42,4 @@ tests/**/*.slang-module /source/slang/hlsl.meta.slang.h /source/slang/core.meta.slang.h prelude/*.h.cpp +/source/slang/cpp.hint diff --git a/prelude/slang-cpp-prelude.h b/prelude/slang-cpp-prelude.h index b00f34d8f..23619d102 100644 --- a/prelude/slang-cpp-prelude.h +++ b/prelude/slang-cpp-prelude.h @@ -1,8 +1,6 @@ #ifndef SLANG_CPP_PRELUDE_H #define SLANG_CPP_PRELUDE_H -#include "../slang.h" - // Because the signiture of isnan, isfinite, and is isinf changed in C++, we use the macro // to use the version in the std namespace. // https://stackoverflow.com/questions/39130040/cmath-hides-isnan-in-math-h-in-c14-c11 @@ -42,7 +40,7 @@ #include "slang-cpp-scalar-intrinsics.h" // TODO(JS): Hack! Output C++ code from slang can copy uninitialized variables. -#if SLANG_VC +#if defined(_MSC_VER) # pragma warning(disable : 4700) #endif @@ -66,4 +64,4 @@ gfx_PipelineState_0* buildPipelineState_0(gfx_ShaderProgram_0* _0, gfx_Renderer_ void dispatchComputation_0(gfx_Renderer_0* _0, gfx_PipelineState_0* _1, gfx_PipelineLayout_0* _2, gfx_DescriptorSet_0* _3, uint32_t _4, uint32_t _5, uint32_t _6); gfx_BufferResource_0* unconvertBuffer_0(RWStructuredBuffer _0); -#endif \ No newline at end of file +#endif diff --git a/prelude/slang-cpp-scalar-intrinsics.h b/prelude/slang-cpp-scalar-intrinsics.h index ec3882cfb..7ee62dbc6 100644 --- a/prelude/slang-cpp-scalar-intrinsics.h +++ b/prelude/slang-cpp-scalar-intrinsics.h @@ -1,13 +1,15 @@ #ifndef SLANG_PRELUDE_SCALAR_INTRINSICS_H #define SLANG_PRELUDE_SCALAR_INTRINSICS_H -#include "../slang.h" - #if SLANG_PROCESSOR_X86_64 && SLANG_VC // If we have visual studio and 64 bit processor, we can assume we have popcnt, and can include x86 intrinsics # include #endif +#ifndef SLANG_FORCE_INLINE +# define SLANG_FORCE_INLINE inline +#endif + #ifdef SLANG_PRELUDE_NAMESPACE namespace SLANG_PRELUDE_NAMESPACE { #endif diff --git a/prelude/slang-cpp-types.h b/prelude/slang-cpp-types.h index 69e69f8df..b0a9c68f6 100644 --- a/prelude/slang-cpp-types.h +++ b/prelude/slang-cpp-types.h @@ -1,8 +1,6 @@ #ifndef SLANG_PRELUDE_CPP_TYPES_H #define SLANG_PRELUDE_CPP_TYPES_H - -#include "../slang.h" - +#include #ifndef SLANG_PRELUDE_ASSERT # ifdef _DEBUG # define SLANG_PRELUDE_ASSERT(VALUE) assert(VALUE) @@ -11,6 +9,10 @@ # endif #endif +#ifndef SLANG_FORCE_INLINE +# define SLANG_FORCE_INLINE inline +#endif + #ifdef SLANG_PRELUDE_NAMESPACE namespace SLANG_PRELUDE_NAMESPACE { #endif @@ -294,6 +296,42 @@ struct SamplerComparisonState ISamplerComparisonState* state; }; +#ifndef SLANG_RESOURCE_SHAPE +# define SLANG_RESOURCE_SHAPE +typedef unsigned int SlangResourceShape; +enum +{ + SLANG_RESOURCE_BASE_SHAPE_MASK = 0x0F, + + SLANG_RESOURCE_NONE = 0x00, + + SLANG_TEXTURE_1D = 0x01, + SLANG_TEXTURE_2D = 0x02, + SLANG_TEXTURE_3D = 0x03, + SLANG_TEXTURE_CUBE = 0x04, + SLANG_TEXTURE_BUFFER = 0x05, + + SLANG_STRUCTURED_BUFFER = 0x06, + SLANG_BYTE_ADDRESS_BUFFER = 0x07, + SLANG_RESOURCE_UNKNOWN = 0x08, + SLANG_ACCELERATION_STRUCTURE = 0x09, + + SLANG_RESOURCE_EXT_SHAPE_MASK = 0xF0, + + SLANG_TEXTURE_FEEDBACK_FLAG = 0x10, + SLANG_TEXTURE_ARRAY_FLAG = 0x40, + SLANG_TEXTURE_MULTISAMPLE_FLAG = 0x80, + + SLANG_TEXTURE_1D_ARRAY = SLANG_TEXTURE_1D | SLANG_TEXTURE_ARRAY_FLAG, + SLANG_TEXTURE_2D_ARRAY = SLANG_TEXTURE_2D | SLANG_TEXTURE_ARRAY_FLAG, + SLANG_TEXTURE_CUBE_ARRAY = SLANG_TEXTURE_CUBE | SLANG_TEXTURE_ARRAY_FLAG, + + SLANG_TEXTURE_2D_MULTISAMPLE = SLANG_TEXTURE_2D | SLANG_TEXTURE_MULTISAMPLE_FLAG, + SLANG_TEXTURE_2D_MULTISAMPLE_ARRAY = + SLANG_TEXTURE_2D | SLANG_TEXTURE_MULTISAMPLE_FLAG | SLANG_TEXTURE_ARRAY_FLAG, +}; +#endif + // struct TextureDimensions { @@ -393,7 +431,7 @@ struct TextureDimensions } } - SlangResourceShape shape; + uint32_t shape; uint32_t width, height, depth; uint32_t numberOfLevels; uint32_t arrayElementCount; ///< For array types, 0 otherwise diff --git a/premake5.lua b/premake5.lua index 1b350998b..3dcb5dd2e 100644 --- a/premake5.lua +++ b/premake5.lua @@ -901,7 +901,7 @@ generatorProject("run-generators", "source/slang/") end if executeBinary then - filter "files:prelude/*.h" + filter "files:prelude/*-prelude.h" buildmessage "slang-embed %{file.relpath}" buildcommands { '"%{cfg.targetdir}/slang-embed" %{file.relpath}' } buildoutputs { "%{file.abspath}.cpp" } @@ -957,6 +957,7 @@ standardProject "slang" files { "prelude/slang-cuda-prelude.h.cpp", "prelude/slang-hlsl-prelude.h.cpp", + "prelude/slang-cpp-prelude.h.cpp" } -- diff --git a/slang.h b/slang.h index 48af5ef36..60e7c43a7 100644 --- a/slang.h +++ b/slang.h @@ -1832,6 +1832,8 @@ extern "C" SLANG_SCALAR_TYPE_UINT16, }; +#ifndef SLANG_RESOURCE_SHAPE +# define SLANG_RESOURCE_SHAPE typedef unsigned int SlangResourceShape; enum { @@ -1863,7 +1865,7 @@ extern "C" SLANG_TEXTURE_2D_MULTISAMPLE = SLANG_TEXTURE_2D | SLANG_TEXTURE_MULTISAMPLE_FLAG, SLANG_TEXTURE_2D_MULTISAMPLE_ARRAY = SLANG_TEXTURE_2D | SLANG_TEXTURE_MULTISAMPLE_FLAG | SLANG_TEXTURE_ARRAY_FLAG, }; - +#endif typedef unsigned int SlangResourceAccess; enum { diff --git a/source/slang/run-generators.vcxproj b/source/slang/run-generators.vcxproj index 41f61f01d..82b993466 100644 --- a/source/slang/run-generators.vcxproj +++ b/source/slang/run-generators.vcxproj @@ -153,6 +153,10 @@ true + + + + @@ -170,32 +174,6 @@ ../../bin/windows-x86/release/slang-embed.exe ../../bin/windows-x64/release/slang-embed.exe - - Document - "../../bin/windows-x86/debug/slang-embed" %(Identity) - "../../bin/windows-x64/debug/slang-embed" %(Identity) - "../../bin/windows-x86/release/slang-embed" %(Identity) - "../../bin/windows-x64/release/slang-embed" %(Identity) - ../../prelude/slang-cpp-scalar-intrinsics.h.cpp - slang-embed %(Identity) - ../../bin/windows-x86/debug/slang-embed.exe - ../../bin/windows-x64/debug/slang-embed.exe - ../../bin/windows-x86/release/slang-embed.exe - ../../bin/windows-x64/release/slang-embed.exe - - - Document - "../../bin/windows-x86/debug/slang-embed" %(Identity) - "../../bin/windows-x64/debug/slang-embed" %(Identity) - "../../bin/windows-x86/release/slang-embed" %(Identity) - "../../bin/windows-x64/release/slang-embed" %(Identity) - ../../prelude/slang-cpp-types.h.cpp - slang-embed %(Identity) - ../../bin/windows-x86/debug/slang-embed.exe - ../../bin/windows-x64/debug/slang-embed.exe - ../../bin/windows-x86/release/slang-embed.exe - ../../bin/windows-x64/release/slang-embed.exe - Document "../../bin/windows-x86/debug/slang-embed" %(Identity) diff --git a/source/slang/run-generators.vcxproj.filters b/source/slang/run-generators.vcxproj.filters index 6a51d5ba7..e8ec8394a 100644 --- a/source/slang/run-generators.vcxproj.filters +++ b/source/slang/run-generators.vcxproj.filters @@ -8,6 +8,14 @@ {E9C7FDCE-D52A-8D73-7EB0-C5296AF258F6} + + + Header Files + + + Header Files + + Source Files @@ -17,12 +25,6 @@ Header Files - - Header Files - - - Header Files - Header Files diff --git a/source/slang/slang.cpp b/source/slang/slang.cpp index 1086338f4..572c9c3a3 100644 --- a/source/slang/slang.cpp +++ b/source/slang/slang.cpp @@ -41,8 +41,9 @@ #undef NOMINMAX #endif -extern char const* slang_cuda_prelude; -extern char const* slang_hlsl_prelude; +extern Slang::String get_slang_cuda_prelude(); +extern Slang::String get_slang_cpp_prelude(); +extern Slang::String get_slang_hlsl_prelude(); namespace Slang { @@ -189,8 +190,9 @@ void Session::init() } // Set up default prelude code for target languages that need a prelude - m_languagePreludes[Index(SourceLanguage::CUDA)] = slang_cuda_prelude; - m_languagePreludes[Index(SourceLanguage::HLSL)] = slang_hlsl_prelude; + m_languagePreludes[Index(SourceLanguage::CUDA)] = get_slang_cuda_prelude(); + m_languagePreludes[Index(SourceLanguage::CPP)] = get_slang_cpp_prelude(); + m_languagePreludes[Index(SourceLanguage::HLSL)] = get_slang_hlsl_prelude(); } ISlangUnknown* Session::getInterface(const Guid& guid) diff --git a/source/slang/slang.vcxproj b/source/slang/slang.vcxproj index a5d51e36b..d98a29118 100644 --- a/source/slang/slang.vcxproj +++ b/source/slang/slang.vcxproj @@ -298,6 +298,7 @@ + diff --git a/source/slang/slang.vcxproj.filters b/source/slang/slang.vcxproj.filters index fec82a8f5..b9f9d69c0 100644 --- a/source/slang/slang.vcxproj.filters +++ b/source/slang/slang.vcxproj.filters @@ -341,6 +341,9 @@ + + Header Files + Header Files diff --git a/tools/slang-embed/slang-embed.cpp b/tools/slang-embed/slang-embed.cpp index 5dee2a609..7e011c041 100644 --- a/tools/slang-embed/slang-embed.cpp +++ b/tools/slang-embed/slang-embed.cpp @@ -14,6 +14,11 @@ #include #include +#include "../../source/core/slang-list.h" +#include "../../source/core/slang-string.h" +#include "../../source/core/slang-string-util.h" +#include "../../source/core/slang-io.h" + // Utility to free pointers on scope exit struct ScopedMemory { @@ -77,13 +82,10 @@ struct App exit(1); } } - - void processInputFile() + size_t charCount = 0; + bool useNewStringLit = true; + void processInputFile(FILE* outputFile, Slang::String inputPath) { - // Note: Eventually we might support multiple input files in a - // single invocation of the tool, but for now we only have - // a single file to process. - // We open the input file in text mode because we are currently // embedding textual source files. If/when this utility gets // used for binary files another mode could be called for. @@ -92,13 +94,92 @@ struct App // could lead to a difference in the embedded bytes based on // the line ending convention of the host platform) // - FILE* inputFile = fopen(inputPath, "r"); - ScopedFile inputFileCleanup(inputFile); - if( !inputFile ) + Slang::StreamReader streamReader(inputPath); + while (!streamReader.IsEnd()) { - fprintf(stderr, "%s: error: failed to open '%s' for reading\n", appName, inputPath); - exit(1); + auto line = streamReader.ReadLine(); + Slang::String trimedLine = line.trimStart(); + if (trimedLine.startsWith("#include")) + { + auto fileName = + Slang::StringUtil::getAtInSplit(trimedLine.getUnownedSlice(), ' ', 1); + if (fileName[0] == '<') + goto normalProcess; + fileName = Slang::UnownedStringSlice(fileName.begin() + 1, fileName.end() - 1); + auto path = + Slang::Path::combine(Slang::Path::getParentDirectory(inputPath), fileName); + if (!Slang::File::exists(path)) + goto normalProcess; + processInputFile(outputFile, path.getUnownedSlice()); + continue; + } + normalProcess:; + if (!useNewStringLit && charCount + line.getLength() > 0x4000) + { + charCount = 0; + useNewStringLit = true; + fprintf(outputFile, ";\n"); + } + if (useNewStringLit) + { + fprintf(outputFile, "sb << \n\""); + useNewStringLit = false; + } + else + { + fprintf(outputFile, "\""); + } + charCount += line.getLength(); + for (auto c : line) + { + // Based on the byte that we are trying to emit, + // we may need to emit an escape sequence. + // + switch (c) + { + // The common C escape sequencs are handled directly. + // + case '"': + fprintf(outputFile, "\\\""); + break; + case '\n': + fprintf(outputFile, "\\n"); + break; + case '\t': + fprintf(outputFile, "\\t"); + break; + + default: + // For all other cases, we detect if the byte + // is in the printable ASCII range, and emit + // it directly if sco. + // + if (c >= 32 && c <= 126) + { + fputc(c, outputFile); + } + else + { + // Otherwise, we emit the byte as an octal + // escape sequence, being sure to emit a + // full three digits to avoid errorneous + // encoding if the following byte might + // represent a digit. + // + fprintf(outputFile, "\\%03o", c); + } + break; + } + } + fprintf(outputFile, "\\n\"\n"); } + } + + void processInputFile() + { + // Note: Eventually we might support multiple input files in a + // single invocation of the tool, but for now we only have + // a single file to process. // We derive an output path simply by appending `.cpp` to the input path. // @@ -160,7 +241,11 @@ struct App // task of outputting the generated source file is simple. // fprintf(outputFile, "// generated code; do not edit\n"); - fprintf(outputFile, "const char* %s =\n", variableName); + fprintf(outputFile, "#include \"../source/core/slang-basic.h\"\n"); + + fprintf(outputFile, "Slang::String get_%s()\n", variableName); + fprintf(outputFile, "{\n"); + fprintf(outputFile, "Slang::StringBuilder sb;\n"); // Note: For now we are embedding the file as a string // literal, with full knowledge that this strategy @@ -175,47 +260,10 @@ struct App // with large array literals, the practical limits // appear to be higher than they are for string literals. - fprintf(outputFile, "\""); - for( ;;) - { - int c = fgetc(inputFile); - if( c == EOF ) - break; + processInputFile(outputFile, Slang::UnownedStringSlice(inputPath)); - // Based on the byte that we are trying to emit, - // we may need to emit an escape sequence. - // - switch( c ) - { - // The common C escape sequencs are handled directly. - // - case '"': fprintf(outputFile, "\\\""); break; - case '\n': fprintf(outputFile, "\\n\"\n\""); break; - case '\t': fprintf(outputFile, "\\t"); break; - - default: - // For all other cases, we detect if the byte - // is in the printable ASCII range, and emit - // it directly if sco. - // - if( c >= 32 && c <= 126 ) - { - fputc(c, outputFile); - } - else - { - // Otherwise, we emit the byte as an octal - // escape sequence, being sure to emit a - // full three digits to avoid errorneous - // encoding if the following byte might - // represent a digit. - // - fprintf(outputFile, "\\%03o", c); - } - break; - } - } - fprintf(outputFile, "\";\n"); + fprintf(outputFile, ";\n"); + fprintf(outputFile, "return sb.ProduceString();\n}\n"); } }; -- cgit v1.2.3