From 63d1d6f8f4bb6db482b21e728245ebf9eee6b55f Mon Sep 17 00:00:00 2001 From: Boris Kolpackov Date: Fri, 16 Feb 2018 11:30:41 +0200 Subject: Fix group link-up race --- build2/cc/compile-rule.cxx | 5 +++++ build2/cc/install-rule.cxx | 18 +++++++++++++----- build2/cc/link-rule.cxx | 17 ++++++++--------- build2/cc/utility.cxx | 2 +- 4 files changed, 27 insertions(+), 15 deletions(-) (limited to 'build2/cc') diff --git a/build2/cc/compile-rule.cxx b/build2/cc/compile-rule.cxx index a6d2d48..632a9bf 100644 --- a/build2/cc/compile-rule.cxx +++ b/build2/cc/compile-rule.cxx @@ -3537,6 +3537,7 @@ namespace build2 // Find the mxx{} prerequisite and extract its "file name" for the // fuzzy match unless the user specified the module name explicitly. // + resolve_group (a, *pt); for (prerequisite_member p: group_prerequisite_members (a, *pt)) { if (p.is_a (*x_mod)) @@ -3649,6 +3650,8 @@ namespace build2 if (in != mn) { + // Note: matched, so the group should be resolved. + // for (prerequisite_member p: group_prerequisite_members (a, *bt)) { if (p.is_a (*x_mod)) // Got to be there. @@ -3865,6 +3868,8 @@ namespace build2 // sort things out. This is pretty similar to what we do in link when // synthesizing dependencies for bmi{}'s. // + // Note: lt is matched and so the group is resolved. + // ps.push_back (prerequisite (lt)); for (prerequisite_member p: group_prerequisite_members (a, lt)) { diff --git a/build2/cc/install-rule.cxx b/build2/cc/install-rule.cxx index 0fdb98b..e74104c 100644 --- a/build2/cc/install-rule.cxx +++ b/build2/cc/install-rule.cxx @@ -107,14 +107,18 @@ namespace build2 // // Note: for now we assume bmi*{} never come from see-through groups. // - if (p.is_a () || p.is_a (compile_types (ot).bmi)) + bool g (false); + if (p.is_a () || (g = p.is_a (compile_types (ot).bmi))) { - // This is tricky: we need to "look" inside groups for mxx{} but if - // found, remap to the group, not member. - // + if (g) + resolve_group (a, *pt); + for (prerequisite_member pm: group_prerequisite_members (a, *pt, members_mode::maybe)) { + // This is tricky: we need to "look" inside groups for mxx{} but if + // found, remap to the group, not member. + // if (pm.is_a (*x_mod)) { pt = t.is_a () @@ -304,8 +308,12 @@ namespace build2 return pt; } - if (p.is_a () || p.is_a (compile_types (ot).bmi)) + bool g (false); + if (p.is_a () || (g = p.is_a (compile_types (ot).bmi))) { + if (g) + resolve_group (a, *pt); + for (prerequisite_member pm: group_prerequisite_members (a, *pt, members_mode::maybe)) { diff --git a/build2/cc/link-rule.cxx b/build2/cc/link-rule.cxx index c59597a..bdf75c7 100644 --- a/build2/cc/link-rule.cxx +++ b/build2/cc/link-rule.cxx @@ -54,15 +54,10 @@ namespace build2 // If this is a library, link-up to our group (this is the target group // protocol which means this can be done whether we match or not). // - if (lt.library ()) - { - //@@ inner/outer race (see install-rule)? - - if (t.group == nullptr) - t.group = &search (t, - lt.utility ? libu::static_type : lib::static_type, - t.dir, t.out, t.name); - } + if (lt.library () && t.group == nullptr) + t.group = &search (t, + lt.utility ? libu::static_type : lib::static_type, + t.dir, t.out, t.name); // Scan prerequisites and see if we can work with what we've got. Note // that X could be C. We handle this by always checking for X first. @@ -777,6 +772,8 @@ namespace build2 ? (group ? bmi::static_type : tt.bmi) : (group ? obj::static_type : tt.obj)); + resolve_group (a, *pt); // Not matched yet so resolve group. + bool src (false); for (prerequisite_member p1: group_prerequisite_members (a, *pt)) { @@ -904,6 +901,8 @@ namespace build2 // bool mod (x_mod != nullptr && p.is_a (*x_mod)); + // Note: group already resolved in the previous loop. + for (prerequisite_member p1: group_prerequisite_members (a, *pt)) { if (p1.is_a (mod ? *x_mod : x_src) || p1.is_a ()) diff --git a/build2/cc/utility.cxx b/build2/cc/utility.cxx index aa47085..74da443 100644 --- a/build2/cc/utility.cxx +++ b/build2/cc/utility.cxx @@ -63,7 +63,7 @@ namespace build2 // Make sure group members are resolved. // - group_view gv (resolve_group_members (a, l)); + group_view gv (resolve_members (a, l)); assert (gv.members != nullptr); lorder lo (li.order); -- cgit v1.1