From c0733be56dc24ef0eb67b26fe0c49d3419e75773 Mon Sep 17 00:00:00 2001 From: jsmall-nvidia Date: Tue, 9 Aug 2022 10:31:22 -0400 Subject: Support for Items on IArtifact (#2347) * #include an absolute path didn't work - because paths were taken to always be relative. * WIP with hierarchical enums. * Some small fixes and improvements around artifact desc related types. * Improvements around hierarchical enum. * Fixes to get Artifact types refactor to be able to execute tests. * Attempt to better categorize PTX. * Work around for potentially unused function warning. * Typo fix. * Simplify Artifact header. * Small improvements around Artifact kind/payload/style. * Added IDestroyable/ICastable * Add IArtifactList. * First impl of IArtifactUtil. * Use the ICastable interface for IArtifactRepresentation. * Added IArtifactRepresentation & IArtifactAssociated. * Add SLANG_OVERRIDE to avoid gcc/clang warning. * Fix calling convention issue on win32. * Fix missing SLANG_OVERRIDE. * First attempt at file abstraction around Artifact. * Added creation of lock file. * Move functionality for determining file paths to the IArtifactUtil. Add casting to ICastable. * Added some casting/finding mechanisms. * Simplify IArtifact interface, and use Items for file reps. * Fix problem with libraries on DXIL. --- source/compiler-core/slang-artifact-util.cpp | 90 ++++++++++++++++++++++++++++ 1 file changed, 90 insertions(+) (limited to 'source/compiler-core/slang-artifact-util.cpp') diff --git a/source/compiler-core/slang-artifact-util.cpp b/source/compiler-core/slang-artifact-util.cpp index 3ca10446c..5c1641f7f 100644 --- a/source/compiler-core/slang-artifact-util.cpp +++ b/source/compiler-core/slang-artifact-util.cpp @@ -3,8 +3,13 @@ #include "slang-artifact-info.h" +#include "../core/slang-file-system.h" +#include "../core/slang-io.h" + namespace Slang { +/* !!!!!!!!!!!!!!!!!!!!!!!!!!!!! ArtifactUtilImpl !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! */ + /* static */ArtifactUtilImpl ArtifactUtilImpl::g_singleton; SlangResult ArtifactUtilImpl::queryInterface(SlangUUID const& uuid, void** outObject) @@ -60,4 +65,89 @@ ArtifactStyle ArtifactUtilImpl::getStyleParent(ArtifactStyle style) { return get UnownedStringSlice ArtifactUtilImpl::getStyleName(ArtifactStyle style) { return getName(style); } bool ArtifactUtilImpl::isStyleDerivedFrom(ArtifactStyle style, ArtifactStyle base) { return isDerivedFrom(style, base); } +SlangResult ArtifactUtilImpl::createLockFile(const char* inNameBase, ISlangMutableFileSystem* fileSystem, ILockFile** outLockFile) +{ + if (fileSystem) + { + if (fileSystem != OSFileSystem::getMutableSingleton()) + { + // We can only create lock files, on the global OS file system + return SLANG_E_NOT_AVAILABLE; + } + fileSystem = nullptr; + } + + const UnownedStringSlice nameBase = (inNameBase && inNameBase[0] != 0) ? UnownedStringSlice(inNameBase) : UnownedStringSlice("unknown"); + + String lockPath; + SLANG_RETURN_ON_FAIL(File::generateTemporary(nameBase, lockPath)); + + ComPtr lockFile(new LockFile(lockPath, fileSystem)); + + *outLockFile = lockFile.detach(); + return SLANG_OK; +} + +SlangResult ArtifactUtilImpl::calcArtifactPath(const ArtifactDesc& desc, const char* inBasePath, ISlangBlob** outPath) +{ + UnownedStringSlice basePath(inBasePath); + + StringBuilder path; + SLANG_RETURN_ON_FAIL(ArtifactInfoUtil::calcPathForDesc(desc, basePath, path)); + + auto blob = new StringBlob(path); + blob->addRef(); + *outPath = blob; + return SLANG_OK; +} + +SlangResult ArtifactUtilImpl::requireFileDefaultImpl(IArtifact* artifact, ArtifactKeep keep, IFileArtifactRepresentation** outFile) +{ + // See if we already have it + if (auto fileRep = findItem(artifact)) + { + fileRep->addRef(); + *outFile = fileRep; + return SLANG_OK; + } + + // If we are going to access as a file we need to be able to write it, and to do that we need a blob + ComPtr blob; + SLANG_RETURN_ON_FAIL(artifact->loadBlob(keep, blob.writeRef())); + + // Okay we need to store as a temporary. Get a lock file. + ComPtr lockFile; + SLANG_RETURN_ON_FAIL(createLockFile(artifact->getName(), nullptr, lockFile.writeRef())); + + // Now we need the appropriate name for this item + ComPtr pathBlob; + SLANG_RETURN_ON_FAIL(calcArtifactPath(artifact->getDesc(), lockFile->getPath(), pathBlob.writeRef())); + + const auto path = StringUtil::getString(pathBlob); + + // Write the contents + SLANG_RETURN_ON_FAIL(File::writeAllBytes(path, blob->getBufferPointer(), blob->getBufferSize())); + + // If the paths are identical we don't need a lock file + if (UnownedStringSlice(lockFile->getPath()) == path.getUnownedSlice()) + { + // Make the lockFile no longer own the file + lockFile->disown(); + // We no longer need the lock file + lockFile.setNull(); + } + + // Create the rep + IFileArtifactRepresentation* fileRep = new FileArtifactRepresentation(IFileArtifactRepresentation::Kind::Owned, path, lockFile, nullptr); + if (canKeep(keep)) + { + artifact->addItem(fileRep); + } + + // Return it + fileRep->addRef(); + *outFile = fileRep; + return SLANG_OK; +} + } // namespace Slang -- cgit v1.2.3