Skip to content

Commit 21dc8df

Browse files
committed
Turn Wdeprecated-literal-operator on by default
It would be nice to see what our users think about this change, as this is something that WG21/EWG quite wants to fix a handful of questionable issues with UB. Depending on the outcome of this after being committed, we might instead suggest EWG undeprecate this, and require a bit of 'magic' from the lexer. Additionally, this patch makes it so we emit this diagnostic ALSO in cases where the literal name is reserved. It doesn't make sense to limit that.
1 parent ee4dd14 commit 21dc8df

33 files changed

+237
-202
lines changed

clang/docs/ReleaseNotes.rst

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -99,6 +99,20 @@ C++ Specific Potentially Breaking Changes
9999
// Was error, now evaluates to false.
100100
constexpr bool b = f() == g();
101101
102+
- The warning ``-Wdeprecated-literal-operator`` is now on by default, as this is
103+
something that WG21 has shown interest in removing from the language. The
104+
result is that anyone who is compiling with ``-Werror`` should see this
105+
diagnostic. To fix this diagnostic, simply removing the space character from
106+
between the ``operator""`` and the user defined literal name will make the
107+
source no longer deprecated. This is consistent with CWG2521.
108+
109+
.. code-block:: c++
110+
111+
// Now diagnoses by default.
112+
unsigned operator"" _udl_name(unsigned long long);
113+
// Fixed version:
114+
unsigned operator""_udl_name(unsigned long long);
115+
102116
ABI Changes in This Version
103117
---------------------------
104118

@@ -216,6 +230,10 @@ Resolutions to C++ Defect Reports
216230
- Clang now allows trailing requires clause on explicit deduction guides.
217231
(`CWG2707: Deduction guides cannot have a trailing requires-clause <https://cplusplus.github.io/CWG/issues/2707.html>`_).
218232

233+
- Clang now diagnoses a space in the first production of a ``literal-operator-id``
234+
by default.
235+
(`CWG2521: User-defined literals and reserved identifiers <https://cplusplus.github.io/CWG/issues/2521.html>`_).
236+
219237
C Language Changes
220238
------------------
221239

@@ -378,6 +396,10 @@ Improvements to Clang's diagnostics
378396

379397
- Clang now emits a diagnostic note at the class declaration when the method definition does not match any declaration (#GH110638).
380398

399+
- Clang now emits a ``-Wdepredcated-literal-operator`` diagnostic, even if the
400+
name was a reserved name, which we improperly allowed to suppress the
401+
diagnostic.
402+
381403
Improvements to Clang's time-trace
382404
----------------------------------
383405

clang/include/clang/Basic/DiagnosticSemaKinds.td

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -439,7 +439,7 @@ def warn_reserved_extern_symbol: Warning<
439439
InGroup<ReservedIdentifier>, DefaultIgnore;
440440
def warn_deprecated_literal_operator_id: Warning<
441441
"identifier %0 preceded by whitespace in a literal operator declaration "
442-
"is deprecated">, InGroup<DeprecatedLiteralOperator>, DefaultIgnore;
442+
"is deprecated">, InGroup<DeprecatedLiteralOperator>;
443443
def warn_reserved_module_name : Warning<
444444
"%0 is a reserved name for a module">, InGroup<ReservedModuleIdentifier>;
445445
def warn_import_implementation_partition_unit_in_interface_unit : Warning<

clang/lib/Sema/SemaExprCXX.cpp

Lines changed: 10 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -503,17 +503,16 @@ bool Sema::checkLiteralOperatorId(const CXXScopeSpec &SS,
503503
const IdentifierInfo *II = Name.Identifier;
504504
ReservedIdentifierStatus Status = II->isReserved(PP.getLangOpts());
505505
SourceLocation Loc = Name.getEndLoc();
506-
if (!PP.getSourceManager().isInSystemHeader(Loc)) {
507-
if (auto Hint = FixItHint::CreateReplacement(
508-
Name.getSourceRange(),
509-
(StringRef("operator\"\"") + II->getName()).str());
510-
isReservedInAllContexts(Status)) {
511-
Diag(Loc, diag::warn_reserved_extern_symbol)
512-
<< II << static_cast<int>(Status) << Hint;
513-
} else {
514-
Diag(Loc, diag::warn_deprecated_literal_operator_id) << II << Hint;
515-
}
516-
}
506+
507+
auto Hint = FixItHint::CreateReplacement(
508+
Name.getSourceRange(),
509+
(StringRef("operator\"\"") + II->getName()).str());
510+
511+
Diag(Loc, diag::warn_deprecated_literal_operator_id) << II << Hint;
512+
513+
if (isReservedInAllContexts(Status))
514+
Diag(Loc, diag::warn_reserved_extern_symbol)
515+
<< II << static_cast<int>(Status) << Hint;
517516
}
518517

519518
if (!SS.isValid())

clang/test/CXX/drs/cwg14xx.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -627,7 +627,7 @@ int i = N::f();
627627

628628
namespace cwg1479 { // cwg1479: 3.1
629629
#if __cplusplus >= 201103L
630-
int operator"" _a(const char*, std::size_t = 0);
630+
int operator""_a(const char*, std::size_t = 0);
631631
// since-cxx11-error@-1 {{literal operator cannot have a default argument}}
632632
#endif
633633
}

clang/test/CXX/drs/cwg17xx.cpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -203,6 +203,9 @@ namespace cwg1762 { // cwg1762: 14
203203
float operator ""E(const char *);
204204
// since-cxx11-error@-1 {{invalid suffix on literal; C++11 requires a space between literal and identifier}}
205205
// since-cxx11-warning@-2 {{user-defined literal suffixes not starting with '_' are reserved; no literal will invoke this operator}}
206+
// since-cxx11-warning@-3 {{identifier 'E' preceded by whitespace in a literal operator declaration is deprecated}}
207+
// FIXME: We could probably do a better job reacting to the fixit here, the
208+
// fact that we complain about the space we added is a little strange.
206209
#endif
207210
}
208211

clang/test/CXX/drs/cwg25xx.cpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,9 @@ operator"" _div();
8888
using ::cwg2521::operator"" _\u03C0___;
8989
using ::cwg2521::operator""_div;
9090
// since-cxx11-warning@-2 {{identifier '_π___' preceded by whitespace in a literal operator declaration is deprecated}}
91+
92+
long double operator"" _RESERVED(long double);
93+
// since-cxx11-warning@-1 {{identifier '_RESERVED' preceded by whitespace in a literal operator declaration is deprecated}}
9194
#pragma clang diagnostic pop
9295
#endif
9396
} // namespace cwg2521

clang/test/CXX/lex/lex.literal/lex.ext/p1.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
// RUN: %clang_cc1 -fsyntax-only -std=c++11 -verify %s
1+
// RUN: %clang_cc1 -fsyntax-only -std=c++11 -Wno-deprecated-literal-operator -verify %s
22

33
void operator "" p31(long double); // expected-warning{{user-defined literal suffixes not starting with '_' are reserved}}
44
void operator "" _p31(long double);

clang/test/CXX/lex/lex.literal/lex.ext/p10.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
// RUN: %clang_cc1 -std=c++11 -verify %s
1+
// RUN: %clang_cc1 -std=c++11 -Wno-deprecated-literal-operator -verify %s
22

33
using size_t = decltype(sizeof(int));
44
void operator "" wibble(const char *); // expected-warning {{user-defined literal suffixes not starting with '_' are reserved; no literal will invoke this operator}}

clang/test/CXX/lex/lex.literal/lex.ext/p11.cpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,16 +6,16 @@ template<typename T, typename U> struct same_type;
66
template<typename T> struct same_type<T, T> {};
77
template<typename T> using X = T;
88
template<typename CharT, X<CharT>...>
9-
int operator "" _x(); // expected-warning {{string literal operator templates are a GNU extension}}
9+
int operator ""_x(); // expected-warning {{string literal operator templates are a GNU extension}}
1010
template<char...>
11-
double operator "" _x();
11+
double operator ""_x();
1212

1313
auto a="string"_x;
1414
auto b=42_x;
1515
same_type<decltype(a), int> test_a;
1616
same_type<decltype(b), double> test_b;
1717

18-
char operator "" _x(const char *begin, size_t size);
18+
char operator ""_x(const char *begin, size_t size);
1919
auto c="string"_x;
2020
auto d=L"string"_x;
2121
same_type<decltype(c), char> test_c;
Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,18 @@
11
// RUN: %clang_cc1 -fsyntax-only -std=c++11 -verify %s
22

3-
int &operator "" _x1 (unsigned long long);
3+
int &operator ""_x1 (unsigned long long);
44
int &i1 = 0x123_x1;
55

6-
double &operator "" _x1 (const char *);
6+
double &operator ""_x1 (const char *);
77
int &i2 = 45_x1;
88

9-
template<char...> char &operator "" _x1 ();
9+
template<char...> char &operator ""_x1 ();
1010
int &i3 = 0377_x1;
1111

1212
int &i4 = 90000000000000000000000000000000000000000000000_x1; // expected-error {{integer literal is too large to be represented in any integer type}}
1313

14-
double &operator "" _x2 (const char *);
14+
double &operator ""_x2 (const char *);
1515
double &i5 = 123123123123123123123123123123123123123123123_x2;
1616

17-
template<char...Cs> constexpr int operator "" _x3() { return sizeof...(Cs); }
17+
template<char...Cs> constexpr int operator ""_x3() { return sizeof...(Cs); }
1818
static_assert(123456789012345678901234567890123456789012345678901234567890_x3 == 60, "");

0 commit comments

Comments
 (0)