[clang] a7eaaba - [Parser] Parse string literal arguments of 'availability', 'external_source_symbol' and 'uuid' attributes as unevaluated
Sergei Barannikov via cfe-commits
cfe-commits at lists.llvm.org
Wed Aug 30 01:47:05 PDT 2023
Author: Sergei Barannikov
Date: 2023-08-30T11:46:54+03:00
New Revision: a7eaaba69906d3305752cb738332b9365e666def
URL: https://github.com/llvm/llvm-project/commit/a7eaaba69906d3305752cb738332b9365e666def
DIFF: https://github.com/llvm/llvm-project/commit/a7eaaba69906d3305752cb738332b9365e666def.diff
LOG: [Parser] Parse string literal arguments of 'availability', 'external_source_symbol' and 'uuid' attributes as unevaluated
This is a complementary to D156237.
These attributes have custom parsing logic.
Reviewed By: cor3ntin
Differential Revision: https://reviews.llvm.org/D159024
Added:
Modified:
clang/lib/Parse/ParseDecl.cpp
clang/lib/Parse/ParseDeclCXX.cpp
clang/test/Parser/attr-availability-xcore.c
clang/test/Parser/attr-availability.c
clang/test/Parser/attr-external-source-symbol.m
clang/test/Parser/ms-square-bracket-attributes.mm
Removed:
################################################################################
diff --git a/clang/lib/Parse/ParseDecl.cpp b/clang/lib/Parse/ParseDecl.cpp
index 8daa33a2a7b5b8..7c27a02ee4af62 100644
--- a/clang/lib/Parse/ParseDecl.cpp
+++ b/clang/lib/Parse/ParseDecl.cpp
@@ -1316,31 +1316,19 @@ void Parser::ParseAvailabilityAttribute(
}
ConsumeToken();
if (Keyword == Ident_message || Keyword == Ident_replacement) {
- if (Tok.isNot(tok::string_literal)) {
+ if (!isTokenStringLiteral()) {
Diag(Tok, diag::err_expected_string_literal)
<< /*Source='availability attribute'*/2;
SkipUntil(tok::r_paren, StopAtSemi);
return;
}
- if (Keyword == Ident_message)
- MessageExpr = ParseStringLiteralExpression();
- else
- ReplacementExpr = ParseStringLiteralExpression();
- // Also reject wide string literals.
- if (StringLiteral *MessageStringLiteral =
- cast_or_null<StringLiteral>(MessageExpr.get())) {
- if (!MessageStringLiteral->isOrdinary()) {
- Diag(MessageStringLiteral->getSourceRange().getBegin(),
- diag::err_expected_string_literal)
- << /*Source='availability attribute'*/ 2;
- SkipUntil(tok::r_paren, StopAtSemi);
- return;
- }
- }
- if (Keyword == Ident_message)
+ if (Keyword == Ident_message) {
+ MessageExpr = ParseUnevaluatedStringLiteralExpression();
break;
- else
+ } else {
+ ReplacementExpr = ParseUnevaluatedStringLiteralExpression();
continue;
+ }
}
// Special handling of 'NA' only when applied to introduced or
@@ -1508,7 +1496,7 @@ void Parser::ParseExternalSourceSymbolAttribute(
else
HasDefinedIn = true;
- if (Tok.isNot(tok::string_literal)) {
+ if (!isTokenStringLiteral()) {
Diag(Tok, diag::err_expected_string_literal)
<< /*Source='external_source_symbol attribute'*/ 3
<< /*language | source container | USR*/ (
@@ -1522,27 +1510,27 @@ void Parser::ParseExternalSourceSymbolAttribute(
if (HadLanguage) {
Diag(KeywordLoc, diag::err_external_source_symbol_duplicate_clause)
<< Keyword;
- ParseStringLiteralExpression();
+ ParseUnevaluatedStringLiteralExpression();
continue;
}
- Language = ParseStringLiteralExpression();
+ Language = ParseUnevaluatedStringLiteralExpression();
} else if (Keyword == Ident_USR) {
if (HadUSR) {
Diag(KeywordLoc, diag::err_external_source_symbol_duplicate_clause)
<< Keyword;
- ParseStringLiteralExpression();
+ ParseUnevaluatedStringLiteralExpression();
continue;
}
- USR = ParseStringLiteralExpression();
+ USR = ParseUnevaluatedStringLiteralExpression();
} else {
assert(Keyword == Ident_defined_in && "Invalid clause keyword!");
if (HadDefinedIn) {
Diag(KeywordLoc, diag::err_external_source_symbol_duplicate_clause)
<< Keyword;
- ParseStringLiteralExpression();
+ ParseUnevaluatedStringLiteralExpression();
continue;
}
- DefinedInExpr = ParseStringLiteralExpression();
+ DefinedInExpr = ParseUnevaluatedStringLiteralExpression();
}
} while (TryConsumeToken(tok::comma));
diff --git a/clang/lib/Parse/ParseDeclCXX.cpp b/clang/lib/Parse/ParseDeclCXX.cpp
index 186a5e61a8fa32..730b6e55246d6b 100644
--- a/clang/lib/Parse/ParseDeclCXX.cpp
+++ b/clang/lib/Parse/ParseDeclCXX.cpp
@@ -4715,9 +4715,9 @@ void Parser::ParseMicrosoftUuidAttributeArgs(ParsedAttributes &Attrs) {
}
ArgsVector ArgExprs;
- if (Tok.is(tok::string_literal)) {
+ if (isTokenStringLiteral()) {
// Easy case: uuid("...") -- quoted string.
- ExprResult StringResult = ParseStringLiteralExpression();
+ ExprResult StringResult = ParseUnevaluatedStringLiteralExpression();
if (StringResult.isInvalid())
return;
ArgExprs.push_back(StringResult.get());
@@ -4772,7 +4772,7 @@ void Parser::ParseMicrosoftUuidAttributeArgs(ParsedAttributes &Attrs) {
Toks[0].setLiteralData(StrBuffer.data());
Toks[0].setLength(StrBuffer.size());
StringLiteral *UuidString =
- cast<StringLiteral>(Actions.ActOnStringLiteral(Toks, nullptr).get());
+ cast<StringLiteral>(Actions.ActOnUnevaluatedStringLiteral(Toks).get());
ArgExprs.push_back(UuidString);
}
diff --git a/clang/test/Parser/attr-availability-xcore.c b/clang/test/Parser/attr-availability-xcore.c
index 0b354a3d01e805..6bc1f45c8ed9fa 100644
--- a/clang/test/Parser/attr-availability-xcore.c
+++ b/clang/test/Parser/attr-availability-xcore.c
@@ -6,6 +6,6 @@
# error 'availability' attribute is not available
#endif
-void f7() __attribute__((availability(macosx,message=L"wide"))); // expected-error {{expected string literal for optional message in 'availability' attribute}}
+void f7() __attribute__((availability(macosx,message=L"wide"))); // expected-warning {{encoding prefix 'L' on an unevaluated string literal has no effect}}
-void f8() __attribute__((availability(macosx,message="a" L"b"))); // expected-error {{expected string literal for optional message in 'availability' attribute}}
+void f8() __attribute__((availability(macosx,message="a" L"b"))); // expected-warning {{encoding prefix 'L' on an unevaluated string literal has no effect}}
diff --git a/clang/test/Parser/attr-availability.c b/clang/test/Parser/attr-availability.c
index 71e80bd0b29f59..aab0f2f3a852a9 100644
--- a/clang/test/Parser/attr-availability.c
+++ b/clang/test/Parser/attr-availability.c
@@ -18,17 +18,17 @@ void f5(void) __attribute__((availability(macosx,introduced=10.5), availability(
void f6(void) __attribute__((availability(macosx,unavailable,introduced=10.5))); // expected-warning{{'unavailable' availability overrides all other availability information}}
-void f7(void) __attribute__((availability(macosx,message=L"wide"))); // expected-error {{expected string literal for optional message in 'availability' attribute}}
+void f7(void) __attribute__((availability(macosx,message=L"wide"))); // expected-warning {{encoding prefix 'L' on an unevaluated string literal has no effect}}
-void f8(void) __attribute__((availability(macosx,message="a" L"b"))); // expected-error {{expected string literal for optional message in 'availability' attribute}}
+void f8(void) __attribute__((availability(macosx,message="a" L"b"))); // expected-warning {{encoding prefix 'L' on an unevaluated string literal has no effect}}
-void f9(void) __attribute__((availability(macosx,message=u8"b"))); // expected-error {{expected string literal for optional message in 'availability' attribute}}
+void f9(void) __attribute__((availability(macosx,message=u8"b"))); // expected-warning {{encoding prefix 'u8' on an unevaluated string literal has no effect}}
-void f10(void) __attribute__((availability(macosx,message="a" u8"b"))); // expected-error {{expected string literal for optional message in 'availability' attribute}}
+void f10(void) __attribute__((availability(macosx,message="a" u8"b"))); // expected-warning {{encoding prefix 'u8' on an unevaluated string literal has no effect}}
-void f11(void) __attribute__((availability(macosx,message=u"b"))); // expected-error {{expected string literal for optional message in 'availability' attribute}}
+void f11(void) __attribute__((availability(macosx,message=u"b"))); // expected-warning {{encoding prefix 'u' on an unevaluated string literal has no effect}}
-void f12(void) __attribute__((availability(macosx,message="a" u"b"))); // expected-error {{expected string literal for optional message in 'availability' attribute}}
+void f12(void) __attribute__((availability(macosx,message="a" u"b"))); // expected-warning {{encoding prefix 'u' on an unevaluated string literal has no effect}}
enum E{
gorf __attribute__((availability(macosx,introduced=8.5, message = 10.0))), // expected-error {{expected string literal for optional message in 'availability' attribute}}
diff --git a/clang/test/Parser/attr-external-source-symbol.m b/clang/test/Parser/attr-external-source-symbol.m
index b94cb3a628145f..329c820371f1d1 100644
--- a/clang/test/Parser/attr-external-source-symbol.m
+++ b/clang/test/Parser/attr-external-source-symbol.m
@@ -95,6 +95,27 @@ void f27(void)
void f28(void)
__attribute__((external_source_symbol(USR="")));
+void f29(void)
+__attribute__((external_source_symbol(language=L"Swift"))); // expected-warning {{encoding prefix 'L' on an unevaluated string literal has no effect}}
+
+void f30(void)
+__attribute__((external_source_symbol(language="Swift", language=L"Swift"))); // expected-error {{duplicate 'language' clause in an 'external_source_symbol' attribute}} \
+ // expected-warning {{encoding prefix 'L' on an unevaluated string literal has no effect}}
+
+void f31(void)
+__attribute__((external_source_symbol(USR=u"foo"))); // expected-warning {{encoding prefix 'u' on an unevaluated string literal has no effect}}
+
+void f32(void)
+__attribute__((external_source_symbol(USR="foo", USR=u"foo"))); // expected-error {{duplicate 'USR' clause in an 'external_source_symbol' attribute}} \
+ // expected-warning {{encoding prefix 'u' on an unevaluated string literal has no effect}}
+
+void f33(void)
+__attribute__((external_source_symbol(defined_in=U"module"))); // expected-warning {{encoding prefix 'U' on an unevaluated string literal has no effect}}
+
+void f34(void)
+__attribute__((external_source_symbol(defined_in="module", defined_in=U"module"))); // expected-error {{duplicate 'defined_in' clause in an 'external_source_symbol' attribute}} \
+ // expected-warning {{encoding prefix 'U' on an unevaluated string literal has no effect}}
+
#if __has_attribute(external_source_symbol) != 20230206
# error "invalid __has_attribute version"
#endif
diff --git a/clang/test/Parser/ms-square-bracket-attributes.mm b/clang/test/Parser/ms-square-bracket-attributes.mm
index c1fc14cec563d3..6c4923dfa43310 100644
--- a/clang/test/Parser/ms-square-bracket-attributes.mm
+++ b/clang/test/Parser/ms-square-bracket-attributes.mm
@@ -17,9 +17,9 @@
)] struct struct_with_uuid_brace;
// uuids must be ascii string literals.
-// expected-error at +1 {{uuid attribute contains a malformed GUID}}
+// expected-warning at +1 {{encoding prefix 'u8' on an unevaluated string literal has no effect and is incompatible with c++2c}}
[uuid(u8"000000A0-0000-0000-C000-000000000049")] struct struct_with_uuid_u8;
-// expected-error at +1 {{uuid attribute contains a malformed GUID}}
+// expected-warning at +1 {{encoding prefix 'L' on an unevaluated string literal has no effect and is incompatible with c++2c}}
[uuid(L"000000A0-0000-0000-C000-000000000049")] struct struct_with_uuid_L;
// cl.exe doesn't allow raw string literals in []-style attributes, but does
More information about the cfe-commits
mailing list