Bug 1214037 - Don't consider the result of an assignment expression MOZ_MUST_USE, r=ehsan

This commit is contained in:
Michael Layzell 2015-10-14 14:14:28 -04:00
parent d4beae866a
commit 24a4505d6d
2 changed files with 49 additions and 1 deletions

View File

@ -224,6 +224,33 @@ bool isInterestingDeclForImplicitConversion(const Decl *decl) {
return !isInIgnoredNamespaceForImplicitConversion(decl) &&
!isIgnoredPathForImplicitConversion(decl);
}
bool isIgnoredExprForMustUse(const Expr *E) {
if (const CXXOperatorCallExpr *OpCall = dyn_cast<CXXOperatorCallExpr>(E)) {
switch (OpCall->getOperator()) {
case OO_Equal:
case OO_PlusEqual:
case OO_MinusEqual:
case OO_StarEqual:
case OO_SlashEqual:
case OO_PercentEqual:
case OO_CaretEqual:
case OO_AmpEqual:
case OO_PipeEqual:
case OO_LessLessEqual:
case OO_GreaterGreaterEqual:
return true;
default:
return false;
}
}
if (const BinaryOperator *Op = dyn_cast<BinaryOperator>(E)) {
return Op->isAssignmentOp();
}
return false;
}
}
class CustomTypeAnnotation {
@ -320,7 +347,7 @@ public:
const Expr *E = dyn_cast_or_null<Expr>(stmt);
if (E) {
QualType T = E->getType();
if (MustUse.hasEffectiveAnnotation(T)) {
if (MustUse.hasEffectiveAnnotation(T) && !isIgnoredExprForMustUse(E)) {
unsigned errorID = Diag.getDiagnosticIDs()->getCustomDiagID(
DiagnosticIDs::Error, "Unused value of must-use type %0");

View File

@ -20,12 +20,15 @@ void use(MayUse&&);
void use(bool);
void foo() {
MustUse u;
producesMustUse(); // expected-error {{Unused value of must-use type 'MustUse'}}
producesMustUsePointer();
producesMustUseRef(); // expected-error {{Unused value of must-use type 'MustUse'}}
producesMayUse();
producesMayUsePointer();
producesMayUseRef();
u = producesMustUse();
{
producesMustUse(); // expected-error {{Unused value of must-use type 'MustUse'}}
producesMustUsePointer();
@ -33,6 +36,7 @@ void foo() {
producesMayUse();
producesMayUsePointer();
producesMayUseRef();
u = producesMustUse();
}
if (true) {
producesMustUse(); // expected-error {{Unused value of must-use type 'MustUse'}}
@ -41,6 +45,7 @@ void foo() {
producesMayUse();
producesMayUsePointer();
producesMayUseRef();
u = producesMustUse();
} else {
producesMustUse(); // expected-error {{Unused value of must-use type 'MustUse'}}
producesMustUsePointer();
@ -48,6 +53,7 @@ void foo() {
producesMayUse();
producesMayUsePointer();
producesMayUseRef();
u = producesMustUse();
}
if(true) producesMustUse(); // expected-error {{Unused value of must-use type 'MustUse'}}
@ -62,6 +68,8 @@ void foo() {
else producesMayUsePointer();
if(true) producesMayUseRef();
else producesMayUseRef();
if(true) u = producesMustUse();
else u = producesMustUse();
while (true) producesMustUse(); // expected-error {{Unused value of must-use type 'MustUse'}}
while (true) producesMustUsePointer();
@ -69,6 +77,7 @@ void foo() {
while (true) producesMayUse();
while (true) producesMayUsePointer();
while (true) producesMayUseRef();
while (true) u = producesMustUse();
do producesMustUse(); // expected-error {{Unused value of must-use type 'MustUse'}}
while (true);
@ -82,6 +91,8 @@ void foo() {
while (true);
do producesMayUseRef();
while (true);
do u = producesMustUse();
while (true);
for (;;) producesMustUse(); // expected-error {{Unused value of must-use type 'MustUse'}}
for (;;) producesMustUsePointer();
@ -89,6 +100,7 @@ void foo() {
for (;;) producesMayUse();
for (;;) producesMayUsePointer();
for (;;) producesMayUseRef();
for (;;) u = producesMustUse();
for (producesMustUse();;); // expected-error {{Unused value of must-use type 'MustUse'}}
for (producesMustUsePointer();;);
@ -96,6 +108,7 @@ void foo() {
for (producesMayUse();;);
for (producesMayUsePointer();;);
for (producesMayUseRef();;);
for (u = producesMustUse();;);
for (;;producesMustUse()); // expected-error {{Unused value of must-use type 'MustUse'}}
for (;;producesMustUsePointer());
@ -103,6 +116,7 @@ void foo() {
for (;;producesMayUse());
for (;;producesMayUsePointer());
for (;;producesMayUseRef());
for (;;u = producesMustUse());
use((producesMustUse(), false)); // expected-error {{Unused value of must-use type 'MustUse'}}
use((producesMustUsePointer(), false));
@ -110,6 +124,7 @@ void foo() {
use((producesMayUse(), false));
use((producesMayUsePointer(), false));
use((producesMayUseRef(), false));
use((u = producesMustUse(), false));
switch (1) {
case 1:
@ -119,6 +134,7 @@ void foo() {
producesMayUse();
producesMayUsePointer();
producesMayUseRef();
u = producesMustUse();
case 2:
producesMustUse(); // expected-error {{Unused value of must-use type 'MustUse'}}
case 3:
@ -131,6 +147,8 @@ void foo() {
producesMayUsePointer();
case 7:
producesMayUseRef();
case 8:
u = producesMustUse();
default:
producesMustUse(); // expected-error {{Unused value of must-use type 'MustUse'}}
producesMustUsePointer();
@ -138,6 +156,7 @@ void foo() {
producesMayUse();
producesMayUsePointer();
producesMayUseRef();
u = producesMustUse();
}
use(producesMustUse());
@ -146,6 +165,7 @@ void foo() {
use(producesMayUse());
use(producesMayUsePointer());
use(producesMayUseRef());
use(u = producesMustUse());
MustUse a = producesMustUse();
MustUse *b = producesMustUsePointer();
@ -153,4 +173,5 @@ void foo() {
MayUse d = producesMayUse();
MayUse *e = producesMayUsePointer();
MayUse &f = producesMayUseRef();
MustUse g = u = producesMustUse();
}