[gcc r17-2722] c++: vrp and pmf conversion [PR126310]
Jason Merrill via Gcc-cvs <[email protected]>
| Newsgroups | gmane.comp.gcc.cvs |
|---|---|
| Message-ID | <[email protected]> |
https://gcc.gnu.org/g:0e429acc24a2305c77da1229c456788e50edcae9 commit r17-2722-g0e429acc24a2305c77da1229c456788e50edcae9 Author: Jason Merrill <[email protected]> Date: Sun Jul 26 12:44:22 2026 -0400 c++: vrp and pmf conversion [PR126310] Here when trying to convert to EncodeFnTy, aka void (sub::*)(int&&), we were instead converting to void (sub::*)(ValuePart&&), and the optimization added by r16-5887 got confused by the values in the array initializer having different RECORD_TYPEs (with different FIELD_DECLs) from the type of the array. So let's correct the conversion to actually end with the requested type. PR c++/126310 gcc/cp/ChangeLog: * call.cc (standard_conversion): Don't build a mixed METHOD_TYPE if it isn't needed. gcc/testsuite/ChangeLog: * g++.dg/opt/pmf2.C: New test. Diff: --- gcc/cp/call.cc | 16 ++++++++++------ gcc/testsuite/g++.dg/opt/pmf2.C | 37 +++++++++++++++++++++++++++++++++++++ 2 files changed, 47 insertions(+), 6 deletions(-) diff --git a/gcc/cp/call.cc b/gcc/cp/call.cc index 143e85760b3b..62ad77a2db6f 100644 --- a/gcc/cp/call.cc +++ b/gcc/cp/call.cc @@ -1546,12 +1546,16 @@ standard_conversion (tree to, tree from, tree expr, bool c_cast_p, if (!same_type_p (fbase, tbase)) { - from = build_memfn_type (fstat, - tbase, - cp_type_quals (tbase), - type_memfn_rqual (tofn)); - from = build_ptrmemfunc_type (build_pointer_type (from)); - conv = build_conv (ck_pmem, from, conv); + tree first = to; + if (!same_type_p (tstat, fstat)) + { + first = build_memfn_type (fstat, + tbase, + cp_type_quals (tbase), + type_memfn_rqual (tofn)); + first = build_ptrmemfunc_type (build_pointer_type (first)); + } + conv = build_conv (ck_pmem, first, conv); conv->base_p = true; } if (fnptr_conv_p (tstat, fstat)) diff --git a/gcc/testsuite/g++.dg/opt/pmf2.C b/gcc/testsuite/g++.dg/opt/pmf2.C new file mode 100644 index 000000000000..88c38a8ea2a4 --- /dev/null +++ b/gcc/testsuite/g++.dg/opt/pmf2.C @@ -0,0 +1,37 @@ +// PR c++/126310 +// { dg-do run { target c++11 } } +// { dg-additional-options -O } + +typedef int ValuePart; +struct base0 { + int t; +}; +struct base1 { + void gg(ValuePart&&) {symbols = 1; } + int symbols; +}; +struct sub : base0, base1 {}; + +using EncodeFnTy = void (sub::*)(int&&); +static const EncodeFnTy encode_fns[] +{ + &sub::gg, + &sub::gg +}; + +[[gnu::noinline,gnu::noclone]] +void f(sub &m, bool i) +{ + (&m->*encode_fns[i])(0); +} +int main() +{ + sub a; + a.t = 0; + a.symbols = 0; + f(a, 0); + if (a.t != 0) + __builtin_abort (); + if (a.symbols != 1) + __builtin_abort (); +}