From: Alex Yesmanchyk Date: Wed, 28 Jan 2026 02:07:07 +0000 (-0500) Subject: c++: Error diagnostics for pointer-to-member type [PR38612] X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=6e9cf03a7602055b534a0bb1f0219d9d35104c2e;p=thirdparty%2Fgcc.git c++: Error diagnostics for pointer-to-member type [PR38612] Consider the following ptrtomem4.C file. Now for test1 and test3 it produces the following errors: ptrtomem4.C: In function 'int test1(int Base::*, X*)': ptrtomem4.C:8:21: error: pointer to member type 'int Base::*' incompatible with incomplete object type 'X' ptrtomem4.C: In function 'int test3(int Base::*, Y*)': ptrtomem4.C:22:21: error: pointer to member type 'int Base::*' incompatible with object type 'Y' because 'Y' is not derived from 'Base' PR c++/38612 gcc/cp/ChangeLog: * typeck2.cc (build_m_component_ref): Improve class mismatch diagnostic. gcc/testsuite/ChangeLog: * g++.dg/diagnostic/ptrtomem4.C: New test. Signed-off-by: Alex Yesmanchyk Co-authored-by: Jason Merrill --- diff --git a/gcc/cp/typeck2.cc b/gcc/cp/typeck2.cc index 1e5e3b24a23..f18c5a7499e 100644 --- a/gcc/cp/typeck2.cc +++ b/gcc/cp/typeck2.cc @@ -2459,8 +2459,16 @@ build_m_component_ref (tree datum, tree component, tsubst_flags_t complain) { mismatch: if (complain & tf_error) - error ("pointer to member type %qT incompatible with object " - "type %qT", type, objtype); + { + if (COMPLETE_TYPE_P (objtype)) + error ("pointer to member type %qT incompatible " + "with object type %qT because %qT is not " + "derived from %qT", ptrmem_type, objtype, + objtype, ctype); + else + error ("pointer to member type %qT incompatible with " + "incomplete object type %qT", ptrmem_type, objtype); + } return error_mark_node; } else if (binfo == error_mark_node) diff --git a/gcc/testsuite/g++.dg/diagnostic/ptrtomem4.C b/gcc/testsuite/g++.dg/diagnostic/ptrtomem4.C new file mode 100644 index 00000000000..564c28b4300 --- /dev/null +++ b/gcc/testsuite/g++.dg/diagnostic/ptrtomem4.C @@ -0,0 +1,24 @@ +// PR c++/38612 + +struct Base {}; +struct X; // X derived from Base later but incomplete here +struct Y {}; // Y not derived from Base + +int test1(int Base::* p2m, X* object) +{ + return object->*p2m; // { dg-error "int Base::.' incompatible with incomplete object type 'X'" } +} + +struct X : Base +{ +}; + +int test2(int Base::* p2m, X* object) +{ + return object->*p2m; // OK +} + +int test3(int Base::* p2m, Y* object) +{ + return object->*p2m; // { dg-error "int Base::.' incompatible with object type 'Y' because 'Y' is not derived from 'Base'" } +}