зеркало из https://github.com/microsoft/clang.git
Tweak VariadicMethodTypeChecker to only create one ExplodedNode when issuing multiple warnings for the same message expression.
Also add a test case showing that we correctly report multiple warnings for the same message expression. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@127605 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Родитель
9fc90c1bf7
Коммит
6fb5c1faca
|
@ -502,10 +502,7 @@ public:
|
|||
bool
|
||||
VariadicMethodTypeChecker::isVariadicMessage(const ObjCMessage &msg) const {
|
||||
const ObjCMethodDecl *MD = msg.getMethodDecl();
|
||||
if (!MD)
|
||||
return false;
|
||||
|
||||
if (!MD->isVariadic())
|
||||
if (!MD || !MD->isVariadic())
|
||||
return false;
|
||||
|
||||
Selector S = msg.getSelector();
|
||||
|
@ -586,13 +583,19 @@ void VariadicMethodTypeChecker::checkPreObjCMessage(ObjCMessage msg,
|
|||
return;
|
||||
|
||||
// Verify that all arguments have Objective-C types.
|
||||
llvm::Optional<ExplodedNode*> errorNode;
|
||||
|
||||
for (unsigned I = variadicArgsBegin; I != variadicArgsEnd; ++I) {
|
||||
QualType ArgTy = msg.getArgType(I);
|
||||
if (ArgTy->isObjCObjectPointerType())
|
||||
continue;
|
||||
|
||||
ExplodedNode *N = C.generateNode();
|
||||
if (!N)
|
||||
// Generate only one error node to use for all bug reports.
|
||||
if (!errorNode.hasValue()) {
|
||||
errorNode = C.generateNode();
|
||||
}
|
||||
|
||||
if (!errorNode.getValue())
|
||||
continue;
|
||||
|
||||
llvm::SmallString<128> sbuf;
|
||||
|
@ -607,7 +610,8 @@ void VariadicMethodTypeChecker::checkPreObjCMessage(ObjCMessage msg,
|
|||
<< "' should be an Objective-C pointer type, not '"
|
||||
<< ArgTy.getAsString() << "'";
|
||||
|
||||
RangedBugReport *R = new RangedBugReport(*BT, os.str(), N);
|
||||
RangedBugReport *R = new RangedBugReport(*BT, os.str(),
|
||||
errorNode.getValue());
|
||||
R->addRange(msg.getArgSourceRange(I));
|
||||
C.EmitReport(R);
|
||||
}
|
||||
|
|
|
@ -63,7 +63,7 @@ typedef struct {} NSFastEnumerationState;
|
|||
void f(id a, id<P> b, C* c, C<P> *d) {
|
||||
[NSArray arrayWithObjects:@"Hello", a, b, c, d, nil];
|
||||
|
||||
[NSArray arrayWithObjects:@"Foo", "Bar", nil]; // expected-warning {{Argument to 'NSArray' method 'arrayWithObjects:' should be an Objective-C pointer type, not 'char *'}}
|
||||
[NSArray arrayWithObjects:@"Foo", "Bar", "Baz", nil]; // expected-warning 2 {{Argument to 'NSArray' method 'arrayWithObjects:' should be an Objective-C pointer type, not 'char *'}}
|
||||
[NSDictionary dictionaryWithObjectsAndKeys:@"Foo", "Bar", nil]; // expected-warning {{Argument to 'NSDictionary' method 'dictionaryWithObjectsAndKeys:' should be an Objective-C pointer type, not 'char *'}}
|
||||
[NSSet setWithObjects:@"Foo", "Bar", nil]; // expected-warning {{Argument to 'NSSet' method 'setWithObjects:' should be an Objective-C pointer type, not 'char *'}}
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче