ObjectiveC [QoI] issue warning if an element of an nsarray

expresison is a concatenated nsstring element.
// rdar://14303083

llvm-svn: 188332
This commit is contained in:
Fariborz Jahanian 2013-08-13 23:44:55 +00:00
parent 2e27459d6c
commit a802c3526b
4 changed files with 21 additions and 4 deletions

View File

@ -552,6 +552,7 @@ def ObjCCocoaAPI : DiagGroup<"objc-cocoa-api", [
]>;
def ObjCStringComparison : DiagGroup<"objc-string-compare">;
def ObjCStringConcatenation : DiagGroup<"objc-string-concatenation">;
def ObjCLiteralComparison : DiagGroup<"objc-literal-compare", [
ObjCStringComparison
]>;

View File

@ -1898,6 +1898,9 @@ def warn_missing_atsign_prefix : Warning<
def warn_objc_string_literal_comparison : Warning<
"direct comparison of a string literal has undefined behavior">,
InGroup<ObjCStringComparison>;
def warn_concatenated_nsarray_literal : Warning<
"concatenated nsstring literal for an nsarray expression">,
InGroup<ObjCStringConcatenation>;
def note_objc_literal_comparison_isequal : Note<
"use 'isEqual:' instead">;

View File

@ -324,7 +324,8 @@ ExprResult Sema::ActOnObjCBoolLiteral(SourceLocation AtLoc,
/// \brief Check that the given expression is a valid element of an Objective-C
/// collection literal.
static ExprResult CheckObjCCollectionLiteralElement(Sema &S, Expr *Element,
QualType T) {
QualType T,
bool ArrayLiteral = false) {
// If the expression is type-dependent, there's nothing for us to do.
if (Element->isTypeDependent())
return Element;
@ -401,14 +402,20 @@ static ExprResult CheckObjCCollectionLiteralElement(Sema &S, Expr *Element,
Recovered = true;
}
}
if (!Recovered) {
S.Diag(Element->getLocStart(), diag::err_invalid_collection_element)
<< Element->getType();
return ExprError();
}
}
if (ArrayLiteral)
if (ObjCStringLiteral *getString = dyn_cast<ObjCStringLiteral>(OrigElement)) {
if (getString->getString() && getString->getString()->getNumConcatenated() > 1)
S.Diag(Element->getLocStart(), diag::warn_concatenated_nsarray_literal)
<< Element->getType();
}
// Make sure that the element has the type that the container factory
// function expects.
return S.PerformCopyInitialization(
@ -710,7 +717,7 @@ ExprResult Sema::BuildObjCArrayLiteral(SourceRange SR, MultiExprArg Elements) {
for (unsigned I = 0, N = Elements.size(); I != N; ++I) {
ExprResult Converted = CheckObjCCollectionLiteralElement(*this,
ElementsBuffer[I],
RequiredType);
RequiredType, true);
if (Converted.isInvalid())
return ExprError();

View File

@ -39,3 +39,9 @@ int main() {
const char *blah;
NSArray *array2 = @[blah]; // expected-error{{collection element of type 'const char *' is not an Objective-C object}}
}
// rdar://14303083
id Test14303083() {
id obj = @[ @"A", (@"B" @"C")];
return @[ @"A", @"B" @"C"]; // expected-warning {{concatenated nsstring literal for an nsarray expression}}
}