On 5/19/25 8:27 AM, Nathaniel Shead wrote:
Bootstrapped and regtested on x86_64-pc-linux-gnu, OK for trunk?
Alternatively could go back to always marking vtables as DECL_EXTERNAL
as well but that doesn't seem to be necessary that I can tell.
DECL_NOT_REALLY_EXTERN doesn't make sense without DECL_EXTERNAL. The
antiquated linkage handling in the front end marks everything that might
or might not get emitted with those two flags (and DECL_DEFER_OUTPUT for
functions). I'd like to simplify that, it's been excessive since the
introduction of cgraph, but for now we should be marking vtables as
DECL_EXTERNAL.
-- >8 --
I missed a testcase in r16-688-gc875748cdc468e for whether a GM vtable
should be emitted in an importer when it has no non-inline key function.
Before that patch the code worked because always we marked all vtables
as DECL_EXTERNAL, which then meant that reading the definition marked
them as DECL_NOT_REALLY_EXTERN.
But it seems to me that really, all vtables should just be considered
DECL_NOT_REALLY_EXTERN until processed by maybe_emit_vtables (this is
how the frontend seems to behave in general); this patch makes that
adjustment.
PR c++/120349
gcc/cp/ChangeLog:
* module.cc (trees_in::read_var_def): Always mark vtables as
DECL_NOT_REALLY_EXTERN.
gcc/testsuite/ChangeLog:
* g++.dg/modules/vtt-3_a.C: New test.
* g++.dg/modules/vtt-3_b.C: New test.
Signed-off-by: Nathaniel Shead <nathanielosh...@gmail.com>
---
gcc/cp/module.cc | 2 +-
gcc/testsuite/g++.dg/modules/vtt-3_a.C | 29 ++++++++++++++++++++++++++
gcc/testsuite/g++.dg/modules/vtt-3_b.C | 14 +++++++++++++
3 files changed, 44 insertions(+), 1 deletion(-)
create mode 100644 gcc/testsuite/g++.dg/modules/vtt-3_a.C
create mode 100644 gcc/testsuite/g++.dg/modules/vtt-3_b.C
diff --git a/gcc/cp/module.cc b/gcc/cp/module.cc
index 200e1c2deb3..d860940caa4 100644
--- a/gcc/cp/module.cc
+++ b/gcc/cp/module.cc
@@ -12781,7 +12781,7 @@ trees_in::read_var_def (tree decl, tree maybe_template)
if (installing)
{
DECL_INITIAL (decl) = init;
- if (DECL_EXTERNAL (decl))
+ if (DECL_EXTERNAL (decl) || vtable)
DECL_NOT_REALLY_EXTERN (decl) = true;
if (VAR_P (decl))
{
diff --git a/gcc/testsuite/g++.dg/modules/vtt-3_a.C
b/gcc/testsuite/g++.dg/modules/vtt-3_a.C
new file mode 100644
index 00000000000..f38f024ba1f
--- /dev/null
+++ b/gcc/testsuite/g++.dg/modules/vtt-3_a.C
@@ -0,0 +1,29 @@
+// PR c++/120349
+// { dg-additional-options "-fmodules -Wno-global-module" }
+// { dg-module-cmi M }
+
+module;
+
+// GMF types; should have vtables emitted in importers
+struct BGG {
+ virtual inline ~BGG() {}
+};
+struct BGM {
+ virtual inline ~BGM() {}
+};
+struct DGG : BGG {};
+
+export module M;
+
+export using ::DGG;
+
+// Module-local types; should have vtables emitted here
+struct BM {
+ virtual inline ~BM() {}
+};
+export struct DGM : BGM {}; // note: this emits BGM's vtable here too
+export struct DM : BM {};
+
+// { dg-final { scan-assembler-not "_ZTV3BGG:" } }
+// { dg-final { scan-assembler "_ZTV3BGM:" } }
+// { dg-final { scan-assembler "_ZTVW1M2BM:" } }
diff --git a/gcc/testsuite/g++.dg/modules/vtt-3_b.C
b/gcc/testsuite/g++.dg/modules/vtt-3_b.C
new file mode 100644
index 00000000000..ef7ae6ca4e6
--- /dev/null
+++ b/gcc/testsuite/g++.dg/modules/vtt-3_b.C
@@ -0,0 +1,14 @@
+// PR c++/120349
+// { dg-additional-options "-fmodules -Wno-global-module" }
+
+import M;
+
+int main() {
+ DGG dgg;
+ DGM dgm;
+ DM dm;
+}
+
+// { dg-final { scan-assembler "_ZTV3BGG:" } }
+// { dg-final { scan-assembler "_ZTV3BGM:" } }
+// { dg-final { scan-assembler-not "_ZTVW1M2BM:" } }