summaryrefslogtreecommitdiffstats
path: root/tools
diff options
context:
space:
mode:
authorjsmall-nvidia <jsmall@nvidia.com>2019-09-16 09:38:21 -0400
committerGitHub <noreply@github.com>2019-09-16 09:38:21 -0400
commit40d8f3aeedf018c7c6766e98ec64733abd90671e (patch)
tree0c9cae7bc88d4344dd53596a88c3ce9918f2df13 /tools
parentc2e5d2468ad6a38cdb8a067da0678302f6cc6066 (diff)
CPU Performance/Testing improvements (#1055)
* First pass of render-test refactor. * Make window construction a function that can choose an implementation. * Remove OpenGL as currently has windows dependency. * Disable Vulkan as Renderer impl has dependency on windows. * Pass Window in as parameter of 'update'. * Add win-window.cpp as was missing. * Fix warning on windows about signs during comparison. * * Added mechanism to add random arrays as buffer inputs and select type * Improved RenderGenerator to generate more types, and to be more careful around int32 ranges. * Added support for security checks (for Visual Studio C++) * Disable Execption handling being on by default when compiling kernels * Added a 'Group' version of the entry point that will evaluate all threads in a group in a single call. In test code use this method if available. * Added -compile-arg to be able to pass arguments to the compile within render-test * Add documention for the _Group execution feature. * Fix some typos in cpu-target.md
Diffstat (limited to 'tools')
-rw-r--r--tools/gfx/render.h3
-rw-r--r--tools/render-test/cpu-compute-util.cpp45
-rw-r--r--tools/render-test/options.cpp13
-rw-r--r--tools/render-test/options.h4
-rw-r--r--tools/render-test/render-test-main.cpp6
-rw-r--r--tools/render-test/shader-input-layout.cpp161
-rw-r--r--tools/render-test/shader-input-layout.h3
-rw-r--r--tools/render-test/slang-support.cpp21
-rw-r--r--tools/render-test/slang-support.h2
9 files changed, 236 insertions, 22 deletions
diff --git a/tools/gfx/render.h b/tools/gfx/render.h
index 42cf5fe60..30373b356 100644
--- a/tools/gfx/render.h
+++ b/tools/gfx/render.h
@@ -12,6 +12,7 @@
#include "../../source/core/slang-smart-pointer.h"
#include "../../source/core/slang-list.h"
#include "../../source/core/slang-dictionary.h"
+#include "../../source/core/slang-process-util.h"
#include "../../slang.h"
@@ -149,6 +150,8 @@ struct ShaderCompileRequest
Slang::List<Slang::String> entryPointGenericTypeArguments;
Slang::List<Slang::String> entryPointExistentialTypeArguments;
Slang::List<Slang::String> globalExistentialTypeArguments;
+
+ Slang::List<Slang::CommandLine::Arg> compileArgs;
};
/// Different formats of things like pixels or elements of vertices
diff --git a/tools/render-test/cpu-compute-util.cpp b/tools/render-test/cpu-compute-util.cpp
index 85a8fb1b0..4294ad539 100644
--- a/tools/render-test/cpu-compute-util.cpp
+++ b/tools/render-test/cpu-compute-util.cpp
@@ -316,6 +316,7 @@ static CPUComputeUtil::Resource* _newOneTexture2D(int elemCount)
slang::EntryPointReflection* entryPoint = nullptr;
Func func = nullptr;
+ Func groupFunc = nullptr;
{
auto entryPointCount = reflection->getEntryPointCount();
SLANG_ASSERT(entryPointCount == 1);
@@ -325,15 +326,19 @@ static CPUComputeUtil::Resource* _newOneTexture2D(int elemCount)
const char* entryPointName = entryPoint->getName();
func = (Func)sharedLibrary->findFuncByName(entryPointName);
- if (!func)
+ StringBuilder groupEntryPointName;
+ groupEntryPointName << entryPointName << "_Group";
+
+ groupFunc = (Func)sharedLibrary->findFuncByName(groupEntryPointName.getBuffer());
+
+ if (func == nullptr && groupFunc == nullptr)
{
return SLANG_FAIL;
}
}
- SlangUInt numThreadsPerAxis[3];
- entryPoint->getComputeThreadGroupSize(3, numThreadsPerAxis);
-
+ // If we have the group function, that's the faster way to execute all threads in group...
+ if (groupFunc)
{
UniformState* uniformState = (UniformState*)context.binding.m_rootBuffer.m_data;
CPPPrelude::UniformEntryPointParams* uniformEntryPointParams = (CPPPrelude::UniformEntryPointParams*)context.binding.m_entryPointBuffer.m_data;
@@ -341,17 +346,33 @@ static CPUComputeUtil::Resource* _newOneTexture2D(int elemCount)
CPPPrelude::ComputeVaryingInput varying;
varying.groupID = {};
- for (int z = 0; z < int(numThreadsPerAxis[2]); ++z)
+ groupFunc(&varying, uniformEntryPointParams, uniformState);
+ }
+ else
+ {
+ // We can also fire off each thread individually
+ SlangUInt numThreadsPerAxis[3];
+ entryPoint->getComputeThreadGroupSize(3, numThreadsPerAxis);
+
{
- varying.groupThreadID.z = z;
- for (int y = 0; y < int(numThreadsPerAxis[1]); ++y)
+ UniformState* uniformState = (UniformState*)context.binding.m_rootBuffer.m_data;
+ CPPPrelude::UniformEntryPointParams* uniformEntryPointParams = (CPPPrelude::UniformEntryPointParams*)context.binding.m_entryPointBuffer.m_data;
+
+ CPPPrelude::ComputeVaryingInput varying;
+ varying.groupID = {};
+
+ for (int z = 0; z < int(numThreadsPerAxis[2]); ++z)
{
- varying.groupThreadID.y = y;
- for (int x = 0; x < int(numThreadsPerAxis[0]); ++x)
+ varying.groupThreadID.z = z;
+ for (int y = 0; y < int(numThreadsPerAxis[1]); ++y)
{
- varying.groupThreadID.x = x;
+ varying.groupThreadID.y = y;
+ for (int x = 0; x < int(numThreadsPerAxis[0]); ++x)
+ {
+ varying.groupThreadID.x = x;
- func(&varying, uniformEntryPointParams, uniformState);
+ func(&varying, uniformEntryPointParams, uniformState);
+ }
}
}
}
@@ -360,6 +381,4 @@ static CPUComputeUtil::Resource* _newOneTexture2D(int elemCount)
return SLANG_OK;
}
-
-
} // renderer_test
diff --git a/tools/render-test/options.cpp b/tools/render-test/options.cpp
index a9e51b8e0..1cf0ffbe8 100644
--- a/tools/render-test/options.cpp
+++ b/tools/render-test/options.cpp
@@ -156,6 +156,19 @@ SlangResult parseOptions(int argc, const char*const* argv, Slang::WriterHelper s
{
gOptions.onlyStartup = true;
}
+ else if (strcmp(arg, "-compile-arg") == 0)
+ {
+ if (argCursor == argEnd)
+ {
+ stdError.print("expected argument for '%s' option\n", arg);
+ return SLANG_FAIL;
+ }
+
+ CommandLine::Arg arg;
+ arg.type = CommandLine::ArgType::Escaped;
+ arg.value = *argCursor++;
+ gOptions.compileArgs.add(arg);
+ }
else if (strcmp(arg, "-adapter") == 0)
{
if (argCursor == argEnd)
diff --git a/tools/render-test/options.h b/tools/render-test/options.h
index 0214c66e7..a57c94ed0 100644
--- a/tools/render-test/options.h
+++ b/tools/render-test/options.h
@@ -6,6 +6,8 @@
#include "../../slang-com-helper.h"
#include "../../source/core/slang-writer.h"
+#include "../../source/core/slang-process-util.h"
+
#include "render.h"
namespace renderer_test {
@@ -59,6 +61,8 @@ struct Options
Slang::List<Slang::String> renderFeatures; /// Required render features for this test to run
+ Slang::List<Slang::CommandLine::Arg> compileArgs;
+
Slang::String adapter; ///< The adapter to use either name or index
};
diff --git a/tools/render-test/render-test-main.cpp b/tools/render-test/render-test-main.cpp
index d2ef2a746..0e457f9e4 100644
--- a/tools/render-test/render-test-main.cpp
+++ b/tools/render-test/render-test-main.cpp
@@ -198,7 +198,7 @@ SlangResult RenderTestApp::initialize(SlangSession* session, Renderer* renderer,
Result RenderTestApp::_initializeShaders(SlangSession* session, Renderer* renderer, Options::ShaderProgramType shaderType, const ShaderCompilerUtil::Input& input)
{
ShaderCompilerUtil::OutputAndLayout output;
- SLANG_RETURN_ON_FAIL(ShaderCompilerUtil::compileWithLayout(session, gOptions.sourcePath, shaderType, input, output));
+ SLANG_RETURN_ON_FAIL(ShaderCompilerUtil::compileWithLayout(session, gOptions.sourcePath, gOptions.compileArgs, gOptions.shaderType, input, output));
m_shaderInputLayout = output.layout;
m_shaderProgram = renderer->createProgram(output.output.desc);
return m_shaderProgram ? SLANG_OK : SLANG_FAIL;
@@ -457,7 +457,7 @@ SLANG_TEST_TOOL_API SlangResult innerMain(Slang::StdWriters* stdWriters, SlangSe
}
ShaderCompilerUtil::OutputAndLayout compilationAndLayout;
- SLANG_RETURN_ON_FAIL(ShaderCompilerUtil::compileWithLayout(session, gOptions.sourcePath, gOptions.shaderType, input, compilationAndLayout));
+ SLANG_RETURN_ON_FAIL(ShaderCompilerUtil::compileWithLayout(session, gOptions.sourcePath, gOptions.compileArgs, gOptions.shaderType, input, compilationAndLayout));
CPUComputeUtil::Context context;
SLANG_RETURN_ON_FAIL(CPUComputeUtil::calcBindings(compilationAndLayout, context));
@@ -467,9 +467,7 @@ SLANG_TEST_TOOL_API SlangResult innerMain(Slang::StdWriters* stdWriters, SlangSe
return CPUComputeUtil::writeBindings(compilationAndLayout.layout, context.buffers, gOptions.outputPath);
}
- // Renderer is constructed (later) using the window
Slang::RefPtr<Renderer> renderer;
-
{
RendererUtil::CreateFunc createFunc = RendererUtil::getCreateFunc(gOptions.rendererType);
if (createFunc)
diff --git a/tools/render-test/shader-input-layout.cpp b/tools/render-test/shader-input-layout.cpp
index 7f75805e9..11c87c0d9 100644
--- a/tools/render-test/shader-input-layout.cpp
+++ b/tools/render-test/shader-input-layout.cpp
@@ -7,6 +7,36 @@ namespace renderer_test
{
using namespace Slang;
+#define SLANG_SCALAR_TYPES(x) \
+ x("int", INT32) \
+ x("uint", UINT32) \
+ x("float", FLOAT32)
+
+ struct TypeInfo
+ {
+ UnownedStringSlice name;
+ SlangScalarType type;
+ };
+
+#define SLANG_SCALAR_TYPE_INFO(name, value) { UnownedStringSlice::fromLiteral(name), SLANG_SCALAR_TYPE_##value },
+ static const TypeInfo g_scalarTypeInfos[] =
+ {
+ SLANG_SCALAR_TYPES(SLANG_SCALAR_TYPE_INFO)
+ };
+#undef SLANG_SCALAR_TYPES
+#undef SLANG_SCALAR_TYPE_INFO
+
+ static SlangScalarType _getScalarType(const UnownedStringSlice& slice)
+ {
+ for (const auto& info : g_scalarTypeInfos)
+ {
+ if (info.name == slice)
+ {
+ return info.type;
+ }
+ }
+ return SLANG_SCALAR_TYPE_NONE;
+ }
Index ShaderInputLayout::findEntryIndexByName(const String& name) const
{
@@ -56,7 +86,7 @@ namespace renderer_test
}
}
- void ShaderInputLayout::parse(const char * source)
+ void ShaderInputLayout::parse(RandomGenerator* rand, const char * source)
{
entries.clear();
globalGenericTypeArguments.clear();
@@ -225,9 +255,138 @@ namespace renderer_test
parser.Read("=");
entry.textureDesc.size = parser.ReadInt();
}
+ else if (word == "random")
+ {
+ parser.Read("(");
+ // Read the type
+ String type = parser.ReadWord();
+ SlangScalarType scalarType = _getScalarType(type.getUnownedSlice());
+ if (scalarType == SLANG_SCALAR_TYPE_NONE)
+ {
+ StringBuilder builder;
+ for (const auto& info : g_scalarTypeInfos)
+ {
+ if (builder.getLength() != 0)
+ {
+ builder << ", ";
+ }
+ builder << info.name;
+ }
+
+ throw TextFormatException("Expecting " + builder + " " + parser.NextToken().Position.Line);
+ }
+
+ parser.Read(",");
+ const int size = int(parser.ReadUInt());
+
+ switch (scalarType)
+ {
+ case SLANG_SCALAR_TYPE_INT32:
+ {
+ bool hasRange = false;
+
+ int32_t minValue = -0x7fffffff - 1;
+ int32_t maxValue = 0x7fffffff;
+
+ if (parser.LookAhead(","))
+ {
+ hasRange = true;
+ parser.ReadToken();
+ minValue = parser.ReadInt();
+
+ if (parser.LookAhead(","))
+ {
+ parser.ReadToken();
+ maxValue = parser.ReadInt();
+ }
+ }
+ SLANG_ASSERT(minValue <= maxValue);
+ maxValue = (maxValue >= minValue) ? maxValue : minValue;
+
+ // Generate the data
+ entry.bufferData.setCount(size);
+
+ int32_t* dst = (int32_t*)entry.bufferData.getBuffer();
+ for (int i = 0; i < size; ++i)
+ {
+ dst[i] = hasRange ? rand->nextInt32InRange(minValue, maxValue) : rand->nextInt32();
+ }
+ break;
+ }
+ case SLANG_SCALAR_TYPE_UINT32:
+ {
+ bool hasRange = false;
+ uint32_t minValue = 0;
+ uint32_t maxValue = 0xffffffff;
+
+ if (parser.LookAhead(","))
+ {
+ parser.ReadToken();
+ minValue = parser.ReadUInt();
+
+ hasRange = true;
+
+ if (parser.LookAhead(","))
+ {
+ parser.ReadToken();
+ maxValue = parser.ReadUInt();
+ }
+ }
+
+ SLANG_ASSERT(minValue <= maxValue);
+ maxValue = (maxValue >= minValue) ? maxValue : minValue;
+
+ // Generate the data
+ entry.bufferData.setCount(size);
+
+ uint32_t* dst = (uint32_t*)entry.bufferData.getBuffer();
+ for (int i = 0; i < size; ++i)
+ {
+ dst[i] = hasRange ? rand->nextUInt32InRange(minValue, maxValue) : rand->nextUInt32();
+ }
+
+ break;
+ }
+ case SLANG_SCALAR_TYPE_FLOAT32:
+ {
+ float minValue = -1.0f;
+ float maxValue = 1.0f;
+
+ if (parser.LookAhead(","))
+ {
+ parser.ReadToken();
+ minValue = parser.ReadFloat();
+
+ if (parser.LookAhead(","))
+ {
+ parser.ReadToken();
+ maxValue = parser.ReadFloat();
+ }
+ }
+
+ SLANG_ASSERT(minValue <= maxValue);
+ maxValue = (maxValue >= minValue) ? maxValue : minValue;
+
+ // Generate the data
+ entry.bufferData.setCount(size);
+
+ float* dst = (float*)entry.bufferData.getBuffer();
+ for (int i = 0; i < size; ++i)
+ {
+ dst[i] = (rand->nextUnitFloat32() * (maxValue - minValue)) + minValue;
+ }
+ break;
+ }
+ }
+
+ // Read the range
+
+ parser.Read(")");
+ }
else if (word == "data")
{
parser.Read("=");
+
parser.Read("[");
while (!parser.IsEnd() && !parser.LookAhead("]"))
{
diff --git a/tools/render-test/shader-input-layout.h b/tools/render-test/shader-input-layout.h
index 2a58bfd2c..009be7514 100644
--- a/tools/render-test/shader-input-layout.h
+++ b/tools/render-test/shader-input-layout.h
@@ -2,6 +2,7 @@
#define SLANG_TEST_SHADER_INPUT_LAYOUT_H
#include "core/slang-basic.h"
+#include "core/slang-random-generator.h"
#include "render.h"
@@ -88,7 +89,7 @@ public:
void updateForTarget(SlangCompileTarget target);
- void parse(const char* source);
+ void parse(Slang::RandomGenerator* rand, const char* source);
};
void generateTextureDataRGB8(TextureData& output, const InputTextureDesc& desc);
diff --git a/tools/render-test/slang-support.cpp b/tools/render-test/slang-support.cpp
index df7e91df8..515481d4f 100644
--- a/tools/render-test/slang-support.cpp
+++ b/tools/render-test/slang-support.cpp
@@ -25,6 +25,17 @@ static const char computeEntryPointName[] = "computeMain";
out.request = slangRequest;
out.session = session;
+ // Parse all the extra args
+ if (request.compileArgs.getCount() > 0)
+ {
+ List<const char*> args;
+ for (const auto& arg : request.compileArgs)
+ {
+ args.add(arg.value.getBuffer());
+ }
+ SLANG_RETURN_ON_FAIL(spProcessCommandLineArguments(slangRequest, args.getBuffer(), int(args.getCount())));
+ }
+
spSetCodeGenTarget(slangRequest, input.target);
spSetTargetProfile(slangRequest, 0, spFindProfile(session, input.profile));
@@ -224,7 +235,7 @@ static const char computeEntryPointName[] = "computeMain";
return SLANG_OK;
}
-/* static */SlangResult ShaderCompilerUtil::compileWithLayout(SlangSession* session, const String& sourcePath, Options::ShaderProgramType shaderType, const ShaderCompilerUtil::Input& input, OutputAndLayout& output)
+/* static */SlangResult ShaderCompilerUtil::compileWithLayout(SlangSession* session, const String& sourcePath, const Slang::List<Slang::CommandLine::Arg>& compileArgs, Options::ShaderProgramType shaderType, const ShaderCompilerUtil::Input& input, OutputAndLayout& output)
{
List<char> sourceText;
SLANG_RETURN_ON_FAIL(readSource(sourcePath, sourceText));
@@ -245,8 +256,11 @@ static const char computeEntryPointName[] = "computeMain";
break;
}
+ // Deterministic random generator
+ RefPtr<RandomGenerator> rand = RandomGenerator::create(0x34234);
+
// Parse the layout
- layout.parse(sourceText.getBuffer());
+ layout.parse(rand, sourceText.getBuffer());
layout.updateForTarget(input.target);
// Setup SourceInfo
@@ -257,6 +271,9 @@ static const char computeEntryPointName[] = "computeMain";
sourceInfo.dataEnd = sourceText.getBuffer() + sourceText.getCount() - 1;
ShaderCompileRequest compileRequest;
+
+ compileRequest.compileArgs = compileArgs;
+
compileRequest.source = sourceInfo;
if (shaderType == Options::ShaderProgramType::Graphics || shaderType == Options::ShaderProgramType::GraphicsCompute)
{
diff --git a/tools/render-test/slang-support.h b/tools/render-test/slang-support.h
index 543ab3258..cd3223c87 100644
--- a/tools/render-test/slang-support.h
+++ b/tools/render-test/slang-support.h
@@ -69,7 +69,7 @@ struct ShaderCompilerUtil
Slang::String sourcePath;
};
- static SlangResult compileWithLayout(SlangSession* session, const Slang::String& sourcePath, Options::ShaderProgramType shaderType, const ShaderCompilerUtil::Input& input, OutputAndLayout& output);
+ static SlangResult compileWithLayout(SlangSession* session, const Slang::String& sourcePath, const Slang::List<Slang::CommandLine::Arg>& compileArgs, Options::ShaderProgramType shaderType, const ShaderCompilerUtil::Input& input, OutputAndLayout& output);
static SlangResult readSource(const Slang::String& inSourcePath, List<char>& outSourceText);