From: Nathan Sidwell Date: Fri, 12 Feb 2021 16:43:09 +0000 (-0800) Subject: c++: Seed imported bindings [PR 99039] X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=8c4137c7ead515baaf1ac8340edeb3a442388b5b;p=gcc.git c++: Seed imported bindings [PR 99039] As mentioned in 99040's fix, we can get inter-module using decls. If the using decl is the only reference to an import, we'll have failed to seed our imports leading to an assertion failure. The fix is straight-forwards, check binding contents when seeding imports. gcc/cp/ * module.cc (module_state::write_cluster): Check bindings for imported using-decls. gcc/testsuite/ * g++.dg/modules/pr99039_a.C: New. * g++.dg/modules/pr99039_b.C: New. --- diff --git a/gcc/cp/module.cc b/gcc/cp/module.cc index 37ccddc74a5..520494f2543 100644 --- a/gcc/cp/module.cc +++ b/gcc/cp/module.cc @@ -3108,7 +3108,8 @@ private: unsigned section; #if CHECKING_P int importedness; /* Checker that imports not occurring - inappropriately. */ + inappropriately. +ve imports ok, + -ve imports not ok. */ #endif public: @@ -14632,13 +14633,36 @@ module_state::write_cluster (elf_out *to, depset *scc[], unsigned size, { depset *dep = b->deps[jx]; - if (!dep->is_binding () - && dep->is_import () && !TREE_VISITED (dep->get_entity ())) + if (dep->is_binding ()) { - tree import = dep->get_entity (); + /* A cross-module using decl could be here. */ + for (unsigned ix = dep->deps.length (); --ix;) + { + depset *bind = dep->deps[ix]; + if (bind->get_entity_kind () == depset::EK_USING + && bind->deps[1]->is_import ()) + { + tree import = bind->deps[1]->get_entity (); + if (!TREE_VISITED (import)) + { + sec.tree_node (import); + dump (dumper::CLUSTER) + && dump ("Seeded import %N", import); + } + } + } + /* Also check the namespace itself. */ + dep = dep->deps[0]; + } - sec.tree_node (import); - dump (dumper::CLUSTER) && dump ("Seeded import %N", import); + if (dep->is_import ()) + { + tree import = dep->get_entity (); + if (!TREE_VISITED (import)) + { + sec.tree_node (import); + dump (dumper::CLUSTER) && dump ("Seeded import %N", import); + } } } } diff --git a/gcc/testsuite/g++.dg/modules/pr99039_a.C b/gcc/testsuite/g++.dg/modules/pr99039_a.C new file mode 100644 index 00000000000..56041e948db --- /dev/null +++ b/gcc/testsuite/g++.dg/modules/pr99039_a.C @@ -0,0 +1,9 @@ +// PR c++/99039 +// { dg-additional-options -fmodules-ts } +export module format; +// { dg-module-cmi format } + +export namespace NS +{ +void Format (); +} diff --git a/gcc/testsuite/g++.dg/modules/pr99039_b.C b/gcc/testsuite/g++.dg/modules/pr99039_b.C new file mode 100644 index 00000000000..6fb76f584fa --- /dev/null +++ b/gcc/testsuite/g++.dg/modules/pr99039_b.C @@ -0,0 +1,9 @@ +// { dg-additional-options -fmodules-ts } +export module hello; +// { dg-module-cmi hello } +import format; + +export namespace NS +{ +using NS::Format; +}