It occurred to me that we weren't warning about this with -Wabi and a
lower -fabi-version. This patch fixes that.
Tested x86_64-pc-linux-gnu, applying to trunk.
commit e924f74640ecd18240fb514f99b0d5b5ceeeffb7
Author: Jason Merrill <ja...@redhat.com>
Date: Wed Sep 2 16:32:15 2015 -0400
PR c++/44282
* mangle.c (write_CV_qualifiers_for_type): Also warn about regparm
mangling with lower -fabi-version.
diff --git a/gcc/cp/mangle.c b/gcc/cp/mangle.c
index 342cb93..2640d52 100644
--- a/gcc/cp/mangle.c
+++ b/gcc/cp/mangle.c
@@ -2196,7 +2196,7 @@ write_CV_qualifiers_for_type (const tree type)
We don't do this with classes and enums because their attributes
are part of their definitions, not something added on. */
- if (abi_version_at_least (10) && !OVERLOAD_TYPE_P (type))
+ if (!OVERLOAD_TYPE_P (type))
{
auto_vec<tree> vec;
for (tree a = TYPE_ATTRIBUTES (type); a; a = TREE_CHAIN (a))
@@ -2207,31 +2207,34 @@ write_CV_qualifiers_for_type (const tree type)
&& !is_attribute_p ("abi_tag", name))
vec.safe_push (a);
}
- vec.qsort (attr_strcmp);
- while (!vec.is_empty())
+ if (abi_version_crosses (10) && !vec.is_empty ())
+ G.need_abi_warning = true;
+ if (abi_version_at_least (10))
{
- tree a = vec.pop();
- const attribute_spec *as
- = lookup_attribute_spec (get_attribute_name (a));
-
- write_char ('U');
- write_unsigned_number (strlen (as->name));
- write_string (as->name);
- if (TREE_VALUE (a))
+ vec.qsort (attr_strcmp);
+ while (!vec.is_empty())
{
- write_char ('I');
- for (tree args = TREE_VALUE (a); args;
- args = TREE_CHAIN (args))
+ tree a = vec.pop();
+ const attribute_spec *as
+ = lookup_attribute_spec (get_attribute_name (a));
+
+ write_char ('U');
+ write_unsigned_number (strlen (as->name));
+ write_string (as->name);
+ if (TREE_VALUE (a))
{
- tree arg = TREE_VALUE (args);
- write_template_arg (arg);
+ write_char ('I');
+ for (tree args = TREE_VALUE (a); args;
+ args = TREE_CHAIN (args))
+ {
+ tree arg = TREE_VALUE (args);
+ write_template_arg (arg);
+ }
+ write_char ('E');
}
- write_char ('E');
+
+ ++num_qualifiers;
}
-
- ++num_qualifiers;
- if (abi_version_crosses (10))
- G.need_abi_warning = true;
}
}
diff --git a/gcc/testsuite/g++.dg/abi/mangle-regparm1a.C b/gcc/testsuite/g++.dg/abi/mangle-regparm1a.C
new file mode 100644
index 0000000..bfa6c9b
--- /dev/null
+++ b/gcc/testsuite/g++.dg/abi/mangle-regparm1a.C
@@ -0,0 +1,21 @@
+// { dg-do run { target { { i?86-*-* x86_64-*-* } && ia32 } } }
+// { dg-options "-fabi-version=8 -Wabi -save-temps" }
+// { dg-final { scan-assembler "_Z18IndirectExternCallIPFviiEiEvT_T0_S3_" } }
+
+template <typename F, typename T>
+void IndirectExternCall(F f, T t1, T t2) { // { dg-warning "mangled name" }
+ typedef F (*WrapF)(F);
+ f (t1, t2);
+}
+
+__attribute__((regparm(3), stdcall))
+void regparm_func (int i, int j)
+{
+ if (i != 24 || j != 42)
+ __builtin_abort();
+}
+
+int main()
+{
+ IndirectExternCall (regparm_func, 24, 42);
+}