Skip to content

Commit 8eb662e

Browse files
committed
After some discussion, conservatively extend our sentinel check to discard
casts, but still require the (casted) type to be a pointer. Fixes PR5685. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@103216 91177308-0d34-0410-b5e6-96231b3b80d8
1 parent 25a7678 commit 8eb662e

File tree

2 files changed

+20
-11
lines changed

2 files changed

+20
-11
lines changed

lib/Sema/SemaExpr.cpp

+13-10
Original file line numberDiff line numberDiff line change
@@ -160,16 +160,19 @@ void Sema::DiagnoseSentinelCalls(NamedDecl *D, SourceLocation Loc,
160160
++sentinel;
161161
}
162162
Expr *sentinelExpr = Args[sentinel];
163-
if (sentinelExpr && (!isa<GNUNullExpr>(sentinelExpr) &&
164-
!sentinelExpr->isTypeDependent() &&
165-
!sentinelExpr->isValueDependent() &&
166-
(!sentinelExpr->getType()->isPointerType() ||
167-
!sentinelExpr->isNullPointerConstant(Context,
168-
Expr::NPC_ValueDependentIsNull)))) {
169-
Diag(Loc, diag::warn_missing_sentinel) << isMethod;
170-
Diag(D->getLocation(), diag::note_sentinel_here) << isMethod;
171-
}
172-
return;
163+
if (!sentinelExpr) return;
164+
if (sentinelExpr->isTypeDependent()) return;
165+
if (sentinelExpr->isValueDependent()) return;
166+
if (sentinelExpr->getType()->isPointerType() &&
167+
sentinelExpr->IgnoreParenCasts()->isNullPointerConstant(Context,
168+
Expr::NPC_ValueDependentIsNull))
169+
return;
170+
171+
// Unfortunately, __null has type 'int'.
172+
if (isa<GNUNullExpr>(sentinelExpr)) return;
173+
174+
Diag(Loc, diag::warn_missing_sentinel) << isMethod;
175+
Diag(D->getLocation(), diag::note_sentinel_here) << isMethod;
173176
}
174177

175178
SourceRange Sema::getExprRange(ExprTy *E) const {

test/Sema/attr-sentinel.c

+7-1
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44

55
#define ATTR __attribute__ ((__sentinel__))
66

7-
void foo1 (int x, ...) ATTR; // expected-note {{function has been explicitly marked sentinel here}}
7+
void foo1 (int x, ...) ATTR; // expected-note 2 {{function has been explicitly marked sentinel here}}
88
void foo5 (int x, ...) __attribute__ ((__sentinel__(1))); // expected-note {{function has been explicitly marked sentinel here}}
99
void foo6 (int x, ...) __attribute__ ((__sentinel__(5))); // expected-note {{function has been explicitly marked sentinel here}}
1010
void foo7 (int x, ...) __attribute__ ((__sentinel__(0))); // expected-note {{function has been explicitly marked sentinel here}}
@@ -24,6 +24,12 @@ void test1() {
2424
foo7(1, NULL); // OK
2525

2626
foo12(1); // expected-warning {{not enough variable arguments in 'foo12' declaration to fit a sentinel}}
27+
28+
// PR 5685
29+
struct A {};
30+
struct A a, b, c;
31+
foo1(3, &a, &b, &c); // expected-warning {{missing sentinel in function call}}
32+
foo1(3, &a, &b, &c, (struct A*) 0);
2733
}
2834

2935

0 commit comments

Comments
 (0)