summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Source/cmGeneratorTarget.cxx56
-rw-r--r--Source/cmGeneratorTarget.h17
2 files changed, 73 insertions, 0 deletions
diff --git a/Source/cmGeneratorTarget.cxx b/Source/cmGeneratorTarget.cxx
index 572e7b8..57bdff7 100644
--- a/Source/cmGeneratorTarget.cxx
+++ b/Source/cmGeneratorTarget.cxx
@@ -4978,6 +4978,16 @@ void cmGeneratorTarget::ComputeImportInfo(std::string const& desired_config,
}
}
+ // Get information if target is managed assembly.
+ {
+ std::string linkProp = "IMPORTED_COMMON_LANGUAGE_RUNTIME";
+ if (auto pc = this->GetProperty(linkProp + suffix)) {
+ info.Managed = this->CheckManagedType(pc);
+ } else if (auto p = this->GetProperty(linkProp)) {
+ info.Managed = this->CheckManagedType(p);
+ }
+ }
+
// Get the cyclic repetition count.
if (this->GetType() == cmStateEnums::STATIC_LIBRARY) {
std::string linkProp = "IMPORTED_LINK_INTERFACE_MULTIPLICITY";
@@ -5474,3 +5484,49 @@ bool cmGeneratorTarget::IsCFBundleOnApple() const
return (this->GetType() == cmStateEnums::MODULE_LIBRARY &&
this->Makefile->IsOn("APPLE") && this->GetPropertyAsBool("BUNDLE"));
}
+
+cmGeneratorTarget::ManagedType cmGeneratorTarget::CheckManagedType(
+ std::string const& propval) const
+{
+ // The type of the managed assembly (mixed unmanaged C++ and C++/CLI,
+ // or only C++/CLI) does only depend on whether the property is an empty
+ // string or contains any value at all. In Visual Studio generators
+ // this propval is prepended with /clr[:] which results in:
+ //
+ // 1. propval does not exist: no /clr flag, unmanaged target, has import
+ // lib
+ // 2. empty propval: add /clr as flag, mixed unmanaged/managed
+ // target, has import lib
+ // 3. any value (safe,pure): add /clr:[propval] as flag, target with
+ // managed code only, no import lib
+ return propval.empty() ? ManagedType::Mixed : ManagedType::Managed;
+}
+
+cmGeneratorTarget::ManagedType cmGeneratorTarget::GetManagedType(
+ const std::string& config) const
+{
+ // Only libraries and executables can be managed targets.
+ if (this->GetType() != cmStateEnums::SHARED_LIBRARY &&
+ this->GetType() != cmStateEnums::STATIC_LIBRARY &&
+ this->GetType() != cmStateEnums::EXECUTABLE) {
+ return ManagedType::Undefined;
+ }
+
+ // Check imported target.
+ if (this->IsImported()) {
+ if (cmGeneratorTarget::ImportInfo const* info =
+ this->GetImportInfo(config)) {
+ return info->Managed;
+ }
+ return ManagedType::Undefined;
+ }
+
+ // Check for explicitly set clr target property.
+ if (auto* clr = this->GetProperty("COMMON_LANGUAGE_RUNTIME")) {
+ return this->CheckManagedType(clr);
+ }
+
+ // TODO: need to check if target is a CSharp target here.
+ // If yes: return ManagedType::Managed.
+ return ManagedType::Native;
+}
diff --git a/Source/cmGeneratorTarget.h b/Source/cmGeneratorTarget.h
index f0c7cee..612d122 100644
--- a/Source/cmGeneratorTarget.h
+++ b/Source/cmGeneratorTarget.h
@@ -603,6 +603,19 @@ public:
/** Return whether this target is a CFBundle (plugin) on Apple. */
bool IsCFBundleOnApple() const;
+ /** Assembly types. The order of the values of this enum is relevant
+ because of smaller/larger comparison operations! */
+ enum ManagedType
+ {
+ Undefined = 0, // target is no lib or executable
+ Native, // target compiles to unmanaged binary.
+ Mixed, // target compiles to mixed (managed and unmanaged) binary.
+ Managed // target compiles to managed binary.
+ };
+
+ /** Return the type of assembly this target compiles to. */
+ ManagedType GetManagedType(const std::string& config) const;
+
struct SourceFileFlags GetTargetSourceFileFlags(
const cmSourceFile* sf) const;
@@ -747,10 +760,12 @@ private:
{
ImportInfo()
: NoSOName(false)
+ , Managed(Native)
, Multiplicity(0)
{
}
bool NoSOName;
+ ManagedType Managed;
unsigned int Multiplicity;
std::string Location;
std::string SOName;
@@ -844,6 +859,8 @@ private:
bool ComputePDBOutputDir(const std::string& kind, const std::string& config,
std::string& out) const;
+ ManagedType CheckManagedType(std::string const& propval) const;
+
public:
const std::vector<const cmGeneratorTarget*>& GetLinkImplementationClosure(
const std::string& config) const;