summaryrefslogtreecommitdiffstats
path: root/source
diff options
context:
space:
mode:
Diffstat (limited to 'source')
-rw-r--r--source/compiler-core/slang-artifact-desc-util.cpp1
-rw-r--r--source/compiler-core/slang-artifact-handler-impl.cpp6
-rw-r--r--source/compiler-core/slang-artifact-handler-impl.h2
-rw-r--r--source/compiler-core/slang-artifact-helper.cpp25
-rw-r--r--source/compiler-core/slang-artifact-helper.h13
-rw-r--r--source/compiler-core/slang-artifact-impl.cpp300
-rw-r--r--source/compiler-core/slang-artifact-impl.h107
-rw-r--r--source/compiler-core/slang-artifact-representation-impl.cpp2
-rw-r--r--source/compiler-core/slang-artifact-util.cpp141
-rw-r--r--source/compiler-core/slang-artifact-util.h30
-rw-r--r--source/compiler-core/slang-artifact.h111
-rw-r--r--source/compiler-core/slang-downstream-compiler.cpp40
-rw-r--r--source/compiler-core/slang-dxc-compiler.cpp4
-rw-r--r--source/compiler-core/slang-fxc-compiler.cpp3
-rw-r--r--source/compiler-core/slang-glslang-compiler.cpp3
-rw-r--r--source/compiler-core/slang-llvm-compiler.cpp5
-rw-r--r--source/compiler-core/slang-nvrtc-compiler.cpp2
-rw-r--r--source/compiler-core/slang-slice-allocator.h1
-rw-r--r--source/core/slang-archive-file-system.cpp4
-rw-r--r--source/core/slang-castable-list-impl.cpp136
-rw-r--r--source/core/slang-castable-list-impl.h53
-rw-r--r--source/core/slang-castable-list.h68
-rw-r--r--source/core/slang-castable-util.h58
-rw-r--r--source/core/slang-castable.cpp (renamed from source/core/slang-castable-util.cpp)4
-rw-r--r--source/core/slang-castable.h106
-rw-r--r--source/core/slang-destroyable.h68
-rw-r--r--source/core/slang-lazy-castable-list.cpp175
-rw-r--r--source/core/slang-lazy-castable-list.h68
-rw-r--r--source/slang/slang-compiler.cpp25
-rw-r--r--source/slang/slang-emit.cpp10
-rw-r--r--source/slang/slang-options.cpp1
-rw-r--r--source/slang/slang-repro.cpp1
-rw-r--r--source/slang/slang.cpp3
33 files changed, 484 insertions, 1092 deletions
diff --git a/source/compiler-core/slang-artifact-desc-util.cpp b/source/compiler-core/slang-artifact-desc-util.cpp
index 3be0448c4..da97ce3f5 100644
--- a/source/compiler-core/slang-artifact-desc-util.cpp
+++ b/source/compiler-core/slang-artifact-desc-util.cpp
@@ -222,6 +222,7 @@ SLANG_HIERARCHICAL_ENUM(ArtifactKind, SLANG_ARTIFACT_KIND, SLANG_ARTIFACT_KIND_E
x(DebugInfo, Metadata) \
x(PdbDebugInfo, DebugInfo) \
x(Diagnostics, Metadata) \
+ x(PostEmitMetadata, Metadata) \
x(Miscellaneous, Base) \
x(Log, Miscellaneous) \
x(Lock, Miscellaneous) \
diff --git a/source/compiler-core/slang-artifact-handler-impl.cpp b/source/compiler-core/slang-artifact-handler-impl.cpp
index 84b786784..1b71dbf59 100644
--- a/source/compiler-core/slang-artifact-handler-impl.cpp
+++ b/source/compiler-core/slang-artifact-handler-impl.cpp
@@ -9,7 +9,7 @@
#include "slang-artifact-helper.h"
#include "slang-artifact-util.h"
-#include "../core/slang-castable-util.h"
+#include "../core/slang-castable.h"
#include "slang-slice-allocator.h"
@@ -93,8 +93,9 @@ SlangResult DefaultArtifactHandler::_addRepresentation(IArtifact* artifact, Arti
return SLANG_OK;
}
-SlangResult DefaultArtifactHandler::expandChildren(IArtifactContainer* container)
+SlangResult DefaultArtifactHandler::expandChildren(IArtifact* container)
{
+ // First check if it has already been expanded
SlangResult res = container->getExpandChildrenResult();
if (res != SLANG_E_UNINITIALIZED)
{
@@ -109,6 +110,7 @@ SlangResult DefaultArtifactHandler::expandChildren(IArtifactContainer* container
container->setChildren(nullptr, 0);
return SLANG_OK;
}
+
// TODO(JS):
// Proper implementation should (for example) be able to expand a Zip file etc.
return SLANG_E_NOT_IMPLEMENTED;
diff --git a/source/compiler-core/slang-artifact-handler-impl.h b/source/compiler-core/slang-artifact-handler-impl.h
index a46005a33..c1cd25980 100644
--- a/source/compiler-core/slang-artifact-handler-impl.h
+++ b/source/compiler-core/slang-artifact-handler-impl.h
@@ -21,7 +21,7 @@ public:
SLANG_NO_THROW void* SLANG_MCALL castAs(const Guid& guid) SLANG_OVERRIDE;
// IArtifactHandler
- SLANG_NO_THROW SlangResult SLANG_MCALL expandChildren(IArtifactContainer* container) SLANG_OVERRIDE;
+ SLANG_NO_THROW SlangResult SLANG_MCALL expandChildren(IArtifact* container) SLANG_OVERRIDE;
SLANG_NO_THROW SlangResult SLANG_MCALL getOrCreateRepresentation(IArtifact* artifact, const Guid& guid, ArtifactKeep keep, ICastable** outCastable) SLANG_OVERRIDE;
static IArtifactHandler* getSingleton() { return &g_singleton; }
diff --git a/source/compiler-core/slang-artifact-helper.cpp b/source/compiler-core/slang-artifact-helper.cpp
index c3b007d28..7f1bf1ea2 100644
--- a/source/compiler-core/slang-artifact-helper.cpp
+++ b/source/compiler-core/slang-artifact-helper.cpp
@@ -9,8 +9,7 @@
#include "../compiler-core/slang-slice-allocator.h"
-#include "../core/slang-castable-list-impl.h"
-#include "../core/slang-castable-util.h"
+#include "../core/slang-castable.h"
#include "../core/slang-file-system.h"
#include "../core/slang-io.h"
@@ -66,15 +65,6 @@ SlangResult DefaultArtifactHelper::createArtifact(const ArtifactDesc& desc, cons
return SLANG_OK;
}
-SlangResult DefaultArtifactHelper::createArtifactContainer(const ArtifactDesc& desc, const char* inName, IArtifactContainer** outArtifactContainer)
-{
- *outArtifactContainer = inName ?
- ArtifactContainer::create(desc, UnownedStringSlice(inName)).detach() :
- ArtifactContainer::create(desc).detach();
-
- return SLANG_OK;
-}
-
ArtifactKind DefaultArtifactHelper::getKindParent(ArtifactKind kind) { return getParent(kind); }
UnownedStringSlice DefaultArtifactHelper::getKindName(ArtifactKind kind) { return getName(kind); }
bool DefaultArtifactHelper::isKindDerivedFrom(ArtifactKind kind, ArtifactKind base) { return isDerivedFrom(kind, base); }
@@ -124,19 +114,6 @@ void DefaultArtifactHelper::getCastable(ISlangUnknown* unk, ICastable** outCasta
*outCastable = CastableUtil::getCastable(unk).detach();
}
-SlangResult DefaultArtifactHelper::createCastableList(const Guid& guid, ICastableList** outList)
-{
- auto list = new CastableList;
- if (auto ptr = list->getInterface(guid))
- {
- list->addRef();
- *outList = (ICastableList*)ptr;
- return SLANG_OK;
- }
- delete list;
- return SLANG_E_NO_INTERFACE;
-}
-
SlangResult DefaultArtifactHelper::createOSFileArtifactRepresentation(
IOSFileArtifactRepresentation::Kind kind, const CharSlice& path, IOSFileArtifactRepresentation* lockFile, IOSFileArtifactRepresentation** outRep)
{
diff --git a/source/compiler-core/slang-artifact-helper.h b/source/compiler-core/slang-artifact-helper.h
index e14a67d7c..a0d4d6b75 100644
--- a/source/compiler-core/slang-artifact-helper.h
+++ b/source/compiler-core/slang-artifact-helper.h
@@ -16,9 +16,7 @@ class IArtifactHelper : public ICastable
/// Create an artifact
virtual SLANG_NO_THROW SlangResult SLANG_MCALL createArtifact(const ArtifactDesc& desc, const char* name, IArtifact** outArtifact) = 0;
- /// Create a container with desc, and specified name. name can be passed as nullptr for no name
- virtual SLANG_NO_THROW SlangResult SLANG_MCALL createArtifactContainer(const ArtifactDesc& desc, const char* name, IArtifactContainer** outArtifactContainer) = 0;
-
+
/// Get the parent to a kind
virtual SLANG_NO_THROW ArtifactKind SLANG_MCALL getKindParent(ArtifactKind kind) = 0;
/// Get the name of a kind
@@ -61,10 +59,6 @@ class IArtifactHelper : public ICastable
virtual SLANG_NO_THROW SlangResult SLANG_MCALL createExtFileArtifactRepresentation(const CharSlice& path, ISlangFileSystemExt* system, IExtFileArtifactRepresentation** outRep) = 0;
- /// Create an empty ICastableList
- virtual SLANG_NO_THROW SlangResult SLANG_MCALL createCastableList(const Guid& guid, ICastableList** outList) = 0;
-
-
virtual SLANG_NO_THROW SlangResult SLANG_MCALL createOSFileArtifact(const ArtifactDesc& desc, const CharSlice& slice, IArtifact** outArtifact) = 0;
};
@@ -81,8 +75,7 @@ public:
// IArtifactHelper
virtual SLANG_NO_THROW SlangResult SLANG_MCALL createArtifact(const ArtifactDesc& desc, const char* name, IArtifact** outArtifact) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW SlangResult SLANG_MCALL createArtifactContainer(const ArtifactDesc& desc, const char* name, IArtifactContainer** outArtifactContainer) SLANG_OVERRIDE;
-
+
virtual SLANG_NO_THROW ArtifactKind SLANG_MCALL getKindParent(ArtifactKind kind) SLANG_OVERRIDE;
virtual SLANG_NO_THROW UnownedStringSlice SLANG_MCALL getKindName(ArtifactKind kind) SLANG_OVERRIDE;
virtual SLANG_NO_THROW bool SLANG_MCALL isKindDerivedFrom(ArtifactKind kind, ArtifactKind base) SLANG_OVERRIDE;
@@ -105,8 +98,6 @@ public:
virtual SLANG_NO_THROW void SLANG_MCALL getCastable(ISlangUnknown* unk, ICastable** outCastable) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW SlangResult SLANG_MCALL createCastableList(const Guid& guid, ICastableList** outList) SLANG_OVERRIDE;
-
virtual SLANG_NO_THROW SlangResult SLANG_MCALL createOSFileArtifactRepresentation(
IOSFileArtifactRepresentation::Kind kind, const CharSlice& path, IOSFileArtifactRepresentation* lockFile, IOSFileArtifactRepresentation** outRep) SLANG_OVERRIDE;
diff --git a/source/compiler-core/slang-artifact-impl.cpp b/source/compiler-core/slang-artifact-impl.cpp
index 237ea7436..9ff67603a 100644
--- a/source/compiler-core/slang-artifact-impl.cpp
+++ b/source/compiler-core/slang-artifact-impl.cpp
@@ -8,26 +8,24 @@
#include "slang-artifact-handler-impl.h"
-#include "../core/slang-castable-util.h"
+#include "slang-slice-allocator.h"
+
+#include "../core/slang-castable.h"
namespace Slang {
-static bool _checkSelf(IArtifact::FindStyle findStyle)
-{
- return Index(findStyle) <= Index(IArtifact::FindStyle::SelfOrChildren);
-}
+namespace { // anonymous
-static bool _checkChildren(IArtifact::FindStyle findStyle)
+/* Get a view as a slice of *raw* pointers */
+template <typename T>
+SLANG_FORCE_INLINE ConstArrayView<T*> _getRawView(const List<ComPtr<T>>& in)
{
- return Index(findStyle) >= Index(IArtifact::FindStyle::SelfOrChildren);
+ return makeConstArrayView((T*const*)in.getBuffer(), in.getCount());
}
-/* !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! Artifact !!!!!!!!!!!!!!!!!!!!!!!!!!! */
+} // anonymous
-IArtifactHandler* Artifact::_getHandler()
-{
- return m_handler ? m_handler : DefaultArtifactHandler::getSingleton();
-}
+/* !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! Artifact !!!!!!!!!!!!!!!!!!!!!!!!!!! */
void* Artifact::castAs(const Guid& guid)
{
@@ -55,9 +53,24 @@ void* Artifact::getObject(const Guid& uuid)
return nullptr;
}
+IArtifactHandler* Artifact::_getHandler()
+{
+ return m_handler ? m_handler : DefaultArtifactHandler::getSingleton();
+}
+
+void Artifact::_requireChildren()
+{
+ if (m_expandResult == SLANG_E_UNINITIALIZED)
+ {
+ const auto res = expandChildren();
+ SLANG_UNUSED(res);
+ SLANG_ASSERT(SLANG_SUCCEEDED(res));
+ }
+}
+
bool Artifact::exists()
{
- for (auto rep : m_representations.getView())
+ for (ICastable* rep : m_representations.getArrayView())
{
if (auto artifactRep = as<IArtifactRepresentation>(rep))
{
@@ -115,6 +128,28 @@ void Artifact::setHandler(IArtifactHandler* handler)
m_handler = handler;
}
+void Artifact::clear(IArtifact::ContainedKind kind)
+{
+ switch (kind)
+ {
+ case ContainedKind::Associated: m_associated.clear(); break;
+ case ContainedKind::Representation: m_representations.clear(); break;
+ case ContainedKind::Children: m_children.clear(); break;
+ default: break;
+ }
+}
+
+void Artifact::removeAt(ContainedKind kind, Index i)
+{
+ switch (kind)
+ {
+ case ContainedKind::Associated: m_associated.removeAt(i); break;
+ case ContainedKind::Representation: m_representations.removeAt(i); break;
+ case ContainedKind::Children: m_children.removeAt(i); break;
+ default: break;
+ }
+}
+
SlangResult Artifact::getOrCreateRepresentation(const Guid& typeGuid, ArtifactKeep keep, ICastable** outCastable)
{
auto handler = _getHandler();
@@ -135,52 +170,87 @@ SlangResult Artifact::loadBlob(Keep keep, ISlangBlob** outBlob)
return SLANG_OK;
}
-void Artifact::addAssociated(ICastable* castable)
+void Artifact::addAssociated(IArtifact* artifact)
{
- SLANG_ASSERT(castable);
- m_associated.add(castable);
+ SLANG_ASSERT(artifact);
+ m_associated.add(ComPtr<IArtifact>(artifact));
}
-
-void* Artifact::findAssociated(const Guid& guid)
+
+static void* _findRepresentation(const ConstArrayView<ICastable*>& castables, const Guid& guid)
{
- return m_associated.find(guid);
+ for (const auto& cur : castables)
+ {
+ if (auto ptr = cur->castAs(guid))
+ {
+ return ptr;
+ }
+ }
+ return nullptr;
}
+static void* _findRepresentation(const ConstArrayView<IArtifact*>& artifacts, const Guid& guid)
+{
+ for (auto child : artifacts)
+ {
+ if (auto rep = child->findRepresentation(Artifact::ContainedKind::Representation, guid))
+ {
+ return rep;
+ }
+ }
+ return nullptr;
+}
-ICastable* Artifact::findAssociatedWithPredicate(ICastableList::FindFunc findFunc, void* data)
+void* Artifact::findRepresentation(ContainedKind kind, const Guid& guid)
{
- return m_associated.findWithPredicate(findFunc, data);
+ switch (kind)
+ {
+ case ContainedKind::Associated: return _findRepresentation(_getRawView(m_associated), guid);
+ case ContainedKind::Representation: return _findRepresentation(_getRawView(m_representations), guid);
+ case ContainedKind::Children:
+ {
+ _requireChildren();
+ return _findRepresentation(_getRawView(m_children), guid);
+ }
+ }
+ return nullptr;
}
-ICastableList* Artifact::getAssociated()
+Slice<IArtifact*> Artifact::getAssociated()
{
- return m_associated.requireList();
+ return SliceUtil::asSlice(m_associated);
}
void Artifact::addRepresentation(ICastable* castable)
{
SLANG_ASSERT(castable);
- if (m_representations.indexOf(castable) >= 0)
+
+ auto view = _getRawView(m_representations);
+ if (view.indexOf(castable) >= 0)
{
SLANG_ASSERT_FAILURE("Already have this representation");
return;
}
- m_representations.add(castable);
+
+ m_representations.add(ComPtr<ICastable>(castable));
}
void Artifact::addRepresentationUnknown(ISlangUnknown* unk)
{
SLANG_ASSERT(unk);
- if (m_representations.indexOfUnknown(unk) >= 0)
+
{
- SLANG_ASSERT_FAILURE("Already have this representation");
- return;
+ const auto view = makeConstArrayView((ISlangUnknown*const*)m_representations.getBuffer(), m_representations.getCount());
+ if (view.indexOf(unk) >= 0)
+ {
+ SLANG_ASSERT_FAILURE("Already have this representation");
+ return;
+ }
}
ComPtr<ICastable> castable;
if (SLANG_SUCCEEDED(unk->queryInterface(SLANG_IID_PPV_ARGS(castable.writeRef()))) && castable)
{
- if (m_representations.indexOf(castable) >= 0)
+ if (_getRawView(m_representations).indexOf(castable) >= 0)
{
SLANG_ASSERT_FAILURE("Already have this representation");
return;
@@ -190,81 +260,16 @@ void Artifact::addRepresentationUnknown(ISlangUnknown* unk)
else
{
UnknownCastableAdapter* adapter = new UnknownCastableAdapter(unk);
- m_representations.add(adapter);
+ m_representations.add(ComPtr<ICastable>(adapter));
}
}
-void* Artifact::findRepresentation(const Guid& guid)
-{
- return m_representations.find(guid);
-}
-
-ICastable* Artifact::findRepresentationWithPredicate(ICastableList::FindFunc findFunc, void* data)
-{
- return m_representations.findWithPredicate(findFunc, data);
-}
-
Slice<ICastable*> Artifact::getRepresentations()
{
- const auto view = m_representations.getView();
- return Slice<ICastable*>(view.getBuffer(), view.getCount());
-}
-
-ICastableList* Artifact::getRepresentationList()
-{
- return m_representations.requireList();
-}
-
-IArtifact* Artifact::findArtifactByDerivedDesc(FindStyle findStyle, const ArtifactDesc& from)
-{
- return (_checkSelf(findStyle) && ArtifactDescUtil::isDescDerivedFrom(m_desc, from)) ? this : nullptr;
-}
-
-IArtifact* Artifact::findArtifactByPredicate(FindStyle findStyle, FindFunc func, void* data)
-{
- return (_checkSelf(findStyle) && func(this, data)) ? this : nullptr;
-}
-
-IArtifact* Artifact::findArtifactByName(FindStyle findStyle, const char* name)
-{
- return (_checkSelf(findStyle) && m_name == name) ? this : nullptr;
+ return SliceUtil::asSlice(m_representations);
}
-IArtifact* Artifact::findArtifactByDesc(FindStyle findStyle, const ArtifactDesc& desc)
-{
- return (_checkSelf(findStyle) && m_desc == desc) ? this : nullptr;
-}
-
-/* !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! ArtifactContainer !!!!!!!!!!!!!!!!!!!!!!!!!!! */
-
-void* ArtifactContainer::getInterface(const Guid& guid)
-{
- if (guid == ISlangUnknown::getTypeGuid() ||
- guid == ICastable::getTypeGuid() ||
- guid == IArtifact::getTypeGuid() ||
- guid == IArtifactContainer::getTypeGuid())
- {
- return static_cast<IArtifactContainer*>(this);
- }
- return nullptr;
-}
-
-void* ArtifactContainer::getObject(const Guid& guid)
-{
- SLANG_UNUSED(guid);
- return nullptr;
-}
-
-void* ArtifactContainer::castAs(const Guid& guid)
-{
- if (auto ptr = getInterface(guid))
- {
- return ptr;
- }
- return getObject(guid);
-}
-
-void ArtifactContainer::setChildren(IArtifact** children, Count count)
+void Artifact::setChildren(IArtifact*const* children, Count count)
{
m_expandResult = SLANG_OK;
@@ -278,117 +283,26 @@ void ArtifactContainer::setChildren(IArtifact** children, Count count)
}
}
-SlangResult ArtifactContainer::expandChildren()
+SlangResult Artifact::expandChildren()
{
auto handler = _getHandler();
return handler->expandChildren(this);
}
-Slice<IArtifact*> ArtifactContainer::getChildren()
+Slice<IArtifact*> Artifact::getChildren()
{
_requireChildren();
-
- return Slice<IArtifact*>((IArtifact**)m_children.getBuffer(), m_children.getCount());
+ return SliceUtil::asSlice(m_children);
}
-void ArtifactContainer::addChild(IArtifact* artifact)
+void Artifact::addChild(IArtifact* artifact)
{
SLANG_ASSERT(artifact);
- SLANG_ASSERT(m_children.indexOf(artifact) < 0);
+ SLANG_ASSERT(_getRawView(m_children).indexOf(artifact) < 0);
_requireChildren();
m_children.add(ComPtr<IArtifact>(artifact));
}
-void ArtifactContainer::removeChildAt(Index index)
-{
- _requireChildren();
-
- m_children.removeAt(index);
-}
-
-void ArtifactContainer::clearChildren()
-{
- _requireChildren();
-
- m_children.clearAndDeallocate();
-}
-
-static bool _isDerivedDesc(IArtifact* artifact, void* data)
-{
- const ArtifactDesc& from = *(const ArtifactDesc*)data;
- return ArtifactDescUtil::isDescDerivedFrom(artifact->getDesc(), from);
-}
-
-static bool _isDesc(IArtifact* artifact, void* data)
-{
- const ArtifactDesc& desc = *(const ArtifactDesc*)data;
- return desc == artifact->getDesc();
-}
-
-static bool _isName(IArtifact* artifact, void* data)
-{
- const char* name = (const char*)data;
- const char* artifactName = artifact->getName();
- if (artifactName == nullptr)
- {
- return false;
- }
- return ::strcmp(name, artifactName) == 0;
-}
-
-
-IArtifact* ArtifactContainer::findArtifactByDerivedDesc(FindStyle findStyle, const ArtifactDesc& from)
-{
- return findArtifactByPredicate(findStyle, _isDerivedDesc, const_cast<ArtifactDesc*>(&from));
-}
-
-IArtifact* ArtifactContainer::findArtifactByName(FindStyle findStyle, const char* name)
-{
- return findArtifactByPredicate(findStyle, _isName, const_cast<char*>(name));
-}
-
-IArtifact* ArtifactContainer::findArtifactByDesc(FindStyle findStyle, const ArtifactDesc& desc)
-{
- return findArtifactByPredicate(findStyle, _isDesc, const_cast<ArtifactDesc*>(&desc));
-}
-
-IArtifact* ArtifactContainer::findArtifactByPredicate(FindStyle findStyle, FindFunc func, void* data)
-{
- if (_checkSelf(findStyle) && func(this, data))
- {
- return this;
- }
-
- if (_checkChildren(findStyle))
- {
- auto children = getChildren();
-
- // First search the children
- for (auto child : children)
- {
- if (func(child, data))
- {
- return child;
- }
- }
-
- // Then the childrens recursively
- if (findStyle == FindStyle::Recursive ||
- findStyle == FindStyle::ChildrenRecursive)
- {
- for (auto child : children)
- {
- if (auto found = child->findArtifactByPredicate(FindStyle::ChildrenRecursive, func, data))
- {
- return found;
- }
- }
- }
- }
-
- return nullptr;
-}
-
} // namespace Slang
diff --git a/source/compiler-core/slang-artifact-impl.h b/source/compiler-core/slang-artifact-impl.h
index b59c700d8..4862142a8 100644
--- a/source/compiler-core/slang-artifact-impl.h
+++ b/source/compiler-core/slang-artifact-impl.h
@@ -4,8 +4,6 @@
#include "slang-artifact.h"
-#include "../core/slang-lazy-castable-list.h"
-
#include "../../slang-com-helper.h"
#include "../../slang-com-ptr.h"
@@ -26,13 +24,10 @@ as the main structure. Within this it can contain kernels, and then a json manif
This all 'works', in that we can add an element of ISlangFileSystem with a desc of Container. Code that uses this can then go through the process
of finding, and getting the blob, and find from the manifest what it means. That does sound a little tedious though. Perhaps we just have an interface
that handles this detail, such that we search for that first. That interface is just attached to the artifact as an element.
-
-Note: Implementation of the IArtifact interface. We derive from IArtifactContainer, such that we don't have the
-irritating multiple inheritance issue. */
-class Artifact : public ComBaseObject, public IArtifactContainer
+*/
+class Artifact : public ComBaseObject, public IArtifact
{
public:
-
SLANG_COM_BASE_IUNKNOWN_ALL
/// ICastable
@@ -49,36 +44,26 @@ public:
virtual SLANG_NO_THROW const char* SLANG_MCALL getName() SLANG_OVERRIDE { return m_name.getBuffer(); }
virtual SLANG_NO_THROW void SLANG_MCALL setName(const char* name) SLANG_OVERRIDE { m_name = name; }
- virtual SLANG_NO_THROW void SLANG_MCALL addAssociated(ICastable* castable) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW void* SLANG_MCALL findAssociated(const Guid& unk) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW ICastableList* SLANG_MCALL getAssociated() SLANG_OVERRIDE;
- virtual SLANG_NO_THROW ICastable* SLANG_MCALL findAssociatedWithPredicate(ICastableList::FindFunc findFunc, void* data) SLANG_OVERRIDE;
-
+ virtual SLANG_NO_THROW void SLANG_MCALL addAssociated(IArtifact* artifact) SLANG_OVERRIDE;
+ virtual SLANG_NO_THROW Slice<IArtifact*> SLANG_MCALL getAssociated() SLANG_OVERRIDE;
+
virtual SLANG_NO_THROW void SLANG_MCALL addRepresentation(ICastable* castable) SLANG_OVERRIDE;
virtual SLANG_NO_THROW void SLANG_MCALL addRepresentationUnknown(ISlangUnknown* rep) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW void* SLANG_MCALL findRepresentation(const Guid& guid) SLANG_OVERRIDE;
virtual SLANG_NO_THROW Slice<ICastable*> SLANG_MCALL getRepresentations() SLANG_OVERRIDE;
- virtual SLANG_NO_THROW ICastableList* SLANG_MCALL getRepresentationList() SLANG_OVERRIDE;
- virtual SLANG_NO_THROW ICastable* SLANG_MCALL findRepresentationWithPredicate(ICastableList::FindFunc findFunc, void* data) SLANG_OVERRIDE;
virtual SLANG_NO_THROW SlangResult SLANG_MCALL getOrCreateRepresentation(const Guid& typeGuid, ArtifactKeep keep, ICastable** outCastable) SLANG_OVERRIDE;
virtual SLANG_NO_THROW IArtifactHandler* SLANG_MCALL getHandler() SLANG_OVERRIDE;
virtual SLANG_NO_THROW void SLANG_MCALL setHandler(IArtifactHandler* handler) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW Slice<IArtifact*> SLANG_MCALL getChildren() SLANG_OVERRIDE { return Slice<IArtifact*>(nullptr, 0); }
-
- virtual SLANG_NO_THROW IArtifact* SLANG_MCALL findArtifactByDerivedDesc(FindStyle findStyle, const ArtifactDesc& desc) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW IArtifact* SLANG_MCALL findArtifactByPredicate(FindStyle findStyle, FindFunc func, void* data) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW IArtifact* SLANG_MCALL findArtifactByName(FindStyle findStyle, const char* name) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW IArtifact* SLANG_MCALL findArtifactByDesc(FindStyle findStyle, const ArtifactDesc& desc) SLANG_OVERRIDE;
+ virtual SLANG_NO_THROW Slice<IArtifact*> SLANG_MCALL getChildren() SLANG_OVERRIDE;
+ virtual SLANG_NO_THROW SlangResult SLANG_MCALL getExpandChildrenResult() SLANG_OVERRIDE { return m_expandResult; }
+ virtual SLANG_NO_THROW void SLANG_MCALL setChildren(IArtifact*const* children, Count count) SLANG_OVERRIDE;
+ virtual SLANG_NO_THROW SlangResult SLANG_MCALL expandChildren() SLANG_OVERRIDE;
+ virtual SLANG_NO_THROW void SLANG_MCALL addChild(IArtifact* artifact) SLANG_OVERRIDE;
- // IArtifactCollection (Not implemented)
- virtual SLANG_NO_THROW SlangResult SLANG_MCALL getExpandChildrenResult() SLANG_OVERRIDE { SLANG_UNREACHABLE("Not implemented"); }
- virtual SLANG_NO_THROW void SLANG_MCALL setChildren(IArtifact** children, Count count) SLANG_OVERRIDE { SLANG_UNUSED(children); SLANG_UNUSED(count); SLANG_UNREACHABLE("Not implemented"); }
- virtual SLANG_NO_THROW SlangResult SLANG_MCALL expandChildren() SLANG_OVERRIDE { SLANG_UNREACHABLE("Not implemented"); }
- virtual SLANG_NO_THROW void SLANG_MCALL addChild(IArtifact* artifact) SLANG_OVERRIDE { SLANG_UNUSED(artifact); SLANG_UNREACHABLE("Not implemented"); }
- virtual SLANG_NO_THROW void SLANG_MCALL removeChildAt(Index index) SLANG_OVERRIDE { SLANG_UNUSED(index); SLANG_UNREACHABLE("Not implemented"); }
- virtual SLANG_NO_THROW void SLANG_MCALL clearChildren() SLANG_OVERRIDE { SLANG_UNREACHABLE("Not implemented"); }
+ virtual SLANG_NO_THROW void* SLANG_MCALL findRepresentation(ContainedKind kind, const Guid& unk) SLANG_OVERRIDE;
+ virtual SLANG_NO_THROW void SLANG_MCALL clear(ContainedKind kind) SLANG_OVERRIDE;
+ virtual SLANG_NO_THROW void SLANG_MCALL removeAt(ContainedKind kind, Index i) SLANG_OVERRIDE;
static ComPtr<IArtifact> create(const Desc& desc) { return ComPtr<IArtifact>(new Artifact(desc)); }
static ComPtr<IArtifact> create(const Desc& desc, const UnownedStringSlice& name) { return ComPtr<IArtifact>(new Artifact(desc, name)); }
@@ -88,77 +73,27 @@ protected:
/// Ctor
Artifact(const Desc& desc, const UnownedStringSlice& name) :
m_desc(desc),
- m_name(name),
- m_parent(nullptr)
+ m_name(name)
{}
Artifact(const Desc& desc) :
- m_desc(desc),
- m_parent(nullptr)
+ m_desc(desc)
{}
IArtifactHandler* _getHandler();
+ void _requireChildren();
void* getInterface(const Guid& uuid);
void* getObject(const Guid& uuid);
Desc m_desc; ///< Description of the artifact
- IArtifact* m_parent; ///< Artifact this artifact belongs to
-
String m_name; ///< Name of this artifact
-
- ComPtr<IArtifactHandler> m_handler; ///< The handler. Can be nullptr and then default handler is used.
-
- LazyCastableList m_associated; ///< Associated items
- LazyCastableList m_representations; ///< Representations
-};
-
-class ArtifactContainer : public Artifact
-{
-public:
- typedef Artifact Super;
- SLANG_COM_BASE_IUNKNOWN_QUERY_INTERFACE
-
- /// ICastable
- virtual SLANG_NO_THROW void* SLANG_MCALL castAs(const Guid& guid) SLANG_OVERRIDE;
-
- /// IArtifact
- virtual SLANG_NO_THROW Slice<IArtifact*> SLANG_MCALL getChildren() SLANG_OVERRIDE;
- virtual SLANG_NO_THROW IArtifact* SLANG_MCALL findArtifactByDerivedDesc(FindStyle findStyle, const ArtifactDesc& desc) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW IArtifact* SLANG_MCALL findArtifactByPredicate(FindStyle findStyle, FindFunc func, void* data) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW IArtifact* SLANG_MCALL findArtifactByName(FindStyle findStyle, const char* name) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW IArtifact* SLANG_MCALL findArtifactByDesc(FindStyle findStyle, const ArtifactDesc& desc) SLANG_OVERRIDE;
-
- // IArtifactCollection
- virtual SLANG_NO_THROW SlangResult SLANG_MCALL getExpandChildrenResult() SLANG_OVERRIDE { return m_expandResult; }
- virtual SLANG_NO_THROW void SLANG_MCALL setChildren(IArtifact** children, Count count) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW SlangResult SLANG_MCALL expandChildren() SLANG_OVERRIDE;
- virtual SLANG_NO_THROW void SLANG_MCALL addChild(IArtifact* artifact) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW void SLANG_MCALL removeChildAt(Index index) SLANG_OVERRIDE;
- virtual SLANG_NO_THROW void SLANG_MCALL clearChildren() SLANG_OVERRIDE;
-
- static ComPtr<IArtifactContainer> create(const Desc& desc) { return ComPtr<IArtifactContainer>(new ArtifactContainer(desc)); }
- static ComPtr<IArtifactContainer> create(const Desc& desc, const UnownedStringSlice& name) { return ComPtr<IArtifactContainer>(new ArtifactContainer(desc, name)); }
-
-protected:
- /// Ctor
- ArtifactContainer(const Desc& desc, const UnownedStringSlice& name) :Super(desc, name) {}
- ArtifactContainer(const Desc& desc) : Super(desc) {}
-
- void* getInterface(const Guid& uuid);
- void* getObject(const Guid& uuid);
- void _requireChildren()
- {
- if (m_expandResult == SLANG_E_UNINITIALIZED)
- {
- const auto res = expandChildren();
- SLANG_UNUSED(res);
- SLANG_ASSERT(SLANG_SUCCEEDED(res));
- }
- }
-
SlangResult m_expandResult = SLANG_E_UNINITIALIZED;
- List<ComPtr<IArtifact>> m_children;
+ ComPtr<IArtifactHandler> m_handler; ///< The handler. Can be nullptr and then default handler is used.
+
+ List<ComPtr<ICastable>> m_representations; ///< All the representation of this artifact
+ List<ComPtr<IArtifact>> m_associated; ///< All the items associated with this artifact
+ List<ComPtr<IArtifact>> m_children; ///< All the child artifacts owned
};
} // namespace Slang
diff --git a/source/compiler-core/slang-artifact-representation-impl.cpp b/source/compiler-core/slang-artifact-representation-impl.cpp
index 105402e6e..85563fe61 100644
--- a/source/compiler-core/slang-artifact-representation-impl.cpp
+++ b/source/compiler-core/slang-artifact-representation-impl.cpp
@@ -9,7 +9,7 @@
#include "slang-artifact-util.h"
-#include "../core/slang-castable-util.h"
+#include "../core/slang-castable.h"
namespace Slang {
diff --git a/source/compiler-core/slang-artifact-util.cpp b/source/compiler-core/slang-artifact-util.cpp
index 413bd5efe..1a920ff18 100644
--- a/source/compiler-core/slang-artifact-util.cpp
+++ b/source/compiler-core/slang-artifact-util.cpp
@@ -1,4 +1,4 @@
-// slang-artifact.cpp
+// slang-artifact-util.cpp
#include "slang-artifact-util.h"
#include "slang-artifact-impl.h"
@@ -6,22 +6,28 @@
#include "slang-artifact-desc-util.h"
+#include "../core/slang-castable.h"
#include "../core/slang-io.h"
namespace Slang {
-/* !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! ArtifactUtil !!!!!!!!!!!!!!!!!!!!!!!!!!! */
+static bool _checkSelf(ArtifactUtil::FindStyle findStyle)
+{
+ return Index(findStyle) <= Index(ArtifactUtil::FindStyle::SelfOrChildren);
+}
-/* static */ComPtr<IArtifactContainer> ArtifactUtil::createContainer(const ArtifactDesc& desc)
+static bool _checkChildren(ArtifactUtil::FindStyle findStyle)
{
- const auto containerDesc = ArtifactDesc::make(ArtifactKind::Container, ArtifactPayload::CompileResults, desc.style);
- return ArtifactContainer::create(containerDesc);
+ return Index(findStyle) >= Index(ArtifactUtil::FindStyle::SelfOrChildren);
}
-/* static */ComPtr<IArtifactContainer> ArtifactUtil::createResultsContainer()
+static bool _checkRecursive(ArtifactUtil::FindStyle findStyle)
{
- return ArtifactContainer::create(ArtifactDesc::make(ArtifactKind::Container, ArtifactPayload::CompileResults));
+ return findStyle == ArtifactUtil::FindStyle::Recursive ||
+ findStyle == ArtifactUtil::FindStyle::ChildrenRecursive;
}
+
+/* !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! ArtifactUtil !!!!!!!!!!!!!!!!!!!!!!!!!!! */
/* static */ComPtr<IArtifact> ArtifactUtil::createArtifact(const ArtifactDesc& desc, const char* name)
{
@@ -32,18 +38,7 @@ namespace Slang {
/* static */ComPtr<IArtifact> ArtifactUtil::createArtifact(const ArtifactDesc& desc)
{
- if (isDerivedFrom(desc.kind, ArtifactKind::Container))
- {
- auto container = ArtifactContainer::create(desc);
-
- ComPtr<IArtifact> artifact;
- artifact.attach(container.detach());
- return artifact;
- }
- else
- {
- return Artifact::create(desc);
- }
+ return Artifact::create(desc);
}
/* static */ComPtr<IArtifact> ArtifactUtil::createArtifactForCompileTarget(SlangCompileTarget target)
@@ -79,7 +74,7 @@ namespace Slang {
return true;
}
- /* Hmm, we might want to have a base class for 'signifiant' payloads,
+ /* Hmm, we might want to have a base class for 'significant' payloads,
where signifiance here means somewhat approximately 'the meat' of a compilation result,
as contrasted with 'meta data', 'diagnostics etc'*/
if (isDerivedFrom(desc.payload, ArtifactPayload::Metadata))
@@ -92,7 +87,7 @@ namespace Slang {
/* static */IArtifact* ArtifactUtil::findSignificant(IArtifact* artifact)
{
- return artifact->findArtifactByPredicate(IArtifact::FindStyle::SelfOrChildren, &ArtifactUtil::isSignificant, nullptr);
+ return findArtifactByPredicate(artifact, FindStyle::SelfOrChildren, &ArtifactUtil::isSignificant, nullptr);
}
UnownedStringSlice ArtifactUtil::findPath(IArtifact* artifact)
@@ -190,4 +185,108 @@ static SlangResult _calcInferred(IArtifact* artifact, const UnownedStringSlice&
}
}
+static bool _isByDerivedDesc(IArtifact* artifact, void* data)
+{
+ const ArtifactDesc& desc = *(const ArtifactDesc*)data;
+ return ArtifactDescUtil::isDescDerivedFrom(artifact->getDesc(), desc);
+}
+
+static bool _isDesc(IArtifact* artifact, void* data)
+{
+ const ArtifactDesc& desc = *(const ArtifactDesc*)data;
+ return artifact->getDesc() == desc;
+}
+
+static bool _isName(IArtifact* artifact, void* data)
+{
+ const char* name = (const char*)data;
+ const auto artifactName = artifact->getName();
+
+ if (name == nullptr || artifactName == nullptr)
+ {
+ return name == artifactName;
+ }
+ return ::strcmp(name, artifactName) == 0;
+}
+
+/* static */IArtifact* ArtifactUtil::findArtifactByDerivedDesc(IArtifact* artifact, FindStyle findStyle, const ArtifactDesc& desc)
+{
+ return findArtifactByPredicate(artifact, findStyle, _isByDerivedDesc, &const_cast<ArtifactDesc&>(desc));
+}
+
+/* static */IArtifact* ArtifactUtil::findArtifactByName(IArtifact* artifact, FindStyle findStyle, const char* name)
+{
+ return findArtifactByPredicate(artifact, findStyle, _isName, const_cast<char*>(name));
+}
+
+/* static */IArtifact* ArtifactUtil::findArtifactByDesc(IArtifact* artifact, FindStyle findStyle, const ArtifactDesc& desc)
+{
+ return findArtifactByPredicate(artifact, findStyle, _isDesc, &const_cast<ArtifactDesc&>(desc));
+}
+
+/* static */IArtifact* ArtifactUtil::findArtifactByPredicate(IArtifact* artifact, FindStyle findStyle, FindFunc func, void* data)
+{
+ if (_checkSelf(findStyle) && func(artifact, data))
+ {
+ return artifact;
+ }
+
+ if (!_checkChildren(findStyle))
+ {
+ return nullptr;
+ }
+
+ // Expand the children so we can search them
+ artifact->expandChildren();
+
+ auto children = artifact->getChildren();
+ if (children.count == 0)
+ {
+ return nullptr;
+ }
+
+ // Check the children
+ for (auto child : children)
+ {
+ if (func(child, data))
+ {
+ return child;
+ }
+ }
+
+ // If it's recursive, we check all the children of children
+ if (_checkRecursive(findStyle))
+ {
+ for (auto child : children)
+ {
+ if (auto found = findArtifactByPredicate(child, FindStyle::ChildrenRecursive, func, data))
+ {
+ return found;
+ }
+ }
+ }
+
+ return nullptr;
+}
+
+/* static */void ArtifactUtil::addAssociated(IArtifact* artifact, IArtifactPostEmitMetadata* metadata)
+{
+ if (metadata)
+ {
+ auto metadataArtifact = ArtifactUtil::createArtifact(ArtifactDesc::make(ArtifactKind::Instance, ArtifactPayload::PostEmitMetadata));
+ metadataArtifact->addRepresentation(metadata);
+ artifact->addAssociated(metadataArtifact);
+ }
+}
+
+/* static */void ArtifactUtil::addAssociated(IArtifact* artifact, IArtifactDiagnostics* diagnostics)
+{
+ if (diagnostics)
+ {
+ auto diagnosticsArtifact = ArtifactUtil::createArtifact(ArtifactDesc::make(ArtifactKind::Instance, ArtifactPayload::Diagnostics));
+ diagnosticsArtifact->addRepresentation(diagnostics);
+ artifact->addAssociated(diagnosticsArtifact);
+ }
+}
+
} // namespace Slang
diff --git a/source/compiler-core/slang-artifact-util.h b/source/compiler-core/slang-artifact-util.h
index 70b736828..78f6da7a9 100644
--- a/source/compiler-core/slang-artifact-util.h
+++ b/source/compiler-core/slang-artifact-util.h
@@ -4,17 +4,34 @@
#include "slang-artifact.h"
#include "slang-artifact-representation.h"
+#include "slang-artifact-associated.h"
+
+#include "../../slang-com-ptr.h"
namespace Slang
{
struct ArtifactUtil
{
- /// Create an empty container which is compatible with the desc
- static ComPtr<IArtifactContainer> createContainer(const ArtifactDesc& desc);
+ typedef bool (*FindFunc)(IArtifact* artifact, void* data);
+
+ enum class FindStyle : uint8_t
+ {
+ Self, ///< Just on self
+ SelfOrChildren, ///< Self, or if container just the children
+ Recursive, ///< On self plus any children recursively
+ Children, ///< Only on children
+ ChildrenRecursive, ///< Only on children recursively
+ };
- /// Create a generic container
- static ComPtr<IArtifactContainer> createResultsContainer();
+ /// Find an artifact that matches desc allowing derivations. Flags is ignored
+ static IArtifact* findArtifactByDerivedDesc(IArtifact* artifact, FindStyle findStyle, const ArtifactDesc& desc);
+ /// Find an artifact that predicate matches
+ static IArtifact* findArtifactByPredicate(IArtifact* artifact, FindStyle findStyle, FindFunc func, void* data);
+ /// Find by name
+ static IArtifact* findArtifactByName(IArtifact* artifact, FindStyle findStyle, const char* name);
+ /// Find by desc exactly
+ static IArtifact* findArtifactByDesc(IArtifact* artifact, FindStyle findStyle, const ArtifactDesc& desc);
/// Creates an empty artifact for a type
static ComPtr<IArtifact> createArtifactForCompileTarget(SlangCompileTarget target);
@@ -46,6 +63,11 @@ struct ArtifactUtil
/// Given a desc and a baseName works out the the output file name
static SlangResult calcName(IArtifact* artifact, const UnownedStringSlice& baseName, StringBuilder& outName);
+
+ /// Convenience function that adds metadata to artifact. If metadata is nullptr nothing is added.
+ static void addAssociated(IArtifact* artifact, IArtifactPostEmitMetadata* metadata);
+ /// Convenience function that adds diagnostics to artifact. If diagnostics is nullptr nothing is added.
+ static void addAssociated(IArtifact* artifact, IArtifactDiagnostics* diagnostics);
};
} // namespace Slang
diff --git a/source/compiler-core/slang-artifact.h b/source/compiler-core/slang-artifact.h
index 65d4d1bf9..80db717d0 100644
--- a/source/compiler-core/slang-artifact.h
+++ b/source/compiler-core/slang-artifact.h
@@ -3,8 +3,7 @@
#define SLANG_ARTIFACT_H
#include "../core/slang-basic.h"
-
-#include "../core/slang-castable-list.h"
+#include "../../slang-com-helper.h"
namespace Slang
{
@@ -184,6 +183,8 @@ enum class ArtifactPayload : uint8_t
SourceMap, ///< A source map
+ PostEmitMetadata, ///< Metadata from post emit (binding information)
+
CountOf,
};
@@ -333,37 +334,29 @@ files could be a Container containing artifacts for
There are several types of ways to associate data with an artifact:
* A representation
-* Associated data
+* An associated artifact
* A child artifact
A `representation` has to wholly represent the artifact. That representation could be a blob, a file on the file system,
an in memory representation. There are two classes of `Representation` - ones that can be turned into blobs (and therefore
derive from IArtifactRepresentation) and ones that are in of themselves a representation (such as a blob or or ISlangSharedLibrary).
-`Associated data` is information that is associated with the artifact, but isn't a (whole) representation. It could be part
+`Associated artifacts` hold information that is associated with the artifact. It could be part
of the representation, or useful for the implementation of a representation. Could also be considered as a kind of side channel
-to associate arbitrary temporary data with an artifact.
-
-A `child artifact` belongs to the artifact, within the hierarchy of artifacts. Child artifacts are held in an IArtifactList.
-
-More long term goals would be to
+to associate arbitrary data including temporary data with an artifact.
-* Make Diagnostics into an interface (such it can be added to a Artifact result)
-* Use Artifact and related types for downstream compiler
+A `child artifact` belongs to the artifact, within the hierarchy of artifacts.
*/
class IArtifact : public ICastable
{
public:
- SLANG_COM_INTERFACE(0x57375e20, 0xbed, 0x42b6, { 0x9f, 0x5e, 0x59, 0x4f, 0x6, 0x2b, 0xe6, 0x90 })
+ SLANG_COM_INTERFACE(0xf90acdb0, 0x9a4a, 0x414e, { 0x85, 0x45, 0x8b, 0x26, 0xc9, 0x2d, 0x94, 0x42 })
- typedef bool (*FindFunc)(IArtifact* artifact, void* data);
- enum class FindStyle : uint8_t
+ enum class ContainedKind
{
- Self, ///< Just on self
- SelfOrChildren, ///< Self, or if container just the children
- Recursive, ///< On self plus any children recursively
- Children, ///< Only on children
- ChildrenRecursive, ///< Only on children recursively
+ Representation,
+ Associated,
+ Children,
};
typedef ArtifactDesc Desc;
@@ -372,6 +365,7 @@ public:
typedef ArtifactPayload Payload;
typedef ArtifactStyle Style;
typedef ArtifactFlags Flags;
+
typedef ArtifactKeep Keep;
/// Get the Desc defining the contents of the artifact
@@ -395,31 +389,21 @@ public:
/// Set the name associated with the artifact
virtual SLANG_NO_THROW void SLANG_MCALL setName(const char* name) = 0;
- /// Add data associated with this artifact
- virtual SLANG_NO_THROW void SLANG_MCALL addAssociated(ICastable* castable) = 0;
- /// Find an associated item
- virtual SLANG_NO_THROW void* SLANG_MCALL SLANG_MCALL findAssociated(const Guid& unk) = 0;
- /// TODO(JS): We may want this to return nullptr if it's empty.
+ /// Add associated artifacts with this artifact
+ virtual SLANG_NO_THROW void SLANG_MCALL addAssociated(IArtifact* artifact) = 0;
/// Get the list of associated items
- virtual SLANG_NO_THROW ICastableList* SLANG_MCALL getAssociated() = 0;
- /// Find first associated that matches the predicate
- virtual SLANG_NO_THROW ICastable* SLANG_MCALL findAssociatedWithPredicate(ICastableList::FindFunc findFunc, void* data) = 0;
-
+ virtual SLANG_NO_THROW Slice<IArtifact*> SLANG_MCALL getAssociated() = 0;
+
/// Add a representation
virtual SLANG_NO_THROW void SLANG_MCALL addRepresentation(ICastable* castable) = 0;
/// Add a representation that doesn't derive from IArtifactRepresentation
virtual SLANG_NO_THROW void SLANG_MCALL addRepresentationUnknown(ISlangUnknown* rep) = 0;
- /// Find representation
- virtual SLANG_NO_THROW void* SLANG_MCALL findRepresentation(const Guid& guid) = 0;
- /// Find first representation that matches the predicate
- virtual SLANG_NO_THROW ICastable* SLANG_MCALL findRepresentationWithPredicate(ICastableList::FindFunc findFunc, void* data) = 0;
/// Get all the representations
virtual SLANG_NO_THROW Slice<ICastable*> SLANG_MCALL getRepresentations() = 0;
- /// Get the list of all representations
- virtual SLANG_NO_THROW ICastableList* SLANG_MCALL getRepresentationList() = 0;
/// Given a typeGuid representing the desired type get or create the representation.
/// If found outCastable holds an entity that *must* be castable to typeGuid
+ /// Use the keep parameter to determine if the representation should be cached on the artifact/s or not.
virtual SLANG_NO_THROW SlangResult SLANG_MCALL getOrCreateRepresentation(const Guid& typeGuid, ArtifactKeep keep, ICastable** outCastable) = 0;
/// Get the handler used for this artifact. If nullptr means the default handler will be used.
@@ -427,69 +411,54 @@ public:
/// Set the handler associated with this artifact. Setting nullptr will use the default handler.
virtual SLANG_NO_THROW void SLANG_MCALL setHandler(IArtifactHandler* handler) = 0;
- /// Get the children, will only remain valid if no mutation of children list
- virtual SLANG_NO_THROW Slice<IArtifact*> SLANG_MCALL getChildren() = 0;
-
- /// Find an artifact that matches desc allowing derivations. Flags is ignored
- virtual SLANG_NO_THROW IArtifact* SLANG_MCALL findArtifactByDerivedDesc(FindStyle findStyle, const ArtifactDesc& desc) = 0;
- /// Find an artifact that predicate matches
- virtual SLANG_NO_THROW IArtifact* SLANG_MCALL findArtifactByPredicate(FindStyle findStyle, FindFunc func, void* data) = 0;
- /// Find by name
- virtual SLANG_NO_THROW IArtifact* SLANG_MCALL findArtifactByName(FindStyle findStyle, const char* name) = 0;
- /// Find by desc exactly
- virtual SLANG_NO_THROW IArtifact* SLANG_MCALL findArtifactByDesc(FindStyle findStyle, const ArtifactDesc& desc) = 0;
-};
-
-/* Interface for an artifact that *contain* a hierarchy of other child artifacts.
-
-Containment is a different concept to *association*. An association can hold any interface, and associations are for
-objects that are associated with an artifact - like diagnostics or meta data. Children artifacts can build up hierarchies
-and the children can be thought to be contained by the artifact they are a child of.
-
-The IArtifactContainer interface exists additionally to provide some type safety, and make it clear
-in code where a container or just 'an artifact' is required.
-*/
-class IArtifactContainer : public IArtifact
-{
-public:
- SLANG_COM_INTERFACE(0xa96e29bd, 0xb546, 0x4e79, { 0xa0, 0xdc, 0x67, 0x49, 0x22, 0x2c, 0x39, 0xad })
-
/// Returns the result of expansion. Will return SLANG_E_UNINITIALIZED if expansion hasn't happened
virtual SLANG_NO_THROW SlangResult SLANG_MCALL getExpandChildrenResult() = 0;
/// Sets all of the children, will set the expansion state to SLANG_OK
- virtual SLANG_NO_THROW void SLANG_MCALL setChildren(IArtifact**children, Count count) = 0;
+ virtual SLANG_NO_THROW void SLANG_MCALL setChildren(IArtifact*const* children, Count count) = 0;
/// Will be called implicitly on access to children
virtual SLANG_NO_THROW SlangResult SLANG_MCALL expandChildren() = 0;
/// Add the artifact to the list
virtual SLANG_NO_THROW void SLANG_MCALL addChild(IArtifact* artifact) = 0;
- /// Removes the child at index, keeps other artifacts in the same order
- virtual SLANG_NO_THROW void SLANG_MCALL removeChildAt(Index index) = 0;
- /// Clear the list
- virtual SLANG_NO_THROW void SLANG_MCALL clearChildren() = 0;
+ /// Get the children, will only remain valid if no mutation of children list
+ virtual SLANG_NO_THROW Slice<IArtifact*> SLANG_MCALL getChildren() = 0;
+
+ /// Find a represention from the specified list
+ virtual SLANG_NO_THROW void* SLANG_MCALL findRepresentation(ContainedKind kind, const Guid& guid) = 0;
+ /// Clear all of the contained kind
+ virtual SLANG_NO_THROW void SLANG_MCALL clear(ContainedKind kind) = 0;
+ /// Remove entry at index for the specified kind
+ virtual SLANG_NO_THROW void SLANG_MCALL removeAt(ContainedKind kind, Index i) = 0;
};
template <typename T>
SLANG_FORCE_INLINE T* findRepresentation(IArtifact* artifact)
{
- return reinterpret_cast<T*>(artifact->findRepresentation(T::getTypeGuid()));
+ return reinterpret_cast<T*>(artifact->findRepresentation(IArtifact::ContainedKind::Representation, T::getTypeGuid()));
+}
+
+template <typename T>
+SLANG_FORCE_INLINE T* findAssociatedRepresentation(IArtifact* artifact)
+{
+ return reinterpret_cast<T*>(artifact->findRepresentation(IArtifact::ContainedKind::Associated, T::getTypeGuid()));
}
template <typename T>
-SLANG_FORCE_INLINE T* findAssociated(IArtifact* artifact)
+SLANG_FORCE_INLINE T* findChildRepresentation(IArtifact* artifact)
{
- return reinterpret_cast<T*>(artifact->findAssociated(T::getTypeGuid()));
+ return reinterpret_cast<T*>(artifact->findRepresentation(IArtifact::ContainedKind::Children, T::getTypeGuid()));
}
/* The IArtifactRepresentation interface represents a single representation that can be part of an artifact. It's special in so far
as
* IArtifactRepresentation can be queried for it's underlying object class
+* Can determine if the representation exists (for example if it's on the file system)
* Can optionally serialize into a blob
*/
class IArtifactRepresentation : public ICastable
{
- SLANG_COM_INTERFACE(0x311457a8, 0x1796, 0x4ebb, { 0x9a, 0xfc, 0x46, 0xa5, 0x44, 0xc7, 0x6e, 0xa9 })
+ SLANG_COM_INTERFACE(0xa3790eb, 0x22b9, 0x430e, { 0xbf, 0xc6, 0x24, 0x6c, 0x5b, 0x5c, 0xcd, 0x0 })
/// Create a representation of the specified typeGuid interface.
/// Calling castAs on the castable will return the specific type
@@ -506,7 +475,7 @@ class IArtifactHandler : public ICastable
SLANG_COM_INTERFACE(0x6a646f57, 0xb3ac, 0x4c6a, { 0xb6, 0xf1, 0x33, 0xb6, 0xef, 0x60, 0xa6, 0xae });
/// Given an artifact expands children
- virtual SLANG_NO_THROW SlangResult SLANG_MCALL expandChildren(IArtifactContainer* container) = 0;
+ virtual SLANG_NO_THROW SlangResult SLANG_MCALL expandChildren(IArtifact* container) = 0;
/// Given an artifact gets or creates a representation.
virtual SLANG_NO_THROW SlangResult SLANG_MCALL getOrCreateRepresentation(IArtifact* artifact, const Guid& guid, ArtifactKeep keep, ICastable** outCastable) = 0;
};
diff --git a/source/compiler-core/slang-downstream-compiler.cpp b/source/compiler-core/slang-downstream-compiler.cpp
index b312f9cb8..88081ad84 100644
--- a/source/compiler-core/slang-downstream-compiler.cpp
+++ b/source/compiler-core/slang-downstream-compiler.cpp
@@ -12,7 +12,7 @@
#include "../core/slang-blob.h"
#include "../core/slang-char-util.h"
-#include "../core/slang-castable-util.h"
+#include "../core/slang-castable.h"
#include "slang-artifact-impl.h"
#include "slang-artifact-representation-impl.h"
@@ -21,8 +21,6 @@
#include "slang-artifact-helper.h"
#include "slang-artifact-desc-util.h"
-#include "../core/slang-castable-list-impl.h"
-
namespace Slang
{
@@ -83,9 +81,8 @@ SlangResult CommandLineDownstreamCompiler::compile(const CompileOptions& inOptio
const auto targetDesc = ArtifactDescUtil::makeDescForCompileTarget(options.targetType);
auto helper = DefaultArtifactHelper::getSingleton();
-
- // Holds all of the artifacts that are relatated to the final artifact - such as debug files, ancillary file and lock files
- auto artifactList = CastableList::create();
+
+ List<ComPtr<IArtifact>> artifactList;
// It may be necessary to produce a temporary file 'lock file'.
ComPtr<IOSFileArtifactRepresentation> lockFile;
@@ -103,7 +100,7 @@ SlangResult CommandLineDownstreamCompiler::compile(const CompileOptions& inOptio
auto lockArtifact = Artifact::create(ArtifactDesc::make(ArtifactKind::Base, ArtifactPayload::Lock, ArtifactStyle::None));
lockArtifact->addRepresentation(lockFile);
- artifactList->add(lockArtifact);
+ artifactList.add(lockArtifact);
// Add the source files such that they can exist
modulePath = lockFile->getPath();
@@ -129,7 +126,7 @@ SlangResult CommandLineDownstreamCompiler::compile(const CompileOptions& inOptio
productArtifact = artifact;
}
- artifactList->add(artifact);
+ artifactList.add(ComPtr<IArtifact>(artifact));
}
}
@@ -163,11 +160,12 @@ SlangResult CommandLineDownstreamCompiler::compile(const CompileOptions& inOptio
// This is useful because `calcCompileProducts` is conservative and may produce artifacts for products that aren't actually
// produced, by the compilation.
{
- Count count = artifactList->getCount();
+
+ Count count = artifactList.getCount();
for (Index i = 0; i < count; ++i)
{
- auto artifact = as<IArtifact>(artifactList->getAt(i));
-
+ IArtifact* artifact = artifactList[i];
+
if (!artifact->exists())
{
// We should find a file rep and if we do we can disown it. Disowning will mean
@@ -184,7 +182,7 @@ SlangResult CommandLineDownstreamCompiler::compile(const CompileOptions& inOptio
}
// Remove from the list
- artifactList->removeAt(i);
+ artifactList.removeAt(i);
--count;
--i;
}
@@ -199,7 +197,7 @@ SlangResult CommandLineDownstreamCompiler::compile(const CompileOptions& inOptio
// If it has a lock file we can assume it's a temporary
if (fileRep->getLockFile())
{
- artifactList->add(sourceArtifact);
+ artifactList.add(ComPtr<IArtifact>(sourceArtifact));
}
}
}
@@ -212,9 +210,8 @@ SlangResult CommandLineDownstreamCompiler::compile(const CompileOptions& inOptio
SLANG_RETURN_ON_FAIL(parseOutput(exeRes, diagnostics));
- // Add the artifact
- artifact->addAssociated(diagnostics);
-
+ ArtifactUtil::addAssociated(artifact, diagnostics);
+
// Find the rep from the 'main' artifact, we'll just use the same representation on the output
// artifact. Sharing is desirable, because the rep owns the file.
if (auto fileRep = productArtifact ? findRepresentation<IOSFileArtifactRepresentation>(productArtifact) : nullptr)
@@ -223,9 +220,16 @@ SlangResult CommandLineDownstreamCompiler::compile(const CompileOptions& inOptio
}
// Add the artifact list if there is anything in it
- if (artifactList->getCount())
+ if (artifactList.getCount())
{
- artifact->addAssociated(artifactList);
+ // Holds all of the artifacts that are relatated to the final artifact - such as debug files, ancillary file and lock files
+ auto artifactContainer = ArtifactUtil::createArtifact(ArtifactDesc::make(ArtifactKind::Container, ArtifactPayload::Unknown, ArtifactStyle::Unknown));
+
+ auto slice = SliceUtil::asSlice(artifactList);
+
+ artifactContainer->setChildren(slice.data, slice.count);
+
+ artifact->addAssociated(artifactContainer);
}
*outArtifact = artifact.detach();
diff --git a/source/compiler-core/slang-dxc-compiler.cpp b/source/compiler-core/slang-dxc-compiler.cpp
index 248d8d118..a39503b13 100644
--- a/source/compiler-core/slang-dxc-compiler.cpp
+++ b/source/compiler-core/slang-dxc-compiler.cpp
@@ -640,7 +640,9 @@ SlangResult DXCDownstreamCompiler::compile(const CompileOptions& inOptions, IArt
}
auto artifact = ArtifactUtil::createArtifactForCompileTarget(options.targetType);
- artifact->addAssociated(diagnostics);
+
+ ArtifactUtil::addAssociated(artifact, diagnostics);
+
if (dxcResultBlob)
{
artifact->addRepresentationUnknown((ISlangBlob*)dxcResultBlob.get());
diff --git a/source/compiler-core/slang-fxc-compiler.cpp b/source/compiler-core/slang-fxc-compiler.cpp
index a9e916abf..de6f5d2bc 100644
--- a/source/compiler-core/slang-fxc-compiler.cpp
+++ b/source/compiler-core/slang-fxc-compiler.cpp
@@ -329,7 +329,8 @@ SlangResult FXCDownstreamCompiler::compile(const CompileOptions& inOptions, IArt
}
auto artifact = ArtifactUtil::createArtifactForCompileTarget(options.targetType);
- artifact->addAssociated(diagnostics);
+
+ ArtifactUtil::addAssociated(artifact, diagnostics);
if (codeBlob)
{
diff --git a/source/compiler-core/slang-glslang-compiler.cpp b/source/compiler-core/slang-glslang-compiler.cpp
index 17abc469b..c1053692f 100644
--- a/source/compiler-core/slang-glslang-compiler.cpp
+++ b/source/compiler-core/slang-glslang-compiler.cpp
@@ -225,7 +225,8 @@ SlangResult GlslangDownstreamCompiler::compile(const CompileOptions& inOptions,
// Set the diagnostics result
diagnostics->setResult(invokeResult);
- artifact->addAssociated(diagnostics);
+
+ ArtifactUtil::addAssociated(artifact, diagnostics);
if (SLANG_FAILED(invokeResult))
{
diff --git a/source/compiler-core/slang-llvm-compiler.cpp b/source/compiler-core/slang-llvm-compiler.cpp
index 88446f605..3d24d3aa1 100644
--- a/source/compiler-core/slang-llvm-compiler.cpp
+++ b/source/compiler-core/slang-llvm-compiler.cpp
@@ -22,9 +22,10 @@ namespace Slang
ComPtr<IDownstreamCompiler> downstreamCompiler;
- if (auto fnV3 = (CreateDownstreamCompilerFunc)library->findFuncByName("createLLVMDownstreamCompiler_V3"))
+ // Only accept V4, so we can update IArtifact without breaking anything
+ if (auto fnV4 = (CreateDownstreamCompilerFunc)library->findFuncByName("createLLVMDownstreamCompiler_V4"))
{
- SLANG_RETURN_ON_FAIL(fnV3(IDownstreamCompiler::getTypeGuid(), downstreamCompiler.writeRef()));
+ SLANG_RETURN_ON_FAIL(fnV4(IDownstreamCompiler::getTypeGuid(), downstreamCompiler.writeRef()));
}
else
{
diff --git a/source/compiler-core/slang-nvrtc-compiler.cpp b/source/compiler-core/slang-nvrtc-compiler.cpp
index e7e90be60..cc8a72dce 100644
--- a/source/compiler-core/slang-nvrtc-compiler.cpp
+++ b/source/compiler-core/slang-nvrtc-compiler.cpp
@@ -928,7 +928,7 @@ SlangResult NVRTCDownstreamCompiler::compile(const DownstreamCompileOptions& inO
auto artifact = ArtifactUtil::createArtifactForCompileTarget(options.targetType);
auto diagnostics = ArtifactDiagnostics::create();
- artifact->addAssociated(diagnostics);
+ ArtifactUtil::addAssociated(artifact, diagnostics);
ComPtr<ISlangBlob> blob;
diff --git a/source/compiler-core/slang-slice-allocator.h b/source/compiler-core/slang-slice-allocator.h
index 984ad32eb..e4ba9e907 100644
--- a/source/compiler-core/slang-slice-allocator.h
+++ b/source/compiler-core/slang-slice-allocator.h
@@ -4,6 +4,7 @@
// Has definition of CharSlice
#include "slang-artifact.h"
+#include "../../slang-com-ptr.h"
#include "../core/slang-memory-arena.h"
diff --git a/source/core/slang-archive-file-system.cpp b/source/core/slang-archive-file-system.cpp
index 63e1c0b01..03237105d 100644
--- a/source/core/slang-archive-file-system.cpp
+++ b/source/core/slang-archive-file-system.cpp
@@ -3,14 +3,14 @@
#include "../../slang-com-helper.h"
#include "../../slang-com-ptr.h"
+#include "../core/slang-castable.h"
+
#include "slang-io.h"
#include "slang-string-util.h"
#include "slang-blob.h"
#include "slang-riff-file-system.h"
-#include "slang-destroyable.h"
-
// Compression systems
#include "slang-deflate-compression-system.h"
#include "slang-lz4-compression-system.h"
diff --git a/source/core/slang-castable-list-impl.cpp b/source/core/slang-castable-list-impl.cpp
deleted file mode 100644
index 4f4b07790..000000000
--- a/source/core/slang-castable-list-impl.cpp
+++ /dev/null
@@ -1,136 +0,0 @@
-// slang-castable-list-impl.cpp
-#include "slang-castable-list-impl.h"
-
-#include "slang-castable-util.h"
-
-namespace Slang {
-
-/* !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! CastableList !!!!!!!!!!!!!!!!!!!!!!!!!!! */
-
-CastableList::~CastableList()
-{
- for (auto castable : m_list)
- {
- castable->release();
- }
-}
-
-void* CastableList::castAs(const Guid& guid)
-{
- if (auto intf = getInterface(guid))
- {
- return intf;
- }
- return getObject(guid);
-}
-
-void* CastableList::getInterface(const Guid& guid)
-{
- if (guid == ISlangUnknown::getTypeGuid() ||
- guid == ICastable::getTypeGuid() ||
- guid == ICastableList::getTypeGuid())
- {
- return static_cast<ICastableList*>(this);
- }
- return nullptr;
-}
-
-void* CastableList::getObject(const Guid& guid)
-{
- SLANG_UNUSED(guid);
- return nullptr;
-}
-
-void* CastableList::find(const Guid& guid)
-{
- for (ICastable* castable : m_list)
- {
- if (auto ptr = castable->castAs(guid))
- {
- return ptr;
- }
- }
- return nullptr;
-}
-
-ICastable* SLANG_MCALL CastableList::findWithPredicate(FindFunc func, void* data)
-{
- for (ICastable* castable : m_list)
- {
- if (func(castable, data))
- {
- return castable;
- }
- }
- return nullptr;
-}
-
-Index CastableList::indexOf(ICastable* castable)
-{
- const Count count = m_list.getCount();
- for (Index i = 0; i < count; ++i)
- {
- ICastable* cur = m_list[i];
- if (cur == castable)
- {
- return i;
- }
- }
- return -1;
-}
-
-void CastableList::add(ICastable* castable)
-{
- SLANG_ASSERT(castable);
- castable->addRef();
- m_list.add(castable);
-}
-
-void CastableList::removeAt(Index i)
-{
- auto castable = m_list[i];
- m_list.removeAt(i);
- castable->release();
-}
-
-void CastableList::clear()
-{
- for (auto castable : m_list)
- {
- castable->release();
- }
- m_list.clear();
-}
-
-void CastableList::addUnknown(ISlangUnknown* unk)
-{
- add(CastableUtil::getCastable(unk));
-}
-
-Index CastableList::indexOfUnknown(ISlangUnknown* unk)
-{
- SLANG_ASSERT(unk);
- // If it has a castable interface we can just look for that
- {
- ComPtr<ICastable> castable;
- if (SLANG_SUCCEEDED(unk->queryInterface(SLANG_IID_PPV_ARGS(castable.writeRef()))) && castable)
- {
- return indexOf(castable);
- }
- }
-
- // It's not derived from ICastable, so can only be in list via an adapter
- const Count count = m_list.getCount();
- for (Index i = 0; i < count; ++i)
- {
- auto adapter = as<IUnknownCastableAdapter>(m_list[i]);
- if (adapter && adapter->getContained() == unk)
- {
- return i;
- }
- }
-
- return -1;
-}
-
-} // namespace Slang
diff --git a/source/core/slang-castable-list-impl.h b/source/core/slang-castable-list-impl.h
deleted file mode 100644
index adbd121fb..000000000
--- a/source/core/slang-castable-list-impl.h
+++ /dev/null
@@ -1,53 +0,0 @@
-// slang-castable-list-impl.h
-#ifndef SLANG_CASTABLE_LIST_IMPL_H
-#define SLANG_CASTABLE_LIST_IMPL_H
-
-#include "slang-castable-list.h"
-
-#include "../../slang-com-helper.h"
-#include "../../slang-com-ptr.h"
-
-#include "../core/slang-com-object.h"
-
-namespace Slang
-{
-
-/* Implementation of the ICastableList interface.
-Is atomic reference counted */
-class CastableList : public ComBaseObject, public ICastableList
-{
-public:
- SLANG_COM_BASE_IUNKNOWN_ALL
-
- // ICastable
- SLANG_NO_THROW void* SLANG_MCALL castAs(const Guid& guid) SLANG_OVERRIDE;
-
- // ICastableList
- virtual Count SLANG_MCALL getCount() SLANG_OVERRIDE { return m_list.getCount(); }
- virtual ICastable* SLANG_MCALL getAt(Index i) SLANG_OVERRIDE { return m_list[i]; }
- virtual void SLANG_MCALL add(ICastable* castable) SLANG_OVERRIDE;
- virtual void SLANG_MCALL addUnknown(ISlangUnknown* unk) SLANG_OVERRIDE;
- virtual void SLANG_MCALL removeAt(Index i) SLANG_OVERRIDE;
- virtual void SLANG_MCALL clear() SLANG_OVERRIDE;
- virtual Index SLANG_MCALL indexOf(ICastable* castable) SLANG_OVERRIDE;
- virtual Index SLANG_MCALL indexOfUnknown(ISlangUnknown* unk) SLANG_OVERRIDE;
- virtual void* SLANG_MCALL find(const Guid& guid) SLANG_OVERRIDE;
- virtual ICastable* SLANG_MCALL findWithPredicate(FindFunc func, void* data) SLANG_OVERRIDE;
- virtual ICastable*const* SLANG_MCALL getBuffer() SLANG_OVERRIDE { return m_list.getBuffer(); }
-
- static ComPtr<ICastableList> create() { return ComPtr<ICastableList>(new CastableList); }
-
- /// Dtor
- virtual ~CastableList();
-
- void* getInterface(const Guid& guid);
- void* getObject(const Guid& guid);
-
-protected:
-
- List<ICastable*> m_list;
-};
-
-} // namespace Slang
-
-#endif
diff --git a/source/core/slang-castable-list.h b/source/core/slang-castable-list.h
deleted file mode 100644
index b9c98d65a..000000000
--- a/source/core/slang-castable-list.h
+++ /dev/null
@@ -1,68 +0,0 @@
-// slang-castable-list.h
-#ifndef SLANG_CASTABLE_LIST_H
-#define SLANG_CASTABLE_LIST_H
-
-#include "../core/slang-basic.h"
-
-#include "../core/slang-destroyable.h"
-
-namespace Slang
-{
-
-
-/* A useful interface for handling lists of castable interfaces. Cannot hold nullptr */
-class ICastableList : public ICastable
-{
- SLANG_COM_INTERFACE(0x335f3d40, 0x934c, 0x40dc, { 0xb5, 0xe1, 0xf7, 0x6e, 0x40, 0x3, 0x62, 0x5 })
-
- typedef bool (*FindFunc)(ICastable* castable, void* data);
-
- /// Get the count of all interfaces held in the list
- virtual Count SLANG_MCALL getCount() = 0;
- /// Get the interface at the specified index
- virtual ICastable* SLANG_MCALL getAt(Index i) = 0;
- /// Add an item to the list
- virtual void SLANG_MCALL add(ICastable* unk) = 0;
- /// Add IUnknown, will cast to ICastable and if that's not possible will wrap
- virtual void SLANG_MCALL addUnknown(ISlangUnknown* unk) = 0;
- /// Remove item at index, remaining items stay in the same order
- virtual void SLANG_MCALL removeAt(Index i) = 0;
- /// Clear the list
- virtual void SLANG_MCALL clear() = 0;
- /// Find the first index of castable, or -1 if not found
- virtual Index SLANG_MCALL indexOf(ICastable* castable) = 0;
- /// Find the index interface (handling wrapping if necessary)
- virtual Index SLANG_MCALL indexOfUnknown(ISlangUnknown* unk) = 0;
- /// Find the first item that casts to non null
- virtual void* SLANG_MCALL find(const Guid& guid) = 0;
- /// Find the fast castable that matches the predicate
- virtual ICastable* SLANG_MCALL findWithPredicate(FindFunc func, void* data) = 0;
- /// Access the internal buffer (any mutation can invalidate this value)
- virtual ICastable*const* SLANG_MCALL getBuffer() = 0;
-};
-
-// Simply finding things in a ICastableList
-template <typename T>
-SLANG_FORCE_INLINE T* find(ICastableList* list)
-{
- return reinterpret_cast<T*>(list->find(T::getTypeGuid()));
-}
-
-template <typename T>
-SLANG_FORCE_INLINE T* find(ICastableList* list, ICastableList::FindFunc func, void* data)
-{
- return reinterpret_cast<T*>(list->findWithPredicate(T::getTypeGuid(), func, data));
-}
-
-/* Adapter interface to make a non castable types work as ICastable */
-class IUnknownCastableAdapter : public ICastable
-{
- SLANG_COM_INTERFACE(0x8b4aad81, 0x4934, 0x4a67, { 0xb2, 0xe2, 0xe9, 0x17, 0xfc, 0x29, 0x12, 0x54 });
-
- /// When using the adapter, this provides a way to directly get the internal no ICastable type
- virtual SLANG_NO_THROW ISlangUnknown* SLANG_MCALL getContained() = 0;
-};
-
-} // namespace Slang
-
-#endif
diff --git a/source/core/slang-castable-util.h b/source/core/slang-castable-util.h
deleted file mode 100644
index 4d3c3900c..000000000
--- a/source/core/slang-castable-util.h
+++ /dev/null
@@ -1,58 +0,0 @@
-// slang-castable-util.h
-#ifndef SLANG_CASTABLE_UTIL_H
-#define SLANG_CASTABLE_UTIL_H
-
-#include "slang-castable-list.h"
-
-#include "../../slang-com-helper.h"
-#include "../../slang-com-ptr.h"
-
-#include "../core/slang-com-object.h"
-
-namespace Slang
-{
-
-/* An adapter such that types which aren't derived from ICastable, can be used as such.
-
-With the following caveats.
-* the interfaces/objects of the adapter are checked *first*, so IUnknown will always be for the adapter
-* assumes when doing a queryInterface on the contained item, it will remain in scope when released (this is *not* strict COM)
-*/
-class UnknownCastableAdapter : public ComBaseObject, public IUnknownCastableAdapter
-{
-public:
- SLANG_COM_BASE_IUNKNOWN_ALL
-
- // ICastable
- SLANG_NO_THROW void* SLANG_MCALL castAs(const Guid& guid) SLANG_OVERRIDE;
-
- // IUnknownCastableAdapter
- virtual SLANG_NO_THROW ISlangUnknown* SLANG_MCALL getContained() SLANG_OVERRIDE { return m_contained; }
-
- UnknownCastableAdapter(ISlangUnknown* unk):
- m_contained(unk)
- {
- SLANG_ASSERT(unk);
- }
-
-protected:
- void* getInterface(const Guid& guid);
- void* getObject(const Guid& guid);
-
- ComPtr<ISlangUnknown> m_contained;
-
- // We hold a cache for a single lookup to make things a little faster
- void* m_found = nullptr;
- Guid m_foundGuid;
-};
-
-struct CastableUtil
-{
- /// Given an ISlangUnkown return as a castable interface.
- /// Can use UnknownCastableAdapter if can't queryInterface unk to ICastable
- static ComPtr<ICastable> getCastable(ISlangUnknown* unk);
-};
-
-} // namespace Slang
-
-#endif
diff --git a/source/core/slang-castable-util.cpp b/source/core/slang-castable.cpp
index 38652d47b..f3c6541dd 100644
--- a/source/core/slang-castable-util.cpp
+++ b/source/core/slang-castable.cpp
@@ -1,5 +1,5 @@
-// slang-castable-util.cpp
-#include "slang-castable-util.h"
+// slang-castable.cpp
+#include "slang-castable.h"
namespace Slang {
diff --git a/source/core/slang-castable.h b/source/core/slang-castable.h
new file mode 100644
index 000000000..a72822f05
--- /dev/null
+++ b/source/core/slang-castable.h
@@ -0,0 +1,106 @@
+// slang-castable.h
+#ifndef SLANG_CASTABLE_H
+#define SLANG_CASTABLE_H
+
+
+#include "../../slang-com-helper.h"
+#include "../../slang-com-ptr.h"
+
+#include "../core/slang-com-object.h"
+
+namespace Slang
+{
+
+// Dynamic cast of ICastable derived types
+template <typename T>
+SLANG_FORCE_INLINE T* dynamicCast(ICastable* castable)
+{
+ if (castable)
+ {
+ void* obj = castable->castAs(T::getTypeGuid());
+ return obj ? reinterpret_cast<T*>(obj) : ((T*)nullptr);
+ }
+ return nullptr;
+}
+
+// as style cast
+template <typename T>
+SLANG_FORCE_INLINE T* as(ICastable* castable)
+{
+ if (castable)
+ {
+ void* obj = castable->castAs(T::getTypeGuid());
+ return obj ? reinterpret_cast<T*>(obj) : ((T*)nullptr);
+ }
+ return nullptr;
+}
+
+/* Adapter interface to make a non castable types work as ICastable */
+class IUnknownCastableAdapter : public ICastable
+{
+ SLANG_COM_INTERFACE(0x8b4aad81, 0x4934, 0x4a67, { 0xb2, 0xe2, 0xe9, 0x17, 0xfc, 0x29, 0x12, 0x54 });
+
+ /// When using the adapter, this provides a way to directly get the internal no ICastable type
+ virtual SLANG_NO_THROW ISlangUnknown* SLANG_MCALL getContained() = 0;
+};
+
+/* An adapter such that types which aren't derived from ICastable, can be used as such.
+
+With the following caveats.
+* the interfaces/objects of the adapter are checked *first*, so IUnknown will always be for the adapter
+* assumes when doing a queryInterface on the contained item, it will remain in scope when released (this is *not* strict COM)
+*/
+class UnknownCastableAdapter : public ComBaseObject, public IUnknownCastableAdapter
+{
+public:
+ SLANG_COM_BASE_IUNKNOWN_ALL
+
+ // ICastable
+ SLANG_NO_THROW void* SLANG_MCALL castAs(const Guid& guid) SLANG_OVERRIDE;
+
+ // IUnknownCastableAdapter
+ virtual SLANG_NO_THROW ISlangUnknown* SLANG_MCALL getContained() SLANG_OVERRIDE { return m_contained; }
+
+ UnknownCastableAdapter(ISlangUnknown* unk):
+ m_contained(unk)
+ {
+ SLANG_ASSERT(unk);
+ }
+
+protected:
+ void* getInterface(const Guid& guid);
+ void* getObject(const Guid& guid);
+
+ ComPtr<ISlangUnknown> m_contained;
+
+ // We hold a cache for a single lookup to make things a little faster
+ void* m_found = nullptr;
+ Guid m_foundGuid;
+};
+
+struct CastableUtil
+{
+ /// Given an ISlangUnkown return as a castable interface.
+ /// Can use UnknownCastableAdapter if can't queryInterface unk to ICastable
+ static ComPtr<ICastable> getCastable(ISlangUnknown* unk);
+};
+
+
+// A way to clone an interface (that derives from IClonable) such that it returns an interface
+// of the same type.
+template <typename T>
+SLANG_FORCE_INLINE ComPtr<T> cloneInterface(T* in)
+{
+ SLANG_ASSERT(in);
+ // Must be derivable from clonable
+ IClonable* clonable = in;
+ // We can clone with the same interface
+ T* clone = (T*)clonable->clone(T::getTypeGuid());
+ // Clone must exist
+ SLANG_ASSERT(clone);
+ return ComPtr<T>(clone);
+}
+
+} // namespace Slang
+
+#endif
diff --git a/source/core/slang-destroyable.h b/source/core/slang-destroyable.h
deleted file mode 100644
index f2c967071..000000000
--- a/source/core/slang-destroyable.h
+++ /dev/null
@@ -1,68 +0,0 @@
-#ifndef SLANG_CORE_DESTROYABLE_H
-#define SLANG_CORE_DESTROYABLE_H
-
-#include "slang-string.h"
-
-#include "../../slang-com-helper.h"
-#include "../../slang-com-ptr.h"
-
-namespace Slang
-{
-
-/* An interface that allows for an object to implement 'destruction'. A destroyed
-interface/object should release any other contained references.
-Behavior of an interface that is IDestroyed should be defined on the interface. Typically
-it will produce an assert on debug builds.
-Calling destroy/isDestroyed can always be performed. */
-class IDestroyable : public ICastable
-{
- SLANG_COM_INTERFACE(0x99c6228e, 0xa82, 0x43eb, { 0x8f, 0xd1, 0xf3, 0x54, 0x3e, 0x2e, 0x86, 0xc0 } );
-
- /// Destroy. Can call on destroyed - is a no op.
- virtual SLANG_NO_THROW void SLANG_MCALL destroy() = 0;
- /// Once destroyed *no* functionality is supported other than IUnknown and destroy/isDestroyed
- virtual SLANG_NO_THROW bool SLANG_MCALL isDestroyed() = 0;
-};
-
-// Dynamic cast of ICastable derived types
-template <typename T>
-SLANG_FORCE_INLINE T* dynamicCast(ICastable* castable)
-{
- if (castable)
- {
- void* obj = castable->castAs(T::getTypeGuid());
- return obj ? reinterpret_cast<T*>(obj) : ((T*)nullptr);
- }
- return nullptr;
-}
-
-// as style cast
-template <typename T>
-SLANG_FORCE_INLINE T* as(ICastable* castable)
-{
- if (castable)
- {
- void* obj = castable->castAs(T::getTypeGuid());
- return obj ? reinterpret_cast<T*>(obj) : ((T*)nullptr);
- }
- return nullptr;
-}
-
-// A way to clone an interface (that derives from IClonable) such that it returns an interface
-// of the same type.
-template <typename T>
-SLANG_FORCE_INLINE ComPtr<T> cloneInterface(T* in)
-{
- SLANG_ASSERT(in);
- // Must be derivable from clonable
- IClonable* clonable = in;
- // We can clone with the same interface
- T* clone = (T*)clonable->clone(T::getTypeGuid());
- // Clone must exist
- SLANG_ASSERT(clone);
- return ComPtr<T>(clone);
-}
-
-}
-
-#endif // SLANG_CORE_DESTROYABLE_H
diff --git a/source/core/slang-lazy-castable-list.cpp b/source/core/slang-lazy-castable-list.cpp
deleted file mode 100644
index 112172108..000000000
--- a/source/core/slang-lazy-castable-list.cpp
+++ /dev/null
@@ -1,175 +0,0 @@
-// slang-lazy-castable-list.cpp
-#include "slang-lazy-castable-list.h"
-
-#include "slang-castable-list-impl.h"
-
-namespace Slang {
-
-void LazyCastableList::removeAt(Index index)
-{
- SLANG_ASSERT(index >= 0 && index < getCount());
-
- switch (m_state)
- {
- case State::None: break;
- case State::One:
- {
- m_state = State::None;
- m_castable.setNull();
- break;
- }
- case State::List:
- {
- static_cast<ICastableList*>(m_castable.get())->removeAt(index);
- break;
- }
- }
-}
-
-void LazyCastableList::clear()
-{
- if (m_state == State::List)
- {
- auto list = static_cast<ICastableList*>(m_castable.get());
- list->clear();
- }
- else
- {
- m_state = State::None;
- m_castable.setNull();
- }
-}
-
-void LazyCastableList::clearAndDeallocate()
-{
- m_state = State::None;
- m_castable.setNull();
-}
-
-Count LazyCastableList::getCount() const
-{
- switch (m_state)
- {
- case State::None: return 0;
- case State::One: return 1;
- default:
- case State::List: return static_cast<ICastableList*>(m_castable.get())->getCount();
- }
-}
-
-void LazyCastableList::add(ICastable* castable)
-{
- SLANG_ASSERT(castable);
- if (m_state == State::None)
- {
- m_castable = castable;
- m_state = State::One;
- }
- else
- {
- requireList()->add(castable);
- }
-}
-
-ICastableList* LazyCastableList::requireList()
-{
- switch (m_state)
- {
- case State::None:
- {
- m_castable = new CastableList;
- m_state = State::List;
- break;
- }
- case State::One:
- {
- // Turn into a list
- auto list = new CastableList;
- list->add(m_castable);
- m_castable = list;
- m_state = State::List;
- break;
- }
- default: break;
- }
- SLANG_ASSERT(m_state == State::List);
- return static_cast<ICastableList*>(m_castable.get());
-}
-
-ICastableList* LazyCastableList::getList()
-{
- return (m_state == State::None) ? nullptr : requireList();
-}
-
-void* LazyCastableList::find(const Guid& guid)
-{
- for (auto castable : getView())
- {
- if (auto ptr = castable->castAs(guid))
- {
- return ptr;
- }
- }
- return nullptr;
-}
-
-ICastable* LazyCastableList::findWithPredicate(ICastableList::FindFunc func, void* data)
-{
- for (auto castable : getView())
- {
- if (func(castable, data))
- {
- return castable;
- }
- }
- return nullptr;
-}
-
-ConstArrayView<ICastable*> LazyCastableList::getView() const
-{
- switch (m_state)
- {
- case State::None: return ConstArrayView<ICastable*>();
- case State::One: return ConstArrayView<ICastable*>((ICastable*const*)&m_castable, 1);
- default:
- case State::List:
- {
- auto list = static_cast<ICastableList*>(m_castable.get());
- return ConstArrayView<ICastable*>(list->getBuffer(), list->getCount());
- }
- }
-}
-
-Index LazyCastableList::indexOf(ICastable* castable) const
-{
- return getView().indexOf(castable);
-}
-
-Index LazyCastableList::indexOfUnknown(ISlangUnknown* unk) const
-{
- // Try as a ICastable first
- {
- ComPtr<ICastable> castable;
- if (SLANG_SUCCEEDED(unk->queryInterface(SLANG_IID_PPV_ARGS(castable.writeRef()))) && castable)
- {
- return indexOf(castable);
- }
- }
-
- // It's not derived from ICastable, so can only be in list via an adapter
- const auto view = getView();
-
- const Count count = view.getCount();
- for (Index i = 0; i < count; ++i)
- {
- auto adapter = as<IUnknownCastableAdapter>(view[i]);
- if (adapter && adapter->getContained() == unk)
- {
- return i;
- }
- }
-
- return -1;
-}
-
-} // namespace Slang
diff --git a/source/core/slang-lazy-castable-list.h b/source/core/slang-lazy-castable-list.h
deleted file mode 100644
index 84bfd8c6d..000000000
--- a/source/core/slang-lazy-castable-list.h
+++ /dev/null
@@ -1,68 +0,0 @@
-// slang-lazy-castable-list.h
-#ifndef SLANG_LAZY_CASTABLE_LIST_H
-#define SLANG_LAZY_CASTABLE_LIST_H
-
-#include "slang-castable-list.h"
-
-#include "../../slang-com-ptr.h"
-
-namespace Slang
-{
-
-/* Sometimes the overhead around having a potential list of items that might often be
-empty or only contain a single element is considerable.
-
-The `LazyCastableList` provides functionality around ICastableList to minimize allocation, or the
-need to allocate an ICastableList. It does this by tracking state in m_state, and varying the
-meaning of m_castable.
-
-* State::None - there is no list
-* State::One - there is a single entry, that is held in m_castable
-* State::List - m_castable is actually ICastableList, and holds the contents
-*/
-class LazyCastableList
-{
-public:
- /// Add a castable to the lsit
- void add(ICastable* castable);
- /// Return the amount of items in the list
- Count getCount() const;
- /// Remove the item at the specified index
- void removeAt(Index index);
- /// Clear the list
- void clear();
- /// Clear and deallocate the list
- void clearAndDeallocate();
- /// Find the first item that castAs(guid) produces a result
- void* find(const Guid& guid);
- /// Find first match using predicate function
- ICastable* findWithPredicate(ICastableList::FindFunc func, void* data);
- /// Get the contents of the list as a view
- ConstArrayView<ICastable*> getView() const;
- /// Get the index of castable in the list. Returns -1 if not found
- Index indexOf(ICastable* castable) const;
- /// Get the index of unk. Handles if the wrapping has been used.
- Index indexOfUnknown(ISlangUnknown* unk) const;
-
- /// Will always return a valid ICastableList
- ICastableList* requireList();
- /// Will return nullptr if the list is empty, else it returns a ICastableList holding the elements
- ICastableList* getList();
-
-protected:
- enum class State
- {
- None,
- One,
- List,
- };
- // A state is not *strictly* necessary, because we can always determine what m_castable is
- // with a castAs. But doing so is not exactly fast, and using the state makes some code simpler
- // additionally.
- State m_state = State::None;
- ComPtr<ICastable> m_castable;
-};
-
-} // namespace Slang
-
-#endif
diff --git a/source/slang/slang-compiler.cpp b/source/slang/slang-compiler.cpp
index 839a4e67c..497cf3d94 100644
--- a/source/slang/slang-compiler.cpp
+++ b/source/slang/slang-compiler.cpp
@@ -8,6 +8,7 @@
#include "../core/slang-riff.h"
#include "../core/slang-type-text-util.h"
#include "../core/slang-type-convert-util.h"
+#include "../core/slang-castable.h"
#include "slang-check.h"
#include "slang-compiler.h"
@@ -1119,7 +1120,7 @@ namespace Slang
ComPtr<IArtifactPostEmitMetadata> metadata;
if (sourceArtifact)
{
- metadata = findAssociated<IArtifactPostEmitMetadata>(sourceArtifact);
+ metadata = findAssociatedRepresentation<IArtifactPostEmitMetadata>(sourceArtifact);
// Set the source artifacts
options.sourceArtifacts = makeSlice(sourceArtifact.readRef(), 1);
@@ -1411,7 +1412,7 @@ namespace Slang
(std::chrono::high_resolution_clock::now() - downstreamStartTime).count() * 0.000000001;
getSession()->addDownstreamCompileTime(downstreamElapsedTime);
- auto diagnostics = findAssociated<IArtifactDiagnostics>(artifact);
+ auto diagnostics = findAssociatedRepresentation<IArtifactDiagnostics>(artifact);
if (diagnostics->getCount())
{
@@ -1468,10 +1469,7 @@ namespace Slang
return SLANG_FAIL;
}
- if (metadata)
- {
- artifact->addAssociated(metadata);
- }
+ ArtifactUtil::addAssociated(artifact, metadata);
// Set the artifact
outArtifact.swap(artifact);
@@ -1975,22 +1973,19 @@ namespace Slang
{
Index nameCount = 0;
- auto associated = m_containerArtifact->getAssociated();
- const Count count = associated->getCount();
- for (Index i = 0; i < count; ++i)
+ for (auto associatedArtifact : m_containerArtifact->getAssociated())
{
- IArtifact* artifact = as<IArtifact>(associated->getAt(i));
- auto desc = artifact->getDesc();
+ auto desc = associatedArtifact->getDesc();
if (isDerivedFrom(desc.payload, ArtifactPayload::SourceMap))
{
StringBuilder artifactFilename;
// Dump out
- const char* artifactName = artifact->getName();
+ const char* artifactName = associatedArtifact->getName();
if (artifactName && artifactName[0] != 0)
{
- SLANG_RETURN_ON_FAIL(ArtifactUtil::calcName(artifact, UnownedStringSlice(artifactName), artifactFilename));
+ SLANG_RETURN_ON_FAIL(ArtifactUtil::calcName(associatedArtifact, UnownedStringSlice(artifactName), artifactFilename));
}
else
{
@@ -2005,13 +2000,13 @@ namespace Slang
baseName.append(nameCount);
}
- SLANG_RETURN_ON_FAIL(ArtifactUtil::calcName(artifact, baseName.getUnownedSlice(), artifactFilename));
+ SLANG_RETURN_ON_FAIL(ArtifactUtil::calcName(associatedArtifact, baseName.getUnownedSlice(), artifactFilename));
nameCount ++;
}
ComPtr<ISlangBlob> blob;
- SLANG_RETURN_ON_FAIL(artifact->loadBlob(ArtifactKeep::No, blob.writeRef()));
+ SLANG_RETURN_ON_FAIL(associatedArtifact->loadBlob(ArtifactKeep::No, blob.writeRef()));
// Try to write it out
{
diff --git a/source/slang/slang-emit.cpp b/source/slang/slang-emit.cpp
index a18eed928..ca141bd7a 100644
--- a/source/slang/slang-emit.cpp
+++ b/source/slang/slang-emit.cpp
@@ -1146,10 +1146,7 @@ SlangResult CodeGenContext::emitEntryPointsSourceFromIR(ComPtr<IArtifact>& outAr
auto artifact = ArtifactUtil::createArtifactForCompileTarget(asExternal(target));
artifact->addRepresentationUnknown(StringBlob::moveCreate(finalResult));
- if (metadata)
- {
- artifact->addAssociated(metadata);
- }
+ ArtifactUtil::addAssociated(artifact, metadata);
if (sourceMap)
{
@@ -1210,10 +1207,7 @@ SlangResult emitSPIRVForEntryPointsDirectly(
auto artifact = ArtifactUtil::createArtifactForCompileTarget(asExternal(codeGenContext->getTargetFormat()));
artifact->addRepresentationUnknown(ListBlob::moveCreate(spirv));
- if (linkedIR.metadata)
- {
- artifact->addAssociated(linkedIR.metadata);
- }
+ ArtifactUtil::addAssociated(artifact, linkedIR.metadata);
outArtifact.swap(artifact);
diff --git a/source/slang/slang-options.cpp b/source/slang/slang-options.cpp
index d30c02484..7e24b53fe 100644
--- a/source/slang/slang-options.cpp
+++ b/source/slang/slang-options.cpp
@@ -20,6 +20,7 @@
#include "slang-repro.h"
#include "slang-serialize-ir.h"
+#include "../core/slang-castable.h"
#include "../core/slang-file-system.h"
#include "../core/slang-type-text-util.h"
#include "../core/slang-hex-dump-util.h"
diff --git a/source/slang/slang-repro.cpp b/source/slang/slang-repro.cpp
index d3a65adc0..d77aa9b21 100644
--- a/source/slang/slang-repro.cpp
+++ b/source/slang/slang-repro.cpp
@@ -7,6 +7,7 @@
#include "../core/slang-math.h"
#include "../core/slang-type-text-util.h"
+#include "../core/slang-castable.h"
#include "slang-options.h"
diff --git a/source/slang/slang.cpp b/source/slang/slang.cpp
index 2f02dcfb7..597e27bb9 100644
--- a/source/slang/slang.cpp
+++ b/source/slang/slang.cpp
@@ -6,6 +6,7 @@
#include "../core/slang-archive-file-system.h"
#include "../core/slang-type-text-util.h"
#include "../core/slang-type-convert-util.h"
+#include "../core/slang-castable.h"
// Artifact
#include "../compiler-core/slang-artifact-impl.h"
@@ -5378,7 +5379,7 @@ SlangResult EndToEndCompileRequest::isParameterLocationUsed(Int entryPointIndex,
return SLANG_E_INVALID_ARG;
// Find a rep
- auto metadata = findAssociated<IArtifactPostEmitMetadata>(artifact);
+ auto metadata = findAssociatedRepresentation<IArtifactPostEmitMetadata>(artifact);
if (!metadata)
return SLANG_E_NOT_AVAILABLE;