On Wed, 8 Jan 2025, Patrick Palka wrote: > On Thu, Dec 12, 2024 at 2:34 PM Patrick Palka <ppa...@redhat.com> wrote: > > > > Bootstrapped and regtested on x86_64-pc-linux-gnu, does this look OK for > > trunk? The older regression does not seem worth fixing.
Oops, does not seem worth fixing _on release branches_ rather. > > Ping. > > > > > -- >8 -- > > > > In the first testcase we're overeagerly diagnosing qualified name lookup > > failure for f from the current instantiation B<T>::C ahead of time > > because we (correctly) deem C to not have any direct dependent bases: > > its only base is B<T> which is part of the current instantiation and > > therefore not a dependent base, and we decide it's safe to diagnose name > > lookup failure ahead of time. > > > > But this testcase demonstrates it's not enough to consider only direct > > dependent bases: f is defined in A<T> which is a dependent base of > > B<T>, so qualified name lookup won't search it ahead of time and in > > turn name lookup won't be exhaustive, and so it's wrong to diagnose > > lookup failure ahead of time. This ultimately suggests that > > any_dependent_bases_p needs to consider indirect bases as well. > > > > It seems sufficient to recurse into any !BINFO_DEPENDENT_BASE_P base > > since the recursive call will exit early for non-dependent types. > > So effectively we'll only recurse into bases belonging to the current > > instantiation. > > > > I considered making only dependentish_scope_p consider indirect > > dependent bases, but it seems other any_dependent_bases_p callers > > also want this behavior, e.g. build_new_method_call for benefit of > > the second testcase (which is an even older regression since GCC 7). > > > > PR c++/117993 > > > > gcc/cp/ChangeLog: > > > > * search.cc (any_dependent_bases_p): Recurse into bases (of > > dependent type) that are not BINFO_DEPENDENT_BASE_P. Document > > default argument. > > > > gcc/testsuite/ChangeLog: > > > > * g++.dg/template/dependent-base4.C: New test. > > * g++.dg/template/dependent-base5.C: New test. > > --- > > gcc/cp/search.cc | 5 ++-- > > .../g++.dg/template/dependent-base4.C | 23 +++++++++++++++++++ > > .../g++.dg/template/dependent-base5.C | 22 ++++++++++++++++++ > > 3 files changed, 48 insertions(+), 2 deletions(-) > > create mode 100644 gcc/testsuite/g++.dg/template/dependent-base4.C > > create mode 100644 gcc/testsuite/g++.dg/template/dependent-base5.C > > > > diff --git a/gcc/cp/search.cc b/gcc/cp/search.cc > > index d438e18b74b..8a65dd3b68e 100644 > > --- a/gcc/cp/search.cc > > +++ b/gcc/cp/search.cc > > @@ -2843,7 +2843,7 @@ original_binfo (tree binfo, tree here) > > TYPE). */ > > > > bool > > -any_dependent_bases_p (tree type) > > +any_dependent_bases_p (tree type /* = current_nonlambda_class_type () */) > > { > > if (!type || !CLASS_TYPE_P (type) || !uses_template_parms (type)) > > return false; > > @@ -2858,7 +2858,8 @@ any_dependent_bases_p (tree type) > > unsigned i; > > tree base_binfo; > > FOR_EACH_VEC_SAFE_ELT (BINFO_BASE_BINFOS (TYPE_BINFO (type)), i, > > base_binfo) > > - if (BINFO_DEPENDENT_BASE_P (base_binfo)) > > + if (BINFO_DEPENDENT_BASE_P (base_binfo) > > + || any_dependent_bases_p (BINFO_TYPE (base_binfo))) > > return true; > > > > return false; > > diff --git a/gcc/testsuite/g++.dg/template/dependent-base4.C > > b/gcc/testsuite/g++.dg/template/dependent-base4.C > > new file mode 100644 > > index 00000000000..84e53b5f3fb > > --- /dev/null > > +++ b/gcc/testsuite/g++.dg/template/dependent-base4.C > > @@ -0,0 +1,23 @@ > > +// PR c++/117993 > > + > > +template<class T> > > +struct A { > > + void f(); > > + typedef void type; > > +}; > > + > > +template<class T> > > +struct B : A<T> { > > + template<class U> struct C; > > +}; > > + > > +template<class T> > > +template<class U> > > +struct B<T>::C : B { > > + void g(C& c) { > > + this->f(); // { dg-bogus "member" } > > + c.f(); // { dg-bogus "member" } > > + C::f(); // { dg-bogus "member" } > > + typename C::type* p; // { dg-bogus "not name a type" } > > + } > > +}; > > diff --git a/gcc/testsuite/g++.dg/template/dependent-base5.C > > b/gcc/testsuite/g++.dg/template/dependent-base5.C > > new file mode 100644 > > index 00000000000..2e9cdaa242b > > --- /dev/null > > +++ b/gcc/testsuite/g++.dg/template/dependent-base5.C > > @@ -0,0 +1,22 @@ > > +template<class T> > > +struct A { }; > > + > > +template<class T> > > +struct B : A<T> { > > + template<class U> struct C; > > +}; > > + > > +struct D { void f(); }; > > + > > +template<class T> > > +template<class U> > > +struct B<T>::C : B { > > + void g() { > > + D::f(); // { dg-bogus "without object" } > > + } > > +}; > > + > > +template<> > > +struct A<int> : D { }; > > + > > +template struct B<int>::C<int>; > > -- > > 2.47.1.440.gcaacdb5dfd > > >