My reworking of pending-entity loading introduced a GC problem. The
post-load processing needs to inhibit GCs (that would otherwise occur
in clone_decl). That wasn't happening on one code path, leading to
dangling pointers in the active call frames.
PR c++/99423
gcc/cp/
* module.cc (post_load_processing): Assert not gcable.
(laxy_load_pendings): Extend no-gc region around
post_load_processing.
gcc/testsuite/
* g++.dg/modules/pr99423_a.H: New.
* g++.dg/modules/pr99423_b.H: New.
static void
post_load_processing ()
{
+ /* We mustn't cause a GC, our caller should have arranged for that
+ not to happen. */
+ gcc_checking_assert (function_depth);
+
if (!post_load_decls)
return;
pending_table->remove (key);
dump.pop (n);
- function_depth--;
lazy_snum = 0;
post_load_processing ();
+ function_depth--;
}
timevar_stop (TV_MODULE_IMPORT);
--- /dev/null
+// PR 99423 ICE seeing GC freed entities
+// { dg-additional-options -fmodule-header }
+// { dg-module-cmi {} }
+template<typename _T1>
+struct pair
+{
+ pair() { }
+};
+
+inline pair<bool> blob ()
+{
+ return {};
+}
--- /dev/null
+// { dg-additional-options {-fmodule-header --param ggc-min-expand=0 --param ggc-min-heapsize=0} }
+// { dg-module-cmi {} }
+
+import "pr99423_a.H";
+
+pair<bool> boom();