[PATCH] D39937: [Sema] Improve diagnostics for const- and ref-qualified member functions

Aaron Puchert via Phabricator via cfe-commits cfe-commits at lists.llvm.org
Wed Aug 26 17:24:20 PDT 2020


aaronpuchert added inline comments.


================
Comment at: test/CXX/over/over.match/over.match.funcs/p4-0x.cpp:22-24
+  void lvalue() &; // expected-note 2 {{'lvalue' declared here}}
+  void const_lvalue() const&;
+  void rvalue() &&; // expected-note {{'rvalue' declared here}}
----------------
lebedev.ri wrote:
> aaron.ballman wrote:
> > jtbandes wrote:
> > > aaron.ballman wrote:
> > > > Can you add examples that cover the other diagnostic wordings as well (volatile, restrict, combinations, etc)?
> > > I've been working on this, but I actually can't trigger the `restrict` variants. Do you know whether this is something that's expected to work? The implicit object param doesn't seem to retain its restrict-ness (full disclosure, I have almost no prior experience with `restrict`...):
> > > 
> > > ```
> > >   void c() const;
> > >   void v() volatile;
> > >   void r() __restrict__;
> > >   void cr() const __restrict__;
> > >   void cv() const volatile;
> > >   void vr() volatile __restrict__;
> > >   void cvr() const volatile __restrict__;
> > > ```
> > > ```
> > > void test_diagnostics(const volatile X0 &__restrict__ cvr) {
> > >   cvr.g(); // expected-error {{not marked const, volatile, or restrict}}  -- actually produces "not marked const or volatile"
> > >   cvr.c(); // expected-error {{not marked volatile or restrict}}  -- actually produces "not marked volatile"
> > >   cvr.v(); // expected-error {{not marked const or restrict}}  -- actually produces "not marked const"
> > >   cvr.r(); // expected-error {{not marked const or volatile}}
> > >   cvr.cr(); // expected-error {{not marked volatile}}
> > >   cvr.cv(); // expected-error {{not marked restrict}}  -- actually produces no error
> > >   cvr.vr(); // expected-error {{not marked const}}
> > >   cvr.cvr();
> > > }
> > > ```
> > Given that `restrict` is a Cism, it's entirely possible that it's not really supported as a member function qualifier. In that case, one more test for `const volatile` should be sufficient.
> Note that you might want to test it regardless, to not miss if it starts to warn for some reason.
I was able to trigger the error with `__restrict`:

```
struct A { void f(); };
struct B
{
	void g() __restrict { return a.f(); }
	//                           ^
	// error: 'this' argument to member function 'f' has type
	//   '__restrict A', but function is not marked restrict
	A a;
};
```

Discovered this when I tried to optimize some code. Unfortunately this doesn't do what I wanted, since qualifiers on a function apply to the pointee of `this`, not `this` itself, which has `const` cv-qualifier. Converting the implicit `this` into an explicit argument we get:

```
void Bg(__restrict B *const); // error: restrict requires a pointer or reference ('B' is invalid)
```

so my original code should also be rejected by the parser. Indeed a type `__restrict A` can't exist. And if the parser does that, the `restrict` part is probably just dead: the pointee of `this` can't be `restrict` since it's a class type, and never a pointer type.


Repository:
  rC Clang

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D39937/new/

https://reviews.llvm.org/D39937



More information about the cfe-commits mailing list