--deqp-vk-device-id=<value>
+To speed up the conformance run on some platforms the following command line
+option may be used to disable frequent fflush() calls to the output logs:
+
+ --deqp-log-flush=disable
+
No other command line options are allowed.
### Win32
namespace
{
+static const deUint32 MAX_BUFFER_SIZE_DIVISOR = 16;
+
struct BufferCaseParameters
{
VkBufferUsageFlags usage;
tcu::TestStatus BufferTestInstance::bufferCreateAndAllocTest (VkDeviceSize size)
{
- const VkDevice vkDevice = m_context.getDevice();
- const DeviceInterface& vk = m_context.getDeviceInterface();
- Move<VkBuffer> testBuffer;
- VkMemoryRequirements memReqs;
- Move<VkDeviceMemory> memory;
- const deUint32 queueFamilyIndex = m_context.getUniversalQueueFamilyIndex();
+ const VkPhysicalDevice vkPhysicalDevice = m_context.getPhysicalDevice();
+ const InstanceInterface& vkInstance = m_context.getInstanceInterface();
+ const VkDevice vkDevice = m_context.getDevice();
+ const DeviceInterface& vk = m_context.getDeviceInterface();
+ Move<VkBuffer> testBuffer;
+ VkMemoryRequirements memReqs;
+ Move<VkDeviceMemory> memory;
+ const deUint32 queueFamilyIndex = m_context.getUniversalQueueFamilyIndex();
+ const VkPhysicalDeviceMemoryProperties memoryProperties = getPhysicalDeviceMemoryProperties(vkInstance, vkPhysicalDevice);
// Create buffer
{
- const VkBufferCreateInfo bufferParams =
+ VkBufferCreateInfo bufferParams =
{
VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO,
DE_NULL,
try
{
- testBuffer = createBuffer(vk, vkDevice, &bufferParams, (const VkAllocationCallbacks*)DE_NULL);
+ testBuffer = createBuffer(vk, vkDevice, &bufferParams);
}
catch (const vk::Error& error)
{
vk.getBufferMemoryRequirements(vkDevice, *testBuffer, &memReqs);
+ const deUint32 heapTypeIndex = (deUint32)deCtz32(memReqs.memoryTypeBits);
+ const VkMemoryType memoryType = memoryProperties.memoryTypes[heapTypeIndex];
+ const VkMemoryHeap memoryHeap = memoryProperties.memoryHeaps[memoryType.heapIndex];
+ const VkDeviceSize maxBufferSize = memoryHeap.size / MAX_BUFFER_SIZE_DIVISOR;
+ // If the requested size is too large, clamp it based on the selected heap size
+ if (size > maxBufferSize)
+ {
+ size = maxBufferSize;
+ bufferParams.size = size;
+ try
+ {
+ // allocate a new buffer with the adjusted size, the old one will be destroyed by the smart pointer
+ testBuffer = createBuffer(vk, vkDevice, &bufferParams);
+ }
+ catch (const vk::Error& error)
+ {
+ return tcu::TestStatus::fail("Buffer creation failed! (requested memory size: " + de::toString(size) + ", Error code: " + de::toString(error.getMessage()) + ")");
+ }
+ vk.getBufferMemoryRequirements(vkDevice, *testBuffer, &memReqs);
+ }
+
if (size > memReqs.size)
{
std::ostringstream errorMsg;
{
const VkPhysicalDevice vkPhysicalDevice = m_context.getPhysicalDevice();
const InstanceInterface& vkInstance = m_context.getInstanceInterface();
- const VkPhysicalDeviceMemoryProperties memoryProperties = getPhysicalDeviceMemoryProperties(vkInstance, vkPhysicalDevice);
VkPhysicalDeviceProperties props;
vkInstance.getPhysicalDeviceProperties(vkPhysicalDevice, &props);
-
- const VkDeviceSize maxTestBufferSize = de::min((VkDeviceSize) props.limits.maxTexelBufferElements, memoryProperties.memoryHeaps[memoryProperties.memoryTypes[0].heapIndex].size / 16);
-
- testStatus = bufferCreateAndAllocTest(maxTestBufferSize);
+ testStatus = bufferCreateAndAllocTest((VkDeviceSize) props.limits.maxTexelBufferElements);
}
return testStatus;
typedPtr[offset + ndx] = randomScalar<T>(rnd, minValue, maxValue);
}
+static void floorAll (vector<float>& values)
+{
+ for (size_t i = 0; i < values.size(); i++)
+ values[i] = deFloatFloor(values[i]);
+}
+
+static void floorAll (vector<Vec4>& values)
+{
+ for (size_t i = 0; i < values.size(); i++)
+ values[i] = floor(values[i]);
+}
+
struct CaseParameter
{
const char* name;
fillRandomScalars(rnd, -200.f, 200.f, &inputFloats1[0], numElements * 4);
+ // CPU might not use the same rounding mode as the GPU. Use whole numbers to avoid rounding differences.
+ floorAll(inputFloats1);
+
for (size_t ndx = 0; ndx < numElements; ++ndx)
outputFloats1[ndx] = inputFloats1[ndx] + Vec4(0.f, 0.5f, 1.5f, 2.5f);
fillRandomScalars(rnd, -200.f, 200.f, &inputFloats[0], numElements);
+ // CPU might not use the same rounding mode as the GPU. Use whole numbers to avoid rounding differences.
+ floorAll(inputFloats);
+
for (size_t ndx = 0; ndx < numElements; ++ndx)
outputFloats[ndx] = inputFloats[ndx] + 7.5f;
fillRandomScalars(rnd, -300.f, 300.f, &inputFloats3[0], numElements);
fillRandomScalars(rnd, -300.f, 300.f, &inputFloats4[0], numElements);
-
- for (size_t ndx = 0; ndx < numElements; ++ndx)
- {
- inputFloats0[ndx] = deFloatFloor(inputFloats0[ndx]);
- inputFloats1[ndx] = deFloatFloor(inputFloats1[ndx]);
- inputFloats2[ndx] = deFloatFloor(inputFloats2[ndx]);
- inputFloats3[ndx] = deFloatFloor(inputFloats3[ndx]);
- inputFloats4[ndx] = deFloatFloor(inputFloats4[ndx]);
- }
+ // CPU might not use the same rounding mode as the GPU. Use whole numbers to avoid rounding differences.
+ floorAll(inputFloats0);
+ floorAll(inputFloats1);
+ floorAll(inputFloats2);
+ floorAll(inputFloats3);
+ floorAll(inputFloats4);
for (size_t ndx = 0; ndx < numElements; ++ndx)
outputFloats[ndx] = inputFloats0[ndx] + inputFloats1[ndx] + inputFloats2[ndx] + inputFloats3[ndx] + inputFloats4[ndx];
fillRandomScalars(rnd, -300.f, 300.f, &inputFloats[0], numElements);
+ // CPU might not use the same rounding mode as the GPU. Use whole numbers to avoid rounding differences.
+ floorAll(inputFloats);
+
for (size_t ndx = 0; ndx < numElements; ++ndx)
{
switch (ndx % 3)
fillRandomScalars(rnd, -100.f, 100.f, &inputFloats[0], numElements);
- for (size_t ndx = 0; ndx < numElements; ++ndx)
- inputFloats[ndx] = deFloatFloor(inputFloats[ndx]);
+ // CPU might not use the same rounding mode as the GPU. Use whole numbers to avoid rounding differences.
+ floorAll(inputFloats);
for (size_t ndx = 0; ndx <= 50; ++ndx)
outputFloats[ndx] = -inputFloats[ndx];
fillRandomScalars(rnd, -100.f, 100.f, &inputFloats[0], numElements);
+ // CPU might not use the same rounding mode as the GPU. Use whole numbers to avoid rounding differences.
+ floorAll(inputFloats);
+
for (size_t ndx = 0; ndx < numElements; ++ndx)
outputFloats[ndx] = inputFloats[ndx] + (inputFloats[ndx] > 10.f ? 1.f : -1.f);
fillRandomScalars(rnd, -100.f, 100.f, &inputFloats[0], numElements);
+ // CPU might not use the same rounding mode as the GPU. Use whole numbers to avoid rounding differences.
+ floorAll(inputFloats);
+
for (size_t ndx = 0; ndx < numElements; ++ndx)
outputFloats[ndx] = inputFloats[ndx] + 10.f;
DE_DECLARE_COMMAND_LINE_OPT(LogShaderSources, bool);
DE_DECLARE_COMMAND_LINE_OPT(TestOOM, bool);
DE_DECLARE_COMMAND_LINE_OPT(VKDeviceID, int);
+DE_DECLARE_COMMAND_LINE_OPT(LogFlush, bool);
static void parseIntList (const char* src, std::vector<int>* dst)
{
<< Option<VKDeviceID> (DE_NULL, "deqp-vk-device-id", "Vulkan device ID (IDs start from 1)", "1")
<< Option<LogImages> (DE_NULL, "deqp-log-images", "Enable or disable logging of result images", s_enableNames, "enable")
<< Option<LogShaderSources> (DE_NULL, "deqp-log-shader-sources", "Enable or disable logging of shader sources", s_enableNames, "enable")
- << Option<TestOOM> (DE_NULL, "deqp-test-oom", "Run tests that exhaust memory on purpose", s_enableNames, TEST_OOM_DEFAULT);
+ << Option<TestOOM> (DE_NULL, "deqp-test-oom", "Run tests that exhaust memory on purpose", s_enableNames, TEST_OOM_DEFAULT)
+ << Option<LogFlush> (DE_NULL, "deqp-log-flush", "Enable or disable log file fflush", s_enableNames, "enable");
}
void registerLegacyOptions (de::cmdline::Parser& parser)
if (!m_cmdLine.getOption<opt::LogShaderSources>())
m_logFlags |= QP_TEST_LOG_EXCLUDE_SHADER_SOURCES;
+ if (!m_cmdLine.getOption<opt::LogFlush>())
+ m_logFlags |= QP_TEST_LOG_NO_FLUSH;
+
if ((m_cmdLine.hasOption<opt::CasePath>()?1:0) +
(m_cmdLine.hasOption<opt::CaseList>()?1:0) +
(m_cmdLine.hasOption<opt::CaseListFile>()?1:0) +
if (!file)
throw Exception("Failed to open " + filename);
- writer = qpXmlWriter_createFileWriter(file, DE_FALSE);
+ writer = qpXmlWriter_createFileWriter(file, DE_FALSE, DE_FALSE);
if (!writer)
throw Exception("XML writer creation failed");
}
log->flags = flags;
- log->writer = qpXmlWriter_createFileWriter(log->outputFile, 0);
+ log->writer = qpXmlWriter_createFileWriter(log->outputFile, 0, !(flags & QP_TEST_LOG_NO_FLUSH));
log->lock = deMutex_create(DE_NULL);
log->isSessionOpen = DE_FALSE;
log->isCaseOpen = DE_FALSE;
/* Flush XML and write out #beginTestCaseResult. */
qpXmlWriter_flush(log->writer);
fprintf(log->outputFile, "\n#beginTestCaseResult %s\n", testCasePath);
- qpTestLog_flushFile(log);
+ if (!(log->flags & QP_TEST_LOG_NO_FLUSH))
+ qpTestLog_flushFile(log);
log->isCaseOpen = DE_TRUE;
/* Flush XML and write #endTestCaseResult. */
qpXmlWriter_flush(log->writer);
fprintf(log->outputFile, "\n#endTestCaseResult\n");
- qpTestLog_flushFile(log);
+ if (!(log->flags & QP_TEST_LOG_NO_FLUSH))
+ qpTestLog_flushFile(log);
log->isCaseOpen = DE_FALSE;
typedef enum qpTestLogFlag_e
{
QP_TEST_LOG_EXCLUDE_IMAGES = (1<<0), /*!< Do not log images. This reduces log size considerably. */
- QP_TEST_LOG_EXCLUDE_SHADER_SOURCES = (1<<1) /*!< Do not log shader sources. Helps to reduce log size further. */
+ QP_TEST_LOG_EXCLUDE_SHADER_SOURCES = (1<<1), /*!< Do not log shader sources. Helps to reduce log size further. */
+ QP_TEST_LOG_NO_FLUSH = (1<<2) /*!< Do not do a fflush after writing the log. */
} qpTestLogFlag;
/* Shader type. */
struct qpXmlWriter_s
{
FILE* outputFile;
+ deBool flushAfterWrite;
deBool xmlPrevIsStartElement;
deBool xmlIsWriting;
}
} while (!isEOS);
- fflush(writer->outputFile);
+ if (writer->flushAfterWrite)
+ fflush(writer->outputFile);
DE_ASSERT(d == &buf[0]); /* buffer must be empty */
return DE_TRUE;
}
-qpXmlWriter* qpXmlWriter_createFileWriter (FILE* outputFile, deBool useCompression)
+qpXmlWriter* qpXmlWriter_createFileWriter (FILE* outputFile, deBool useCompression, deBool flushAfterWrite)
{
qpXmlWriter* writer = (qpXmlWriter*)deCalloc(sizeof(qpXmlWriter));
if (!writer)
DE_UNREF(useCompression); /* no compression supported. */
writer->outputFile = outputFile;
+ writer->flushAfterWrite = flushAfterWrite;
return writer;
}
* \brief Create a file based XML Writer instance
* \param fileName Name of the file
* \param useCompression Set to DE_TRUE to use compression, if supported by implementation
+ * \param flushAfterWrite Set to DE_TRUE to call fflush after writing each XML token
* \return qpXmlWriter instance, or DE_NULL if cannot create file
*//*--------------------------------------------------------------------*/
-qpXmlWriter* qpXmlWriter_createFileWriter (FILE* outFile, deBool useCompression);
+qpXmlWriter* qpXmlWriter_createFileWriter (FILE* outFile, deBool useCompression, deBool flushAfterWrite);
/*--------------------------------------------------------------------*//*!
* \brief XML Writer instance