DxcTestUtils.h 9.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209
  1. ///////////////////////////////////////////////////////////////////////////////
  2. // //
  3. // DxcTestUtils.h //
  4. // Copyright (C) Microsoft Corporation. All rights reserved. //
  5. // This file is distributed under the University of Illinois Open Source //
  6. // License. See LICENSE.TXT for details. //
  7. // //
  8. // This file provides utility functions for testing dxc APIs. //
  9. // //
  10. ///////////////////////////////////////////////////////////////////////////////
  11. #pragma once
  12. #include <string>
  13. #include <vector>
  14. #include <map>
  15. #include "dxc/dxcapi.h"
  16. #include "dxc/Support/dxcapi.use.h"
  17. #include "llvm/ADT/ArrayRef.h"
  18. #include "llvm/ADT/StringRef.h"
  19. #include "llvm/ADT/StringMap.h"
  20. namespace hlsl {
  21. namespace options {
  22. class DxcOpts;
  23. class MainArgs;
  24. }
  25. }
  26. /// Use this class to run a FileCheck invocation in memory.
  27. class FileCheckForTest {
  28. public:
  29. FileCheckForTest();
  30. std::string CheckFilename;
  31. /// File to check (defaults to stdin)
  32. std::string InputFilename;
  33. /// Prefix to use from check file (defaults to 'CHECK')
  34. std::vector<std::string> CheckPrefixes;
  35. /// Do not treat all horizontal whitespace as equivalent
  36. bool NoCanonicalizeWhiteSpace;
  37. /// Add an implicit negative check with this pattern to every
  38. /// positive check. This can be used to ensure that no instances of
  39. /// this pattern occur which are not matched by a positive pattern
  40. std::vector<std::string> ImplicitCheckNot;
  41. /// Allow the input file to be empty. This is useful when making
  42. /// checks that some error message does not occur, for example.
  43. bool AllowEmptyInput;
  44. /// VariableTable - This holds all the current filecheck variables.
  45. llvm::StringMap<std::string> VariableTable;
  46. /// String to read in place of standard input.
  47. std::string InputForStdin;
  48. /// Output stream.
  49. std::string test_outs;
  50. /// Output stream.
  51. std::string test_errs;
  52. int Run();
  53. };
  54. // wstring because most uses need UTF-16: IDxcResult output names, include handler
  55. typedef std::map<std::wstring, CComPtr<IDxcBlob>> FileMap;
  56. // The result of running a single command in a run pipeline
  57. struct FileRunCommandResult {
  58. CComPtr<IDxcOperationResult> OpResult; // The operation result, if any.
  59. std::string StdOut;
  60. std::string StdErr;
  61. int ExitCode = 0;
  62. bool AbortPipeline = false; // True to prevent running subsequent commands
  63. static inline FileRunCommandResult Success() {
  64. FileRunCommandResult result;
  65. result.ExitCode = 0;
  66. return result;
  67. }
  68. static inline FileRunCommandResult Success(std::string StdOut) {
  69. FileRunCommandResult result;
  70. result.ExitCode = 0;
  71. result.StdOut = std::move(StdOut);
  72. return result;
  73. }
  74. static inline FileRunCommandResult Error(int ExitCode, std::string StdErr) {
  75. FileRunCommandResult result;
  76. result.ExitCode = ExitCode;
  77. result.StdErr = std::move(StdErr);
  78. return result;
  79. }
  80. static inline FileRunCommandResult Error(std::string StdErr) {
  81. return Error(1, StdErr);
  82. }
  83. };
  84. typedef std::map<std::string, std::string> PluginToolsPaths;
  85. class FileRunCommandPart {
  86. public:
  87. FileRunCommandPart(const std::string &command, const std::string &arguments, LPCWSTR commandFileName);
  88. FileRunCommandPart(const FileRunCommandPart&) = default;
  89. FileRunCommandPart(FileRunCommandPart&&) = default;
  90. FileRunCommandResult Run(dxc::DxcDllSupport &DllSupport, const FileRunCommandResult *Prior, PluginToolsPaths *pPluginToolsPaths = nullptr, LPCWSTR dumpName = nullptr);
  91. FileRunCommandResult RunHashTests(dxc::DxcDllSupport &DllSupport);
  92. FileRunCommandResult ReadOptsForDxc(hlsl::options::MainArgs &argStrings, hlsl::options::DxcOpts &Opts, unsigned flagsToInclude = 0);
  93. std::string Command; // Command to run, eg %dxc
  94. std::string Arguments; // Arguments to command
  95. LPCWSTR CommandFileName; // File name replacement for %s
  96. FileMap *pVFS = nullptr; // Files in virtual file system
  97. private:
  98. FileRunCommandResult RunFileChecker(const FileRunCommandResult *Prior, LPCWSTR dumpName = nullptr);
  99. FileRunCommandResult RunDxc(dxc::DxcDllSupport &DllSupport, const FileRunCommandResult *Prior);
  100. FileRunCommandResult RunDxv(dxc::DxcDllSupport &DllSupport, const FileRunCommandResult *Prior);
  101. FileRunCommandResult RunOpt(dxc::DxcDllSupport &DllSupport, const FileRunCommandResult *Prior);
  102. FileRunCommandResult RunD3DReflect(dxc::DxcDllSupport &DllSupport, const FileRunCommandResult *Prior);
  103. FileRunCommandResult RunDxr(dxc::DxcDllSupport &DllSupport, const FileRunCommandResult *Prior);
  104. FileRunCommandResult RunLink(dxc::DxcDllSupport &DllSupport, const FileRunCommandResult *Prior);
  105. FileRunCommandResult RunTee(const FileRunCommandResult *Prior);
  106. FileRunCommandResult RunXFail(const FileRunCommandResult *Prior);
  107. FileRunCommandResult RunDxilVer(dxc::DxcDllSupport& DllSupport, const FileRunCommandResult* Prior);
  108. FileRunCommandResult RunDxcHashTest(dxc::DxcDllSupport &DllSupport);
  109. FileRunCommandResult RunFromPath(const std::string &path, const FileRunCommandResult *Prior);
  110. FileRunCommandResult RunFileCompareText(const FileRunCommandResult *Prior);
  111. #ifdef _WIN32
  112. FileRunCommandResult RunFxc(dxc::DxcDllSupport &DllSupport, const FileRunCommandResult* Prior);
  113. #endif
  114. void SubstituteFilenameVars(std::string &args);
  115. #ifdef _WIN32
  116. bool ReadFileContentToString(HANDLE hFile, std::string &str);
  117. #endif
  118. };
  119. void ParseCommandParts(LPCSTR commands, LPCWSTR fileName, std::vector<FileRunCommandPart> &parts);
  120. void ParseCommandPartsFromFile(LPCWSTR fileName, std::vector<FileRunCommandPart> &parts);
  121. class FileRunTestResult {
  122. public:
  123. std::string ErrorMessage;
  124. int RunResult;
  125. static FileRunTestResult RunHashTestFromFileCommands(LPCWSTR fileName);
  126. static FileRunTestResult RunFromFileCommands(LPCWSTR fileName,
  127. PluginToolsPaths *pPluginToolsPaths = nullptr,
  128. LPCWSTR dumpName = nullptr);
  129. static FileRunTestResult RunFromFileCommands(LPCWSTR fileName,
  130. dxc::DxcDllSupport &dllSupport,
  131. PluginToolsPaths *pPluginToolsPaths = nullptr,
  132. LPCWSTR dumpName = nullptr);
  133. };
  134. void AssembleToContainer(dxc::DxcDllSupport &dllSupport, IDxcBlob *pModule, IDxcBlob **pContainer);
  135. std::string BlobToUtf8(_In_ IDxcBlob *pBlob);
  136. std::wstring BlobToUtf16(_In_ IDxcBlob *pBlob);
  137. void CheckOperationSucceeded(IDxcOperationResult *pResult, IDxcBlob **ppBlob);
  138. bool CheckOperationResultMsgs(IDxcOperationResult *pResult,
  139. llvm::ArrayRef<LPCSTR> pErrorMsgs,
  140. bool maySucceedAnyway, bool bRegex);
  141. bool CheckOperationResultMsgs(IDxcOperationResult *pResult,
  142. const LPCSTR *pErrorMsgs, size_t errorMsgCount,
  143. bool maySucceedAnyway, bool bRegex);
  144. bool CheckMsgs(const LPCSTR pText, size_t TextCount, const LPCSTR *pErrorMsgs,
  145. size_t errorMsgCount, bool bRegex);
  146. bool CheckNotMsgs(const LPCSTR pText, size_t TextCount, const LPCSTR *pErrorMsgs,
  147. size_t errorMsgCount, bool bRegex);
  148. void GetDxilPart(dxc::DxcDllSupport &dllSupport, IDxcBlob *pProgram, IDxcBlob **pDxilPart);
  149. std::string DisassembleProgram(dxc::DxcDllSupport &dllSupport, IDxcBlob *pProgram);
  150. void SplitPassList(LPWSTR pPassesBuffer, std::vector<LPCWSTR> &passes);
  151. void MultiByteStringToBlob(dxc::DxcDllSupport &dllSupport, const std::string &val, UINT32 codePoint, _Outptr_ IDxcBlob **ppBlob);
  152. void MultiByteStringToBlob(dxc::DxcDllSupport &dllSupport, const std::string &val, UINT32 codePoint, _Outptr_ IDxcBlobEncoding **ppBlob);
  153. void Utf8ToBlob(dxc::DxcDllSupport &dllSupport, const std::string &val, _Outptr_ IDxcBlob **ppBlob);
  154. void Utf8ToBlob(dxc::DxcDllSupport &dllSupport, const std::string &val, _Outptr_ IDxcBlobEncoding **ppBlob);
  155. void Utf8ToBlob(dxc::DxcDllSupport &dllSupport, const char *pVal, _Outptr_ IDxcBlobEncoding **ppBlob);
  156. void Utf16ToBlob(dxc::DxcDllSupport &dllSupport, const std::wstring &val, _Outptr_ IDxcBlob **ppBlob);
  157. void Utf16ToBlob(dxc::DxcDllSupport &dllSupport, const std::wstring &val, _Outptr_ IDxcBlobEncoding **ppBlob);
  158. void VerifyCompileOK(dxc::DxcDllSupport &dllSupport, LPCSTR pText,
  159. LPWSTR pTargetProfile, LPCWSTR pArgs,
  160. _Outptr_ IDxcBlob **ppResult);
  161. void VerifyCompileOK(dxc::DxcDllSupport &dllSupport, LPCSTR pText,
  162. LPWSTR pTargetProfile, std::vector<LPCWSTR> &args,
  163. _Outptr_ IDxcBlob **ppResult);
  164. HRESULT GetVersion(dxc::DxcDllSupport& DllSupport, REFCLSID clsid, unsigned &Major, unsigned &Minor);
  165. bool ParseTargetProfile(llvm::StringRef targetProfile, llvm::StringRef &outStage, unsigned &outMajor, unsigned &outMinor);
  166. class VersionSupportInfo {
  167. private:
  168. bool m_CompilerIsDebugBuild;
  169. public:
  170. bool m_InternalValidator;
  171. unsigned m_DxilMajor, m_DxilMinor;
  172. unsigned m_ValMajor, m_ValMinor;
  173. VersionSupportInfo();
  174. // Initialize version info structure. TODO: add device shader model support
  175. void Initialize(dxc::DxcDllSupport &dllSupport);
  176. // Return true if IR sensitive test should be skipped, and log comment
  177. bool SkipIRSensitiveTest();
  178. // Return true if test requiring DXIL of given version should be skipped, and log comment
  179. bool SkipDxilVersion(unsigned major, unsigned minor);
  180. // Return true if out-of-memory test should be skipped, and log comment
  181. bool SkipOutOfMemoryTest();
  182. };