https://gcc.gnu.org/bugzilla/show_bug.cgi?id=58993

Patrick Palka <ppalka at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |ppalka at gcc dot gnu.org
             Status|NEW                         |ASSIGNED
           Assignee|unassigned at gcc dot gnu.org      |ppalka at gcc dot 
gnu.org

--- Comment #8 from Patrick Palka <ppalka at gcc dot gnu.org> ---
(In reply to Jonathan Wakely from comment #5)
> Warning-free testcase:
> 
> class base {
> private:
>     void foo() { }
> };
> 
> template <typename T>
> struct bar : public base {
>     void test() {
>         (void) &base::foo;  // should be rejected
>     }
> };
> 
> template <>
> struct bar<void> : public base {
>     void test() {
>         // &base::foo;  // correctly rejected
>     }
> };
> 
> int main() {
>     bar<int>().test();
>     bar<void>().test();
> }
> 
> Still accepted by trunk.
> 
> 
> Clang says:
> 
> 58993.cc:9:23: error: 'foo' is a private member of 'base'
>         (void) &base::foo;  // should be rejected
>                       ^
> 58993.cc:3:10: note: declared private here
>     void foo() { }
>          ^
> 1 error generated.
> 
> 
> and EDG says:
> 
> "58993.cc", line 9: error: function "base::foo" (declared at line 3) is
>           inaccessible
>           (void) &base::foo;  // should be rejected
>                         ^
>           detected during instantiation of "void bar<T>::test() [with T=int]"
>                     at line 21
> 
> 1 error detected in the compilation of "58993.cc".

With GCC 11 (after the PR41437 patch), we reject the first access only if
bar<T>::test() is defined out-of-line:

class base {
private:
    int foo() { }
};

template <typename T>
struct bar : public base {
    void test();
};

template <typename T>
void bar<T>::test() {
    &base::foo;
}

int main() {
    bar<int>().test();
}

Investigating.

Reply via email to