aboutsummaryrefslogtreecommitdiff
path: root/libbuild2/file.cxx
diff options
context:
space:
mode:
authorBoris Kolpackov <boris@codesynthesis.com>2024-01-11 14:45:15 +0200
committerBoris Kolpackov <boris@codesynthesis.com>2024-01-15 08:52:39 +0200
commit05ee8c20d83c2f108aa71a65e19b7adff8ff9aa0 (patch)
tree34f54b78150895a1bf1c93214a0b5cfc8203dd8f /libbuild2/file.cxx
parent1d925696ac7eb8d7adb4d70b3f5afb010d745931 (diff)
Fail with unable to import rather than unknown target type
Diffstat (limited to 'libbuild2/file.cxx')
-rw-r--r--libbuild2/file.cxx69
1 files changed, 62 insertions, 7 deletions
diff --git a/libbuild2/file.cxx b/libbuild2/file.cxx
index e62e607..81a9dac 100644
--- a/libbuild2/file.cxx
+++ b/libbuild2/file.cxx
@@ -2063,16 +2063,13 @@ namespace build2
&t);
}
- // Suggest appropriate ways to import the specified target (as type and
- // name) from the specified project.
- //
- static void
+ void
import_suggest (const diag_record& dr,
const project_name& pn,
const target_type* tt,
const string& tn,
bool rule_hint,
- const char* qual = nullptr)
+ const char* qual)
{
string pv (pn.variable ());
@@ -2899,6 +2896,11 @@ namespace build2
static names
import2_buildfile (context&, names&&, bool, const location&);
+ static const target*
+ import2 (context&, const scope&, names&,
+ const string&, bool, const optional<string>&, bool,
+ const location&);
+
pair<names, import_kind>
import (scope& base,
name tgt,
@@ -2971,7 +2973,7 @@ namespace build2
// fallback case.
//
if (const target* t = import2 (ctx,
- base.find_prerequisite_key (ns, loc),
+ base, ns,
*ph2,
opt && !r.second /* optional */,
nullopt /* metadata */,
@@ -3168,6 +3170,8 @@ namespace build2
return *t;
}
+ // NOTE: see similar code in import2() below if changing anything here.
+
if (opt || exist)
return nullptr;
@@ -3185,6 +3189,57 @@ namespace build2
dr << endf;
}
+ // As above but with scope/ns instead of pk. This version deals with the
+ // unknown target type case.
+ //
+ static const target*
+ import2 (context& ctx,
+ const scope& base, names& ns,
+ const string& hint,
+ bool opt,
+ const optional<string>& meta,
+ bool exist,
+ const location& loc)
+ {
+ // If we have a rule hint, then it's natural to expect this target type is
+ // known to the importing project. Ditto for project-less import.
+ //
+ const target_type* tt (nullptr);
+ if (hint.empty ())
+ {
+ size_t n;
+ if ((n = ns.size ()) != 0 && n == (ns[0].pair ? 2 : 1))
+ {
+ const name& n (ns.front ());
+
+ if (n.typed () && !n.proj->empty ())
+ {
+ tt = base.find_target_type (n.type);
+
+ if (tt == nullptr)
+ {
+ // A subset of code in the above version of import2().
+ //
+ if (opt || exist)
+ return nullptr;
+
+ diag_record dr;
+ dr << fail (loc) << "unable to import target " << ns;
+ import_suggest (dr, *n.proj, nullptr, string (), meta.has_value ());
+ }
+ }
+ }
+ }
+
+ return import2 (ctx,
+ base.find_prerequisite_key (ns, loc, tt),
+ hint,
+ opt,
+ meta,
+ exist,
+ loc);
+ }
+
static names
import2_buildfile (context&, names&& ns, bool opt, const location& loc)
{
@@ -3323,7 +3378,7 @@ namespace build2
// fallback case.
//
pt = import2 (ctx,
- base.find_prerequisite_key (ns, loc),
+ base, ns,
*ph2,
opt && !r.second,
meta,