LLVM Bugzilla is read-only and represents the historical archive of all LLVM issues filled before November 26, 2021. Use github to submit LLVM bugs

Bug 17747 - member function `void foo() __restrict__;` incorrectly applies restrict to type, not pointer
Summary: member function `void foo() __restrict__;` incorrectly applies restrict to ty...
Status: NEW
Alias: None
Product: clang
Classification: Unclassified
Component: C++ (show other bugs)
Version: trunk
Hardware: PC Linux
: P normal
Assignee: Unassigned Clang Bugs
URL:
Keywords:
: 17793 (view as bug list)
Depends on:
Blocks:
 
Reported: 2013-10-30 23:07 PDT by Sean Silva
Modified: 2020-10-19 02:27 PDT (History)
5 users (show)

See Also:
Fixed By Commit(s):


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Sean Silva 2013-10-30 23:07:15 PDT
struct Foo {
  void member() __restrict__ {
    Foo *__restrict__ This = this;
  }
};

Clang gives the diagnostic:

test.cpp:3:23: error: cannot initialize a variable of type 'Foo *restrict' with
      an rvalue of type 'restrict Foo *'
    Foo *__restrict__ This = this;
                      ^      ~~~~
1 error generated.

Clang seems to think that `this` has type `restrict Foo *` (restrict on Foo, rather than the pointer)

The GCC extension says:

<http://gcc.gnu.org/onlinedocs/gcc/Restricted-Pointers.html#Restricted-Pointers>

"Within the body of T::fn, this has the effective definition T *__restrict__ const this."
Comment 1 Richard Smith 2013-11-03 21:36:24 PST
*** Bug 17793 has been marked as a duplicate of this bug. ***
Comment 2 Reid Kleckner 2018-02-26 13:41:53 PST
I ran into this again while working on debug info, and wrote up a long bug report to discover that it was a duplicate.

See also https://bugs.llvm.org/show_bug.cgi?id=10667.
Comment 3 Ian Mallett 2020-10-19 02:27:43 PDT
I also ran into this bug, and also wrote up a long bug report to discover that it was a duplicate.  So, I'll try to add a bit more information.  This bug is almost 7 years old now!

So first, this still occurs in Clang trunk 12.0.0 (but way earlier also; I checked as far back as 3.0.0).  I can't give a cleaner example than the OP, but I will comment that Clang's error message is, specifically:

    <source>:3:23: error: cannot initialize a variable of type 'Foo *__restrict' with an rvalue of type '__restrict Foo *'
        Foo *__restrict__ This = this;
                          ^      ~~~~

It is also worth noting the GCC, MSVC, ICC, and possibly others all do not suffer from this problem.

As has been mentioned, the bug is that Clang appears to think that the type of `this` is `Foo __restrict__*` (that is, a pointer to a restrict-qualified `Foo` object, not a restrict-qualified pointer to a `Foo` object).  This, of course, makes no sense.  Restrict-qualification is a pointer thing.  Indeed, in other contexts, even *writing* such a type is sensibly impossible.  E.g. the following line will correctly fail:

    Foo __restrict* foo = nullptr; //fails (correctly)

Note: while `__restrict` is not a C++ keyword, when applied to C++ member functions, it is widely implemented as the `this` pointer becoming restrict-qualified.  That seems to be what Clang attempted here, but got the type incorrect.

Note: a C-style cast works around this problem, but obviously this is not a solution.