diff options
author | Richard Smith <richard-llvm@metafoo.co.uk> | 2012-04-10 01:32:12 +0000 |
---|---|---|
committer | Richard Smith <richard-llvm@metafoo.co.uk> | 2012-04-10 01:32:12 +0000 |
commit | 6ee326af4e77e6f05973486097884d7431f2108d (patch) | |
tree | def0e1b57abc33f0654ba903dec1f37715442417 /test/SemaCXX | |
parent | 0e9bf71c6187da074fd6d382a7b1d11fd9ddf3dd (diff) |
Disambiguation of '[[':
* In C++11, '[[' is ill-formed unless it starts an attribute-specifier. Reject
array sizes and array indexes which begin with a lambda-expression. Recover by
parsing the lambda as a lambda.
* In Objective-C++11, either '[' could be the start of a message-send.
Fully disambiguate this case: it turns out that the grammars of message-sends,
lambdas and attributes do not actually overlap. Accept any occurrence of '[['
where either '[' starts a message send, but reject a lambda in an array index
just like in C++11 mode.
Implement a couple of changes to the attribute wording which occurred after our
attributes implementation landed:
* In a function-declaration, the attributes go after the exception specification,
not after the right paren.
* A reference type can have attributes applied.
* An 'identifier' in an attribute can also be a keyword. Support for alternative
tokens (iso646 keywords) in attributes to follow.
And some bug fixes:
* Parse attributes after declarator-ids, even if they are not simple identifiers.
* Do not accept attributes after a parenthesized declarator.
* Accept attributes after an array size in a new-type-id.
* Partially disamiguate 'delete' followed by a lambda. More work is required
here for the case where the lambda-introducer is '[]'.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@154369 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'test/SemaCXX')
-rw-r--r-- | test/SemaCXX/new-delete-0x.cpp | 32 | ||||
-rw-r--r-- | test/SemaCXX/new-delete.cpp | 3 |
2 files changed, 33 insertions, 2 deletions
diff --git a/test/SemaCXX/new-delete-0x.cpp b/test/SemaCXX/new-delete-0x.cpp new file mode 100644 index 0000000000..dcc2e9b8b1 --- /dev/null +++ b/test/SemaCXX/new-delete-0x.cpp @@ -0,0 +1,32 @@ +// RUN: %clang_cc1 -fsyntax-only -verify %s -triple=i686-pc-linux-gnu -std=c++11 + +using size_t = decltype(sizeof(0)); +struct noreturn_t {} constexpr noreturn = {}; + +void *operator new [[noreturn]] (size_t, noreturn_t); +void operator delete [[noreturn]] (void*, noreturn_t); + +void good_news() +{ + auto p = new int[2][[]]; + auto q = new int[[]][2]; + auto r = new int*[[]][2][[]]; + auto s = new (int(*[[]])[2][[]]); +} + +void bad_news(int *ip) +{ + // attribute-specifiers can go almost anywhere in a new-type-id... + auto r = new int[[]{return 1;}()][2]; // expected-error {{expected ']'}} + auto s = new int*[[]{return 1;}()][2]; // expected-error {{expected ']'}} + // ... but not here: + auto t = new (int(*)[[]]); // expected-error {{an attribute list cannot appear here}} + auto u = new (int(*)[[]{return 1;}()][2]); // expected-error {{C++11 only allows consecutive left square brackets when introducing an attribute}} expected-error {{variably modified type}} +} + +void good_deletes() +{ + delete [&]{ return (int*)0; }(); + // FIXME: This appears to be legal. + delete []{ return (int*)0; }(); // unexpected-error {{expected expression}} +} diff --git a/test/SemaCXX/new-delete.cpp b/test/SemaCXX/new-delete.cpp index 88d85ca792..e77e3d652f 100644 --- a/test/SemaCXX/new-delete.cpp +++ b/test/SemaCXX/new-delete.cpp @@ -102,8 +102,7 @@ void good_deletes() void bad_deletes() { delete 0; // expected-error {{cannot delete expression of type 'int'}} - delete [0] (int*)0; // expected-error {{expected ']'}} \ - // expected-note {{to match this '['}} + delete [0] (int*)0; // expected-error {{expected expression}} delete (void*)0; // expected-warning {{cannot delete expression with pointer-to-'void' type 'void *'}} delete (T*)0; // expected-warning {{deleting pointer to incomplete type}} ::S::delete (int*)0; // expected-error {{expected unqualified-id}} |