diff --git a/include/dxc/Support/dxcfilesystem.h b/include/dxc/Support/dxcfilesystem.h index 2fda88097..de3d84148 100644 --- a/include/dxc/Support/dxcfilesystem.h +++ b/include/dxc/Support/dxcfilesystem.h @@ -13,6 +13,7 @@ #include "dxc/dxcapi.h" #include "llvm/Support/MSFileSystem.h" +#include namespace clang { class CompilerInstance; @@ -46,4 +47,6 @@ DxcArgsFileSystem * CreateDxcArgsFileSystem(_In_ IDxcBlobUtf8 *pSource, _In_ LPCWSTR pSourceName, _In_opt_ IDxcIncludeHandler *pIncludeHandler); +void MakeAbsoluteOrCurDirRelativeW(LPCWSTR &Path, std::wstring &PathStorage); + } // namespace dxcutil \ No newline at end of file diff --git a/tools/clang/tools/dxcompiler/dxcfilesystem.cpp b/tools/clang/tools/dxcompiler/dxcfilesystem.cpp index 8065ff556..ef1c8c8fa 100644 --- a/tools/clang/tools/dxcompiler/dxcfilesystem.cpp +++ b/tools/clang/tools/dxcompiler/dxcfilesystem.cpp @@ -180,6 +180,10 @@ bool IsAbsoluteOrCurDirRelativeW(LPCWSTR Path) { return FALSE; } +} + +namespace dxcutil { + void MakeAbsoluteOrCurDirRelativeW(LPCWSTR &Path, std::wstring &PathStorage) { if (IsAbsoluteOrCurDirRelativeW(Path)) { return; @@ -191,9 +195,6 @@ void MakeAbsoluteOrCurDirRelativeW(LPCWSTR &Path, std::wstring &PathStorage) { } } -} - -namespace dxcutil { /// File system based on API arguments. Support being added incrementally. /// /// DxcArgsFileSystem emulates a file system to clang/llvm based on API diff --git a/tools/clang/tools/dxcompiler/dxcpdbutils.cpp b/tools/clang/tools/dxcompiler/dxcpdbutils.cpp index fc19335a2..b83437a7f 100644 --- a/tools/clang/tools/dxcompiler/dxcpdbutils.cpp +++ b/tools/clang/tools/dxcompiler/dxcpdbutils.cpp @@ -38,6 +38,7 @@ #include "dxc/Support/HLSLOptions.h" #include "dxcshadersourceinfo.h" +#include "dxc/Support/dxcfilesystem.h" #include #include @@ -79,6 +80,8 @@ static HRESULT CopyWstringToBSTR(const std::wstring &str, BSTR *pResult) { } static std::wstring NormalizePath(const WCHAR *path) { + std::wstring PathStorage; + dxcutil::MakeAbsoluteOrCurDirRelativeW(path, PathStorage); std::string FilenameStr8 = Unicode::UTF16ToUTF8StringOrThrow(path); llvm::SmallString<128> NormalizedPath; llvm::sys::path::native(FilenameStr8, NormalizedPath); @@ -223,7 +226,8 @@ struct PdbRecompilerIncludeHandler : public IDxcIncludeHandler { return E_POINTER; *ppIncludeSource = nullptr; - auto it = m_FileMap.find(NormalizePath(pFilename)); + std::wstring Filename = NormalizePath(pFilename); + auto it = m_FileMap.find(Filename); if (it == m_FileMap.end()) return E_FAIL; diff --git a/tools/clang/unittests/HLSL/CompilerTest.cpp b/tools/clang/unittests/HLSL/CompilerTest.cpp index f0ef410c4..475b1eeef 100644 --- a/tools/clang/unittests/HLSL/CompilerTest.cpp +++ b/tools/clang/unittests/HLSL/CompilerTest.cpp @@ -130,6 +130,7 @@ public: TEST_METHOD(CompileThenTestPdbUtils) TEST_METHOD(CompileThenTestPdbUtilsStripped) TEST_METHOD(CompileThenTestPdbUtilsEmptyEntry) + TEST_METHOD(CompileThenTestPdbUtilsRelativePath) TEST_METHOD(CompileWithRootSignatureThenStripRootSignature) TEST_METHOD(CompileWhenIncludeThenLoadInvoked) @@ -1536,6 +1537,58 @@ TEST_F(CompilerTest, CompileThenTestPdbUtils) { TestPdbUtils(/*bSlim*/true, /*bSourceInDebugModule*/false, /*strip*/true); // Slim PDB, where source info is stored in its own part, and debug module is NOT present } +TEST_F(CompilerTest, CompileThenTestPdbUtilsRelativePath) { + std::string main_source = R"x( + #include "helper.h" + cbuffer MyCbuffer : register(b1) { + float4 my_cbuf_foo; + } + + [RootSignature("CBV(b1)")] + float4 main() : SV_Target { + return my_cbuf_foo; + } + )x"; + + CComPtr pCompiler; + VERIFY_SUCCEEDED(m_dllSupport.CreateInstance(CLSID_DxcCompiler, &pCompiler)); + + DxcBuffer SourceBuf = {}; + SourceBuf.Ptr = main_source.c_str(); + SourceBuf.Size = main_source.size(); + SourceBuf.Encoding = CP_UTF8; + + std::vector args; + args.push_back(L"/Tps_6_0"); + args.push_back(L"/Zi"); + args.push_back(L"/Qsource_only_debug"); + args.push_back(L"shaders/Shader.hlsl"); + + CComPtr pInclude; + std::string included_File = "#define ZERO 0"; + pInclude = new TestIncludeHandler(m_dllSupport); + pInclude->CallResults.emplace_back(included_File.c_str()); + + CComPtr pResult; + VERIFY_SUCCEEDED(pCompiler->Compile(&SourceBuf, args.data(), args.size(), pInclude, IID_PPV_ARGS(&pResult))); + + CComPtr pPdb; + CComPtr pPdbName; + VERIFY_SUCCEEDED(pResult->GetOutput(DXC_OUT_PDB, IID_PPV_ARGS(&pPdb), &pPdbName)); + + CComPtr pPdbUtils; + VERIFY_SUCCEEDED(m_dllSupport.CreateInstance(CLSID_DxcPdbUtils, &pPdbUtils)); + + VERIFY_SUCCEEDED(pPdbUtils->Load(pPdb)); + + CComPtr pFullPdb; + VERIFY_SUCCEEDED(pPdbUtils->GetFullPDB(&pFullPdb)); + + VERIFY_SUCCEEDED(pPdbUtils->Load(pFullPdb)); + VERIFY_IS_TRUE(pPdbUtils->IsFullPDB()); +} + + TEST_F(CompilerTest, CompileThenTestPdbUtilsEmptyEntry) { std::string main_source = R"x( cbuffer MyCbuffer : register(b1) {