Skip to content

Commit 2a02147

Browse files
authored
[clang] [Sema] Simplify Expr::isUnusedResultAWarning for CXXConstructExpr (#153116)
…Expr Two tests have new warnings because `warn_unused_result` is now respected for constructor temporaries. These tests were newly added in #112521 last year. This is good because the new behavior is better than the old. @Sirraide and @Mick235711 what do you think about it?
1 parent 5b2c3aa commit 2a02147

File tree

3 files changed

+14
-26
lines changed

3 files changed

+14
-26
lines changed

clang/lib/AST/Expr.cpp

Lines changed: 11 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -2805,32 +2805,20 @@ bool Expr::isUnusedResultAWarning(const Expr *&WarnE, SourceLocation &Loc,
28052805

28062806
case CXXTemporaryObjectExprClass:
28072807
case CXXConstructExprClass: {
2808-
if (const CXXRecordDecl *Type = getType()->getAsCXXRecordDecl()) {
2809-
const auto *WarnURAttr = Type->getAttr<WarnUnusedResultAttr>();
2810-
if (Type->hasAttr<WarnUnusedAttr>() ||
2811-
(WarnURAttr && WarnURAttr->IsCXX11NoDiscard())) {
2812-
WarnE = this;
2813-
Loc = getBeginLoc();
2814-
R1 = getSourceRange();
2815-
return true;
2816-
}
2817-
}
2818-
28192808
const auto *CE = cast<CXXConstructExpr>(this);
2820-
if (const CXXConstructorDecl *Ctor = CE->getConstructor()) {
2821-
const auto *WarnURAttr = Ctor->getAttr<WarnUnusedResultAttr>();
2822-
if (WarnURAttr && WarnURAttr->IsCXX11NoDiscard()) {
2823-
WarnE = this;
2824-
Loc = getBeginLoc();
2825-
R1 = getSourceRange();
2809+
const CXXRecordDecl *Type = getType()->getAsCXXRecordDecl();
28262810

2827-
if (unsigned NumArgs = CE->getNumArgs())
2828-
R2 = SourceRange(CE->getArg(0)->getBeginLoc(),
2829-
CE->getArg(NumArgs - 1)->getEndLoc());
2830-
return true;
2831-
}
2832-
}
2811+
if ((Type && Type->hasAttr<WarnUnusedAttr>()) ||
2812+
CE->hasUnusedResultAttr(Ctx)) {
2813+
WarnE = this;
2814+
Loc = getBeginLoc();
2815+
R1 = getSourceRange();
28332816

2817+
if (unsigned NumArgs = CE->getNumArgs())
2818+
R2 = SourceRange(CE->getArg(0)->getBeginLoc(),
2819+
CE->getArg(NumArgs - 1)->getEndLoc());
2820+
return true;
2821+
}
28342822
return false;
28352823
}
28362824

clang/test/CXX/dcl.dcl/dcl.attr/dcl.attr.nodiscard/p2.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -115,7 +115,7 @@ void usage() {
115115
S(); // expected-warning {{ignoring temporary created by a constructor declared with 'nodiscard' attribute}}
116116
S('A'); // expected-warning {{ignoring temporary created by a constructor declared with 'nodiscard' attribute: Don't let that S-Char go!}}
117117
S(1);
118-
S(2.2);
118+
S(2.2); // expected-warning {{ignoring temporary created by a constructor declared with 'gnu::warn_unused_result' attribute}}
119119
Y(); // expected-warning {{ignoring temporary of type 'Y' declared with 'nodiscard' attribute: Don't throw me away either!}}
120120
S s;
121121
ConvertTo{}; // expected-warning {{ignoring return value of type 'ConvertTo' declared with 'nodiscard' attribute: Don't throw me away!}}

clang/test/SemaCXX/warn-unused-result.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -309,7 +309,7 @@ void use() {
309309

310310
S<double>(2); // no warning
311311
S<int>(2); // expected-warning {{ignoring temporary of type 'S<int>' declared with 'nodiscard'}}
312-
S<const char>(2); // no warning (warn_unused_result does not diagnose constructor temporaries)
312+
S<const char>(2); // expected-warning {{ignoring temporary of type 'S<const char>' declared with 'clang::warn_unused_result' attribute}}
313313

314314
// function should take precedence over type
315315
obtain2(1.0); // expected-warning {{ignoring return value of function declared with 'nodiscard'}}
@@ -336,7 +336,7 @@ struct [[nodiscard]] G {
336336
void use2() {
337337
H{2}; // no warning
338338
H(2.0); // expected-warning {{ignoring temporary created by a constructor declared with 'nodiscard'}}
339-
H("Hello"); // no warning (warn_unused_result does not diagnose constructor temporaries)
339+
H("Hello"); // expected-warning {{ignoring temporary created by a constructor declared with 'warn_unused_result' attribute}}
340340

341341
// no warning for explicit cast to void
342342
(void)H(2);

0 commit comments

Comments
 (0)