SemaChecking.cpp revision f871d0cc377a1367b519a6cce26be74607566eba
159907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner//===--- SemaChecking.cpp - Extra Semantic Checking -----------------------===// 259907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner// 359907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner// The LLVM Compiler Infrastructure 459907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner// 50bc735ffcfb223c0186419547abaa5c84482663eChris Lattner// This file is distributed under the University of Illinois Open Source 60bc735ffcfb223c0186419547abaa5c84482663eChris Lattner// License. See LICENSE.TXT for details. 759907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner// 859907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner//===----------------------------------------------------------------------===// 959907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner// 101eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump// This file implements extra semantic analysis beyond what is enforced 1159907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner// by the C type system. 1259907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner// 1359907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner//===----------------------------------------------------------------------===// 1459907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner 1559907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner#include "Sema.h" 16826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek#include "clang/Analysis/Analyses/FormatString.h" 1759907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner#include "clang/AST/ASTContext.h" 18199c3d6cd16aebbb9c7f0d42af9d922c9628bf70Ken Dyck#include "clang/AST/CharUnits.h" 19c4a1dea2dc56bd1357ec91b829a0b9e68229a13eDaniel Dunbar#include "clang/AST/DeclObjC.h" 202324512285caac0332bbbc6e4cab6245d2a370a1Ted Kremenek#include "clang/AST/ExprCXX.h" 217ff22b259d4d4729f701679e3a7f0e242365e07fTed Kremenek#include "clang/AST/ExprObjC.h" 22f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump#include "clang/AST/DeclObjC.h" 23f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump#include "clang/AST/StmtCXX.h" 24f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump#include "clang/AST/StmtObjC.h" 25719e61573f27c11057ecfe0dd8f141621602c571Chris Lattner#include "clang/Lex/LiteralSupport.h" 2659907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner#include "clang/Lex/Preprocessor.h" 27f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump#include "llvm/ADT/BitVector.h" 28f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump#include "llvm/ADT/STLExtras.h" 290d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman#include "llvm/ADT/StringExtras.h" 303bfc5f49e0e37e235bb0d33bcbcb36af9d1f84abTom Care#include "llvm/Support/raw_ostream.h" 31691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher#include "clang/Basic/TargetBuiltins.h" 3226a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman#include "clang/Basic/TargetInfo.h" 33a1f3dba77b7418575c1ff539ffa74ebaa068280cZhongxing Xu#include <limits> 3459907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattnerusing namespace clang; 3559907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner 3660800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner/// getLocationOfStringLiteralByte - Return a source location that points to the 3760800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner/// specified byte of the specified string literal. 3860800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner/// 3960800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner/// Strings are amazingly complex. They can be formed from multiple tokens and 4060800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner/// can have escape sequences in them in addition to the usual trigraph and 4160800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner/// escaped newline business. This routine handles this complexity. 4260800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner/// 4360800081361b0ffc114877b8abbc81cb57b4edf6Chris LattnerSourceLocation Sema::getLocationOfStringLiteralByte(const StringLiteral *SL, 4460800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner unsigned ByteNo) const { 4560800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner assert(!SL->isWide() && "This doesn't work for wide strings yet"); 461eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4760800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner // Loop over all of the tokens in this string until we find the one that 4860800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner // contains the byte we're looking for. 4960800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner unsigned TokNo = 0; 5060800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner while (1) { 5160800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner assert(TokNo < SL->getNumConcatenated() && "Invalid byte number!"); 5260800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner SourceLocation StrTokLoc = SL->getStrTokenLoc(TokNo); 531eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 5460800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner // Get the spelling of the string so that we can get the data that makes up 5560800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner // the string literal, not the identifier for the macro it is potentially 5660800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner // expanded through. 5760800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner SourceLocation StrTokSpellingLoc = SourceMgr.getSpellingLoc(StrTokLoc); 5860800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner 5960800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner // Re-lex the token to get its length and original spelling. 6060800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner std::pair<FileID, unsigned> LocInfo = 6160800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner SourceMgr.getDecomposedLoc(StrTokSpellingLoc); 62f715ca12bfc9fddfde75f98a197424434428b821Douglas Gregor bool Invalid = false; 63f6ac97b101c8840efa92bf29166077ce4049e293Benjamin Kramer llvm::StringRef Buffer = SourceMgr.getBufferData(LocInfo.first, &Invalid); 64f715ca12bfc9fddfde75f98a197424434428b821Douglas Gregor if (Invalid) 65aea67dbd653a2dd6dd5cc2159279e81e855b2482Douglas Gregor return StrTokSpellingLoc; 66aea67dbd653a2dd6dd5cc2159279e81e855b2482Douglas Gregor 67f6ac97b101c8840efa92bf29166077ce4049e293Benjamin Kramer const char *StrData = Buffer.data()+LocInfo.second; 681eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 6960800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner // Create a langops struct and enable trigraphs. This is sufficient for 7060800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner // relexing tokens. 7160800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner LangOptions LangOpts; 7260800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner LangOpts.Trigraphs = true; 731eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 7460800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner // Create a lexer starting at the beginning of this token. 75f6ac97b101c8840efa92bf29166077ce4049e293Benjamin Kramer Lexer TheLexer(StrTokSpellingLoc, LangOpts, Buffer.begin(), StrData, 76f6ac97b101c8840efa92bf29166077ce4049e293Benjamin Kramer Buffer.end()); 7760800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner Token TheTok; 7860800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner TheLexer.LexFromRawLexer(TheTok); 791eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 80443e53c7845f01c8ed693ccd137abb0bd76564f6Chris Lattner // Use the StringLiteralParser to compute the length of the string in bytes. 81b90f4b3fb94056609da9cca5eef7358d95a363b2Douglas Gregor StringLiteralParser SLP(&TheTok, 1, PP, /*Complain=*/false); 82443e53c7845f01c8ed693ccd137abb0bd76564f6Chris Lattner unsigned TokNumBytes = SLP.GetStringLength(); 831eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 842197c963543397777919cec22b65feb31a9ddf79Chris Lattner // If the byte is in this token, return the location of the byte. 8560800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner if (ByteNo < TokNumBytes || 8660800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner (ByteNo == TokNumBytes && TokNo == SL->getNumConcatenated())) { 871eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump unsigned Offset = 88b90f4b3fb94056609da9cca5eef7358d95a363b2Douglas Gregor StringLiteralParser::getOffsetOfStringByte(TheTok, ByteNo, PP, 89b90f4b3fb94056609da9cca5eef7358d95a363b2Douglas Gregor /*Complain=*/false); 901eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 91719e61573f27c11057ecfe0dd8f141621602c571Chris Lattner // Now that we know the offset of the token in the spelling, use the 92719e61573f27c11057ecfe0dd8f141621602c571Chris Lattner // preprocessor to get the offset in the original source. 93719e61573f27c11057ecfe0dd8f141621602c571Chris Lattner return PP.AdvanceToTokenCharacter(StrTokLoc, Offset); 9460800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner } 951eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 9660800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner // Move to the next string token. 9760800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner ++TokNo; 9860800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner ByteNo -= TokNumBytes; 9960800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner } 10060800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner} 10160800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner 1024403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn/// CheckablePrintfAttr - does a function call have a "printf" attribute 1034403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn/// and arguments that merit checking? 1044403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynnbool Sema::CheckablePrintfAttr(const FormatAttr *Format, CallExpr *TheCall) { 1054403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn if (Format->getType() == "printf") return true; 1064403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn if (Format->getType() == "printf0") { 1074403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn // printf0 allows null "format" string; if so don't check format/args 1084403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn unsigned format_idx = Format->getFormatIdx() - 1; 1094a2614e94672c47395abcde60518776fbebec589Sebastian Redl // Does the index refer to the implicit object argument? 1104a2614e94672c47395abcde60518776fbebec589Sebastian Redl if (isa<CXXMemberCallExpr>(TheCall)) { 1114a2614e94672c47395abcde60518776fbebec589Sebastian Redl if (format_idx == 0) 1124a2614e94672c47395abcde60518776fbebec589Sebastian Redl return false; 1134a2614e94672c47395abcde60518776fbebec589Sebastian Redl --format_idx; 1144a2614e94672c47395abcde60518776fbebec589Sebastian Redl } 1154403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn if (format_idx < TheCall->getNumArgs()) { 1164403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn Expr *Format = TheCall->getArg(format_idx)->IgnoreParenCasts(); 117efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek if (!Format->isNullPointerConstant(Context, 118efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek Expr::NPC_ValueDependentIsNull)) 1194403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn return true; 1204403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn } 1214403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn } 1224403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn return false; 1234403a5e1f956fa86d515492dbe7c7a2817d8780dRyan Flynn} 12460800081361b0ffc114877b8abbc81cb57b4edf6Chris Lattner 1250eb23307222bda7ad95d968eac4e1ab30864b213Sebastian RedlAction::OwningExprResult 126d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders CarlssonSema::CheckBuiltinFunctionCall(unsigned BuiltinID, CallExpr *TheCall) { 1270eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl OwningExprResult TheCallResult(Owned(TheCall)); 1282def48394f6d48bde0dec2b514193c2b533265b5Douglas Gregor 129d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson switch (BuiltinID) { 13030ce344307f8a8b00054021307015571f83c7364Chris Lattner case Builtin::BI__builtin___CFStringMakeConstantString: 131925e60d3fa706f31886027c876989af79eb0e0d2Chris Lattner assert(TheCall->getNumArgs() == 1 && 1321b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner "Wrong # arguments to builtin CFStringMakeConstantString"); 133690398188ea5b428f06aa13c7d4ce6eb741ad4f9Chris Lattner if (CheckObjCString(TheCall->getArg(0))) 1340eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl return ExprError(); 135d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson break; 13649ff7a1c8c67d56e62d3b4627463b705c0d5008cTed Kremenek case Builtin::BI__builtin_stdarg_start: 13730ce344307f8a8b00054021307015571f83c7364Chris Lattner case Builtin::BI__builtin_va_start: 1380eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl if (SemaBuiltinVAStart(TheCall)) 1390eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl return ExprError(); 140d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson break; 1411b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner case Builtin::BI__builtin_isgreater: 1421b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner case Builtin::BI__builtin_isgreaterequal: 1431b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner case Builtin::BI__builtin_isless: 1441b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner case Builtin::BI__builtin_islessequal: 1451b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner case Builtin::BI__builtin_islessgreater: 1461b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner case Builtin::BI__builtin_isunordered: 1470eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl if (SemaBuiltinUnorderedCompare(TheCall)) 1480eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl return ExprError(); 149d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson break; 150e771a7ac11fb27f0e734e5de4d858f2c268895e5Benjamin Kramer case Builtin::BI__builtin_fpclassify: 151e771a7ac11fb27f0e734e5de4d858f2c268895e5Benjamin Kramer if (SemaBuiltinFPClassification(TheCall, 6)) 152e771a7ac11fb27f0e734e5de4d858f2c268895e5Benjamin Kramer return ExprError(); 153e771a7ac11fb27f0e734e5de4d858f2c268895e5Benjamin Kramer break; 1549ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman case Builtin::BI__builtin_isfinite: 1559ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman case Builtin::BI__builtin_isinf: 1569ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman case Builtin::BI__builtin_isinf_sign: 1579ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman case Builtin::BI__builtin_isnan: 1589ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman case Builtin::BI__builtin_isnormal: 1593b1e26b708e8d00d4ba10ff857201bae2aff6baeBenjamin Kramer if (SemaBuiltinFPClassification(TheCall, 1)) 1609ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman return ExprError(); 1619ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman break; 1626cfda23b3768f93a6eb0b2a9135c8334a20125bbEli Friedman case Builtin::BI__builtin_return_address: 163691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher case Builtin::BI__builtin_frame_address: { 164691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher llvm::APSInt Result; 165691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher if (SemaBuiltinConstantArg(TheCall, 0, Result)) 1660eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl return ExprError(); 167d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson break; 168691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher } 169691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher case Builtin::BI__builtin_eh_return_data_regno: { 170691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher llvm::APSInt Result; 171691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher if (SemaBuiltinConstantArg(TheCall, 0, Result)) 17221fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner return ExprError(); 17321fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner break; 174691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher } 175d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman case Builtin::BI__builtin_shufflevector: 1760eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl return SemaBuiltinShuffleVector(TheCall); 1770eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl // TheCall will be freed by the smart pointer here, but that's fine, since 1780eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl // SemaBuiltinShuffleVector guts it, but then doesn't release it. 1794493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar case Builtin::BI__builtin_prefetch: 1800eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl if (SemaBuiltinPrefetch(TheCall)) 1810eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl return ExprError(); 182d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson break; 183d5f8a4fd4d6dfb0415b93bb7ab721bba5cab1332Daniel Dunbar case Builtin::BI__builtin_object_size: 1840eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl if (SemaBuiltinObjectSize(TheCall)) 1850eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl return ExprError(); 186d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson break; 187d875fed28578835de89cd407e9db4be788596d7cEli Friedman case Builtin::BI__builtin_longjmp: 188d875fed28578835de89cd407e9db4be788596d7cEli Friedman if (SemaBuiltinLongjmp(TheCall)) 189d875fed28578835de89cd407e9db4be788596d7cEli Friedman return ExprError(); 190d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson break; 1915caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_fetch_and_add: 1925caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_fetch_and_sub: 1935caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_fetch_and_or: 1945caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_fetch_and_and: 1955caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_fetch_and_xor: 1965caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_add_and_fetch: 1975caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_sub_and_fetch: 1985caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_and_and_fetch: 1995caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_or_and_fetch: 2005caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_xor_and_fetch: 2015caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_val_compare_and_swap: 2025caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_bool_compare_and_swap: 2035caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_lock_test_and_set: 2045caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_lock_release: 205d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth return SemaBuiltinAtomicOverloaded(move(TheCallResult)); 20626a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman } 20726a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman 20826a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman // Since the target specific builtins for each arch overlap, only check those 20926a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman // of the arch we are compiling for. 21026a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman if (BuiltinID >= Builtin::FirstTSBuiltin) { 21126a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman switch (Context.Target.getTriple().getArch()) { 21226a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman case llvm::Triple::arm: 21326a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman case llvm::Triple::thumb: 21426a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman if (CheckARMBuiltinFunctionCall(BuiltinID, TheCall)) 21526a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman return ExprError(); 21626a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman break; 21726a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman case llvm::Triple::x86: 21826a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman case llvm::Triple::x86_64: 21926a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman if (CheckX86BuiltinFunctionCall(BuiltinID, TheCall)) 22026a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman return ExprError(); 22126a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman break; 22226a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman default: 22326a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman break; 22426a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman } 22526a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman } 22626a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman 22726a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman return move(TheCallResult); 22826a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman} 22926a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman 23026a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begemanbool Sema::CheckX86BuiltinFunctionCall(unsigned BuiltinID, CallExpr *TheCall) { 23126a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman switch (BuiltinID) { 232691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher case X86::BI__builtin_ia32_palignr128: 233691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher case X86::BI__builtin_ia32_palignr: { 234691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher llvm::APSInt Result; 235691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher if (SemaBuiltinConstantArg(TheCall, 2, Result)) 23626a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman return true; 237691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher break; 238691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher } 23971993dd85eed9cc42c6b2fa61ee5c53026b74817Anders Carlsson } 24026a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman return false; 24126a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman} 2421eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 24361eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman// Get the valid immediate range for the specified NEON type code. 24461eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begemanstatic unsigned RFT(unsigned t, bool shift = false) { 24561eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman bool quad = t & 0x10; 24661eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman 24761eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman switch (t & 0x7) { 24861eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman case 0: // i8 249d69ec16b1b03b4a97c571ff14f15769fe13c1e5aNate Begeman return shift ? 7 : (8 << (int)quad) - 1; 25061eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman case 1: // i16 251d69ec16b1b03b4a97c571ff14f15769fe13c1e5aNate Begeman return shift ? 15 : (4 << (int)quad) - 1; 25261eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman case 2: // i32 253d69ec16b1b03b4a97c571ff14f15769fe13c1e5aNate Begeman return shift ? 31 : (2 << (int)quad) - 1; 25461eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman case 3: // i64 255d69ec16b1b03b4a97c571ff14f15769fe13c1e5aNate Begeman return shift ? 63 : (1 << (int)quad) - 1; 25661eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman case 4: // f32 25761eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman assert(!shift && "cannot shift float types!"); 258d69ec16b1b03b4a97c571ff14f15769fe13c1e5aNate Begeman return (2 << (int)quad) - 1; 25961eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman case 5: // poly8 26061eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman assert(!shift && "cannot shift polynomial types!"); 261d69ec16b1b03b4a97c571ff14f15769fe13c1e5aNate Begeman return (8 << (int)quad) - 1; 26261eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman case 6: // poly16 26361eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman assert(!shift && "cannot shift polynomial types!"); 264d69ec16b1b03b4a97c571ff14f15769fe13c1e5aNate Begeman return (4 << (int)quad) - 1; 26561eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman case 7: // float16 26661eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman assert(!shift && "cannot shift float types!"); 267d69ec16b1b03b4a97c571ff14f15769fe13c1e5aNate Begeman return (4 << (int)quad) - 1; 26861eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman } 26961eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman return 0; 27061eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman} 27161eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman 27226a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begemanbool Sema::CheckARMBuiltinFunctionCall(unsigned BuiltinID, CallExpr *TheCall) { 2731c2a88cfaeb11227d3a6bf7204207e0c8cf6de6fNate Begeman llvm::APSInt Result; 2741c2a88cfaeb11227d3a6bf7204207e0c8cf6de6fNate Begeman 2750d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman unsigned mask = 0; 27661eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman unsigned TV = 0; 2771c2a88cfaeb11227d3a6bf7204207e0c8cf6de6fNate Begeman switch (BuiltinID) { 278a23326b5c244a03bf61ebb86db60a777ea26f926Nate Begeman#define GET_NEON_OVERLOAD_CHECK 279a23326b5c244a03bf61ebb86db60a777ea26f926Nate Begeman#include "clang/Basic/arm_neon.inc" 280a23326b5c244a03bf61ebb86db60a777ea26f926Nate Begeman#undef GET_NEON_OVERLOAD_CHECK 2811c2a88cfaeb11227d3a6bf7204207e0c8cf6de6fNate Begeman } 2821c2a88cfaeb11227d3a6bf7204207e0c8cf6de6fNate Begeman 2830d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman // For NEON intrinsics which are overloaded on vector element type, validate 2840d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman // the immediate which specifies which variant to emit. 2850d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman if (mask) { 2860d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman unsigned ArgNo = TheCall->getNumArgs()-1; 2870d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman if (SemaBuiltinConstantArg(TheCall, ArgNo, Result)) 2880d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman return true; 2890d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman 29061eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman TV = Result.getLimitedValue(32); 29161eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman if ((TV > 31) || (mask & (1 << TV)) == 0) 2920d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman return Diag(TheCall->getLocStart(), diag::err_invalid_neon_type_code) 2930d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman << TheCall->getArg(ArgNo)->getSourceRange(); 2940d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman } 2951c2a88cfaeb11227d3a6bf7204207e0c8cf6de6fNate Begeman 2960d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman // For NEON intrinsics which take an immediate value as part of the 2970d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman // instruction, range check them here. 29861eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman unsigned i = 0, l = 0, u = 0; 2990d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman switch (BuiltinID) { 3000d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman default: return false; 301bb37f50c2d0d72e1fa5b349d5f6a11fdc5acb86eNate Begeman case ARM::BI__builtin_arm_ssat: i = 1; l = 1; u = 31; break; 302bb37f50c2d0d72e1fa5b349d5f6a11fdc5acb86eNate Begeman case ARM::BI__builtin_arm_usat: i = 1; u = 31; break; 30399c40bb13b523d58d7aeb6446e4f486d6918ca58Nate Begeman case ARM::BI__builtin_arm_vcvtr_f: 30499c40bb13b523d58d7aeb6446e4f486d6918ca58Nate Begeman case ARM::BI__builtin_arm_vcvtr_d: i = 1; u = 1; break; 305a23326b5c244a03bf61ebb86db60a777ea26f926Nate Begeman#define GET_NEON_IMMEDIATE_CHECK 306a23326b5c244a03bf61ebb86db60a777ea26f926Nate Begeman#include "clang/Basic/arm_neon.inc" 307a23326b5c244a03bf61ebb86db60a777ea26f926Nate Begeman#undef GET_NEON_IMMEDIATE_CHECK 3080d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman }; 3090d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman 31061eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman // Check that the immediate argument is actually a constant. 3110d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman if (SemaBuiltinConstantArg(TheCall, i, Result)) 3120d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman return true; 3130d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman 31461eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman // Range check against the upper/lower values for this isntruction. 3150d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman unsigned Val = Result.getZExtValue(); 31661eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman if (Val < l || Val > (u + l)) 3170d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman return Diag(TheCall->getLocStart(), diag::err_argument_invalid_range) 31861eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman << llvm::utostr(l) << llvm::utostr(u+l) 31961eecf5aea018ea65c9ab0bccacd2996b15c632dNate Begeman << TheCall->getArg(i)->getSourceRange(); 3200d15c5321a11a5fee53b17ca8e9e0d72d6192b23Nate Begeman 32199c40bb13b523d58d7aeb6446e4f486d6918ca58Nate Begeman // FIXME: VFP Intrinsics should error if VFP not present. 32226a31428f130b66f61834d1b4d1cf72f590f70b9Nate Begeman return false; 323d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson} 324d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson 325d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson/// CheckFunctionCall - Check a direct function call for various correctness 326d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson/// and safety properties not strictly enforced by the C type system. 327d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlssonbool Sema::CheckFunctionCall(FunctionDecl *FDecl, CallExpr *TheCall) { 328d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson // Get the IdentifierInfo* for the called function. 329d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson IdentifierInfo *FnInfo = FDecl->getIdentifier(); 330de45428f923b38d80407dbb9ede0df504256f9f6Daniel Dunbar 331d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson // None of the checks below are needed for functions that don't have 332d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson // simple names (e.g., C++ conversion functions). 333d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson if (!FnInfo) 334d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson return false; 3351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 336de45428f923b38d80407dbb9ede0df504256f9f6Daniel Dunbar // FIXME: This mechanism should be abstracted to be less fragile and 337de45428f923b38d80407dbb9ede0df504256f9f6Daniel Dunbar // more efficient. For example, just map function ids to custom 338de45428f923b38d80407dbb9ede0df504256f9f6Daniel Dunbar // handlers. 339de45428f923b38d80407dbb9ede0df504256f9f6Daniel Dunbar 34059907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner // Printf checking. 34140b598eea1310ec9ed554d56ce3e25b34c585458Argyrios Kyrtzidis if (const FormatAttr *Format = FDecl->getAttr<FormatAttr>()) { 342826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const bool b = Format->getType() == "scanf"; 343826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek if (b || CheckablePrintfAttr(Format, TheCall)) { 3443d692df4b9c58895f9843b03543ec57447c93679Ted Kremenek bool HasVAListArg = Format->getFirstArg() == 0; 345826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek CheckPrintfScanfArguments(TheCall, HasVAListArg, 346826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek Format->getFormatIdx() - 1, 347826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek HasVAListArg ? 0 : Format->getFirstArg() - 1, 348826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek !b); 3493c385e5f8d9008fff18597ca302be19fa86e51f6Douglas Gregor } 35059907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner } 3511eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 3521eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump for (const NonNullAttr *NonNull = FDecl->getAttr<NonNullAttr>(); NonNull; 353d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson NonNull = NonNull->getNext<NonNullAttr>()) 354d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson CheckNonNullArguments(NonNull, TheCall); 3550eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl 356d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson return false; 35771993dd85eed9cc42c6b2fa61ee5c53026b74817Anders Carlsson} 35871993dd85eed9cc42c6b2fa61ee5c53026b74817Anders Carlsson 359d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlssonbool Sema::CheckBlockCall(NamedDecl *NDecl, CallExpr *TheCall) { 360725165f2846bd37d3aaf863747fa30126992085eFariborz Jahanian // Printf checking. 36140b598eea1310ec9ed554d56ce3e25b34c585458Argyrios Kyrtzidis const FormatAttr *Format = NDecl->getAttr<FormatAttr>(); 362725165f2846bd37d3aaf863747fa30126992085eFariborz Jahanian if (!Format) 363d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson return false; 3641eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 365725165f2846bd37d3aaf863747fa30126992085eFariborz Jahanian const VarDecl *V = dyn_cast<VarDecl>(NDecl); 366725165f2846bd37d3aaf863747fa30126992085eFariborz Jahanian if (!V) 367d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson return false; 3681eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 369725165f2846bd37d3aaf863747fa30126992085eFariborz Jahanian QualType Ty = V->getType(); 370725165f2846bd37d3aaf863747fa30126992085eFariborz Jahanian if (!Ty->isBlockPointerType()) 371d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson return false; 3721eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 373826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const bool b = Format->getType() == "scanf"; 374826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek if (!b && !CheckablePrintfAttr(Format, TheCall)) 375d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson return false; 3761eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 377d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson bool HasVAListArg = Format->getFirstArg() == 0; 378826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek CheckPrintfScanfArguments(TheCall, HasVAListArg, Format->getFormatIdx() - 1, 379826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek HasVAListArg ? 0 : Format->getFirstArg() - 1, !b); 380d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson 381d406bf0e8c17012110a8476d03c6f9a97b56ecf7Anders Carlsson return false; 382725165f2846bd37d3aaf863747fa30126992085eFariborz Jahanian} 383725165f2846bd37d3aaf863747fa30126992085eFariborz Jahanian 3845caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner/// SemaBuiltinAtomicOverloaded - We have a call to a function like 3855caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner/// __sync_fetch_and_add, which is an overloaded function based on the pointer 3865caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner/// type of its first argument. The main ActOnCallExpr routines have already 3875caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner/// promoted the types of arguments because all of these calls are prototyped as 3885caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner/// void(...). 3895caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner/// 3905caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner/// This function goes through and does final semantic checking for these 3915caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner/// builtins, 392d201457cc781f1b13d0f4b1268ff934e6004cbffChandler CarruthSema::OwningExprResult 393d201457cc781f1b13d0f4b1268ff934e6004cbffChandler CarruthSema::SemaBuiltinAtomicOverloaded(OwningExprResult TheCallResult) { 394d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth CallExpr *TheCall = (CallExpr *)TheCallResult.get(); 3955caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner DeclRefExpr *DRE =cast<DeclRefExpr>(TheCall->getCallee()->IgnoreParenCasts()); 3965caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner FunctionDecl *FDecl = cast<FunctionDecl>(DRE->getDecl()); 3975caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner 3985caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // Ensure that we have at least one argument to do type inference from. 399d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth if (TheCall->getNumArgs() < 1) { 400d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth Diag(TheCall->getLocEnd(), diag::err_typecheck_call_too_few_args_at_least) 401d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth << 0 << 1 << TheCall->getNumArgs() 402d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth << TheCall->getCallee()->getSourceRange(); 403d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth return ExprError(); 404d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth } 4051eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4065caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // Inspect the first argument of the atomic builtin. This should always be 4075caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // a pointer type, whose element is an integral scalar or pointer type. 4085caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // Because it is a pointer type, we don't have to worry about any implicit 4095caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // casts here. 410d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth // FIXME: We don't allow floating point scalars as input. 4115caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner Expr *FirstArg = TheCall->getArg(0); 412d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth if (!FirstArg->getType()->isPointerType()) { 413d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth Diag(DRE->getLocStart(), diag::err_atomic_builtin_must_be_pointer) 414d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth << FirstArg->getType() << FirstArg->getSourceRange(); 415d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth return ExprError(); 416d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth } 4171eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 418d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth QualType ValType = 419d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth FirstArg->getType()->getAs<PointerType>()->getPointeeType(); 4201eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump if (!ValType->isIntegerType() && !ValType->isPointerType() && 421d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth !ValType->isBlockPointerType()) { 422d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth Diag(DRE->getLocStart(), diag::err_atomic_builtin_must_be_pointer_intptr) 423d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth << FirstArg->getType() << FirstArg->getSourceRange(); 424d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth return ExprError(); 425d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth } 4265caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner 4278d13d221cf7c1657404c611efaadf3ac19d899b3Chandler Carruth // The majority of builtins return a value, but a few have special return 4288d13d221cf7c1657404c611efaadf3ac19d899b3Chandler Carruth // types, so allow them to override appropriately below. 4298d13d221cf7c1657404c611efaadf3ac19d899b3Chandler Carruth QualType ResultType = ValType; 4308d13d221cf7c1657404c611efaadf3ac19d899b3Chandler Carruth 4315caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // We need to figure out which concrete builtin this maps onto. For example, 4325caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // __sync_fetch_and_add with a 2 byte object turns into 4335caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // __sync_fetch_and_add_2. 4345caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner#define BUILTIN_ROW(x) \ 4355caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner { Builtin::BI##x##_1, Builtin::BI##x##_2, Builtin::BI##x##_4, \ 4365caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner Builtin::BI##x##_8, Builtin::BI##x##_16 } 4371eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4385caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner static const unsigned BuiltinIndices[][5] = { 4395caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_fetch_and_add), 4405caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_fetch_and_sub), 4415caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_fetch_and_or), 4425caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_fetch_and_and), 4435caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_fetch_and_xor), 4441eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4455caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_add_and_fetch), 4465caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_sub_and_fetch), 4475caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_and_and_fetch), 4485caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_or_and_fetch), 4495caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_xor_and_fetch), 4501eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4515caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_val_compare_and_swap), 4525caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_bool_compare_and_swap), 4535caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_lock_test_and_set), 4545caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner BUILTIN_ROW(__sync_lock_release) 4555caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner }; 4561eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump#undef BUILTIN_ROW 4571eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4585caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // Determine the index of the size. 4595caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner unsigned SizeIndex; 460199c3d6cd16aebbb9c7f0d42af9d922c9628bf70Ken Dyck switch (Context.getTypeSizeInChars(ValType).getQuantity()) { 4615caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case 1: SizeIndex = 0; break; 4625caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case 2: SizeIndex = 1; break; 4635caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case 4: SizeIndex = 2; break; 4645caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case 8: SizeIndex = 3; break; 4655caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case 16: SizeIndex = 4; break; 4665caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner default: 467d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth Diag(DRE->getLocStart(), diag::err_atomic_builtin_pointer_size) 468d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth << FirstArg->getType() << FirstArg->getSourceRange(); 469d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth return ExprError(); 4705caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner } 4711eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4725caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // Each of these builtins has one pointer argument, followed by some number of 4735caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // values (0, 1 or 2) followed by a potentially empty varags list of stuff 4745caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // that we ignore. Find out which row of BuiltinIndices to read from as well 4755caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // as the number of fixed args. 4767814e6d6645d587891293d59ecf6576defcfac92Douglas Gregor unsigned BuiltinID = FDecl->getBuiltinID(); 4775caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner unsigned BuiltinIndex, NumFixed = 1; 4785caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner switch (BuiltinID) { 4795caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner default: assert(0 && "Unknown overloaded atomic builtin!"); 4805caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_fetch_and_add: BuiltinIndex = 0; break; 4815caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_fetch_and_sub: BuiltinIndex = 1; break; 4825caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_fetch_and_or: BuiltinIndex = 2; break; 4835caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_fetch_and_and: BuiltinIndex = 3; break; 4845caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_fetch_and_xor: BuiltinIndex = 4; break; 4851eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4867eff7c4153faf45b19b5919ef409ee5f6794eb25Daniel Dunbar case Builtin::BI__sync_add_and_fetch: BuiltinIndex = 5; break; 4877eff7c4153faf45b19b5919ef409ee5f6794eb25Daniel Dunbar case Builtin::BI__sync_sub_and_fetch: BuiltinIndex = 6; break; 4887eff7c4153faf45b19b5919ef409ee5f6794eb25Daniel Dunbar case Builtin::BI__sync_and_and_fetch: BuiltinIndex = 7; break; 4897eff7c4153faf45b19b5919ef409ee5f6794eb25Daniel Dunbar case Builtin::BI__sync_or_and_fetch: BuiltinIndex = 8; break; 4907eff7c4153faf45b19b5919ef409ee5f6794eb25Daniel Dunbar case Builtin::BI__sync_xor_and_fetch: BuiltinIndex = 9; break; 4911eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4925caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_val_compare_and_swap: 4937eff7c4153faf45b19b5919ef409ee5f6794eb25Daniel Dunbar BuiltinIndex = 10; 4945caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner NumFixed = 2; 4955caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner break; 4965caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_bool_compare_and_swap: 4977eff7c4153faf45b19b5919ef409ee5f6794eb25Daniel Dunbar BuiltinIndex = 11; 4985caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner NumFixed = 2; 4998d13d221cf7c1657404c611efaadf3ac19d899b3Chandler Carruth ResultType = Context.BoolTy; 5005caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner break; 5017eff7c4153faf45b19b5919ef409ee5f6794eb25Daniel Dunbar case Builtin::BI__sync_lock_test_and_set: BuiltinIndex = 12; break; 5025caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner case Builtin::BI__sync_lock_release: 5037eff7c4153faf45b19b5919ef409ee5f6794eb25Daniel Dunbar BuiltinIndex = 13; 5045caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner NumFixed = 0; 5058d13d221cf7c1657404c611efaadf3ac19d899b3Chandler Carruth ResultType = Context.VoidTy; 5065caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner break; 5075caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner } 5081eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 5095caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // Now that we know how many fixed arguments we expect, first check that we 5105caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // have at least that many. 511d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth if (TheCall->getNumArgs() < 1+NumFixed) { 512d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth Diag(TheCall->getLocEnd(), diag::err_typecheck_call_too_few_args_at_least) 513d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth << 0 << 1+NumFixed << TheCall->getNumArgs() 514d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth << TheCall->getCallee()->getSourceRange(); 515d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth return ExprError(); 516d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth } 5171eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 518e7ac0a94f1dee3fae9292eb8372962b6d70b3e0dChris Lattner // Get the decl for the concrete builtin from this, we can tell what the 519e7ac0a94f1dee3fae9292eb8372962b6d70b3e0dChris Lattner // concrete integer type we should convert to is. 520e7ac0a94f1dee3fae9292eb8372962b6d70b3e0dChris Lattner unsigned NewBuiltinID = BuiltinIndices[BuiltinIndex][SizeIndex]; 521e7ac0a94f1dee3fae9292eb8372962b6d70b3e0dChris Lattner const char *NewBuiltinName = Context.BuiltinInfo.GetName(NewBuiltinID); 522e7ac0a94f1dee3fae9292eb8372962b6d70b3e0dChris Lattner IdentifierInfo *NewBuiltinII = PP.getIdentifierInfo(NewBuiltinName); 5231eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump FunctionDecl *NewBuiltinDecl = 524e7ac0a94f1dee3fae9292eb8372962b6d70b3e0dChris Lattner cast<FunctionDecl>(LazilyCreateBuiltin(NewBuiltinII, NewBuiltinID, 525e7ac0a94f1dee3fae9292eb8372962b6d70b3e0dChris Lattner TUScope, false, DRE->getLocStart())); 526d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth 527f871d0cc377a1367b519a6cce26be74607566ebaJohn McCall // The first argument --- the pointer --- has a fixed type; we 528f871d0cc377a1367b519a6cce26be74607566ebaJohn McCall // deduce the types of the rest of the arguments accordingly. Walk 529f871d0cc377a1367b519a6cce26be74607566ebaJohn McCall // the remaining arguments, converting them to the deduced value type. 5305caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner for (unsigned i = 0; i != NumFixed; ++i) { 5315caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner Expr *Arg = TheCall->getArg(i+1); 5321eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 5335caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // If the argument is an implicit cast, then there was a promotion due to 5345caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // "...", just remove it now. 5355caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner if (ImplicitCastExpr *ICE = dyn_cast<ImplicitCastExpr>(Arg)) { 5365caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner Arg = ICE->getSubExpr(); 5375caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner ICE->setSubExpr(0); 5385caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner TheCall->setArg(i+1, Arg); 5395caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner } 5401eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 5415caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // GCC does an implicit conversion to the pointer or integer ValType. This 5425caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // can fail in some cases (1i -> int**), check for this error case now. 543cdb61979755c1c0699c1ee25eede9a50bf94d29bAnders Carlsson CastExpr::CastKind Kind = CastExpr::CK_Unknown; 544f871d0cc377a1367b519a6cce26be74607566ebaJohn McCall CXXCastPath BasePath; 5455cf86ba6b5a724bf91cb52feade1158f1fbeb605Anders Carlsson if (CheckCastTypes(Arg->getSourceRange(), ValType, Arg, Kind, BasePath)) 546d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth return ExprError(); 5471eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 5485caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // Okay, we have something that *can* be converted to the right type. Check 5495caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // to see if there is a potentially weird extension going on here. This can 5505caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // happen when you do an atomic operation on something like an char* and 5515caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // pass in 42. The 42 gets converted to char. This is even more strange 5525caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // for things like 45.123 -> char, etc. 5531eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // FIXME: Do this check. 554f871d0cc377a1367b519a6cce26be74607566ebaJohn McCall ImpCastExprToType(Arg, ValType, Kind, ImplicitCastExpr::RValue, &BasePath); 5555caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner TheCall->setArg(i+1, Arg); 5565caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner } 5571eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 5585caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // Switch the DeclRefExpr to refer to the new decl. 5595caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner DRE->setDecl(NewBuiltinDecl); 5605caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner DRE->setType(NewBuiltinDecl->getType()); 5611eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 5625caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // Set the callee in the CallExpr. 5635caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner // FIXME: This leaks the original parens and implicit casts. 5645caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner Expr *PromotedCall = DRE; 5655caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner UsualUnaryConversions(PromotedCall); 5665caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner TheCall->setCallee(PromotedCall); 5671eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 568db4325b098eff5e9e660db19f0148423fb21f27fChandler Carruth // Change the result type of the call to match the original value type. This 569db4325b098eff5e9e660db19f0148423fb21f27fChandler Carruth // is arbitrary, but the codegen for these builtins ins design to handle it 570db4325b098eff5e9e660db19f0148423fb21f27fChandler Carruth // gracefully. 5718d13d221cf7c1657404c611efaadf3ac19d899b3Chandler Carruth TheCall->setType(ResultType); 572d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth 573d201457cc781f1b13d0f4b1268ff934e6004cbffChandler Carruth return move(TheCallResult); 5745caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner} 5755caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner 5765caa370ea6f70bd3e7e4a9cc3b69ac1a849c8534Chris Lattner 577690398188ea5b428f06aa13c7d4ce6eb741ad4f9Chris Lattner/// CheckObjCString - Checks that the argument to the builtin 57871993dd85eed9cc42c6b2fa61ee5c53026b74817Anders Carlsson/// CFString constructor is correct 579fd942628abfe30e30427875db953222ae99b4325Steve Naroff/// FIXME: GCC currently emits the following warning: 5801eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// "warning: input conversion stopped due to an input byte that does not 581fd942628abfe30e30427875db953222ae99b4325Steve Naroff/// belong to the input codeset UTF-8" 582fd942628abfe30e30427875db953222ae99b4325Steve Naroff/// Note: It might also make sense to do the UTF-16 conversion here (would 583fd942628abfe30e30427875db953222ae99b4325Steve Naroff/// simplify the backend). 584690398188ea5b428f06aa13c7d4ce6eb741ad4f9Chris Lattnerbool Sema::CheckObjCString(Expr *Arg) { 58556f349400c5932a196509c0480ff6f99a9a0b48fChris Lattner Arg = Arg->IgnoreParenCasts(); 58671993dd85eed9cc42c6b2fa61ee5c53026b74817Anders Carlsson StringLiteral *Literal = dyn_cast<StringLiteral>(Arg); 58771993dd85eed9cc42c6b2fa61ee5c53026b74817Anders Carlsson 58871993dd85eed9cc42c6b2fa61ee5c53026b74817Anders Carlsson if (!Literal || Literal->isWide()) { 589fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner Diag(Arg->getLocStart(), diag::err_cfstring_literal_not_string_constant) 590fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner << Arg->getSourceRange(); 5919cdc4d3834f203dcde3ff274b8928e4620a914d5Anders Carlsson return true; 59271993dd85eed9cc42c6b2fa61ee5c53026b74817Anders Carlsson } 5931eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 594f015b034159d40e7033309e50036804eb1971787Daniel Dunbar const char *Data = Literal->getStrData(); 595f015b034159d40e7033309e50036804eb1971787Daniel Dunbar unsigned Length = Literal->getByteLength(); 596f015b034159d40e7033309e50036804eb1971787Daniel Dunbar 597f015b034159d40e7033309e50036804eb1971787Daniel Dunbar for (unsigned i = 0; i < Length; ++i) { 598f015b034159d40e7033309e50036804eb1971787Daniel Dunbar if (!Data[i]) { 599f015b034159d40e7033309e50036804eb1971787Daniel Dunbar Diag(getLocationOfStringLiteralByte(Literal, i), 600f015b034159d40e7033309e50036804eb1971787Daniel Dunbar diag::warn_cfstring_literal_contains_nul_character) 601f015b034159d40e7033309e50036804eb1971787Daniel Dunbar << Arg->getSourceRange(); 602f015b034159d40e7033309e50036804eb1971787Daniel Dunbar break; 603f015b034159d40e7033309e50036804eb1971787Daniel Dunbar } 604f015b034159d40e7033309e50036804eb1971787Daniel Dunbar } 6051eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 6069cdc4d3834f203dcde3ff274b8928e4620a914d5Anders Carlsson return false; 60759907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner} 60859907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner 609c27c665c88b49dfb212aedc7bab8b9bf67658b9eChris Lattner/// SemaBuiltinVAStart - Check the arguments to __builtin_va_start for validity. 610c27c665c88b49dfb212aedc7bab8b9bf67658b9eChris Lattner/// Emit an error and return true on failure, return false on success. 611925e60d3fa706f31886027c876989af79eb0e0d2Chris Lattnerbool Sema::SemaBuiltinVAStart(CallExpr *TheCall) { 612925e60d3fa706f31886027c876989af79eb0e0d2Chris Lattner Expr *Fn = TheCall->getCallee(); 613925e60d3fa706f31886027c876989af79eb0e0d2Chris Lattner if (TheCall->getNumArgs() > 2) { 6142c21a073525cdfa68e4439b7af551385dc2796abChris Lattner Diag(TheCall->getArg(2)->getLocStart(), 615fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner diag::err_typecheck_call_too_many_args) 616ccfa9639f8d09733bcf1c2572c5bd3daba5bd632Eric Christopher << 0 /*function call*/ << 2 << TheCall->getNumArgs() 617ccfa9639f8d09733bcf1c2572c5bd3daba5bd632Eric Christopher << Fn->getSourceRange() 6181eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump << SourceRange(TheCall->getArg(2)->getLocStart(), 619fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner (*(TheCall->arg_end()-1))->getLocEnd()); 62030ce344307f8a8b00054021307015571f83c7364Chris Lattner return true; 62130ce344307f8a8b00054021307015571f83c7364Chris Lattner } 62256f20ae1010aa71defd7572f660b41288c56cdd1Eli Friedman 62356f20ae1010aa71defd7572f660b41288c56cdd1Eli Friedman if (TheCall->getNumArgs() < 2) { 624d77b9a29651d748f0e30a8dad8969635fc04f725Eric Christopher return Diag(TheCall->getLocEnd(), 625d77b9a29651d748f0e30a8dad8969635fc04f725Eric Christopher diag::err_typecheck_call_too_few_args_at_least) 626d77b9a29651d748f0e30a8dad8969635fc04f725Eric Christopher << 0 /*function call*/ << 2 << TheCall->getNumArgs(); 62756f20ae1010aa71defd7572f660b41288c56cdd1Eli Friedman } 62856f20ae1010aa71defd7572f660b41288c56cdd1Eli Friedman 629c27c665c88b49dfb212aedc7bab8b9bf67658b9eChris Lattner // Determine whether the current function is variadic or not. 6309ea9bdbc14374f7bacdb50d3e52c664ff12150ffDouglas Gregor BlockScopeInfo *CurBlock = getCurBlock(); 631c27c665c88b49dfb212aedc7bab8b9bf67658b9eChris Lattner bool isVariadic; 632cd9c51433c06705645d1ee5a13da3c9a72d7d025Steve Naroff if (CurBlock) 633c71a4915ca216847599d03cab4ed1c5086b0eb43John McCall isVariadic = CurBlock->TheDecl->isVariadic(); 6349498d388810d284d3970aef0d69fa4d069fd6cafTed Kremenek else if (FunctionDecl *FD = getCurFunctionDecl()) 6359498d388810d284d3970aef0d69fa4d069fd6cafTed Kremenek isVariadic = FD->isVariadic(); 6369498d388810d284d3970aef0d69fa4d069fd6cafTed Kremenek else 63753d0ea5f5bfa647ec23418bf3a3b7c183b51e4bdArgyrios Kyrtzidis isVariadic = getCurMethodDecl()->isVariadic(); 6381eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 639c27c665c88b49dfb212aedc7bab8b9bf67658b9eChris Lattner if (!isVariadic) { 64030ce344307f8a8b00054021307015571f83c7364Chris Lattner Diag(Fn->getLocStart(), diag::err_va_start_used_in_non_variadic_function); 64130ce344307f8a8b00054021307015571f83c7364Chris Lattner return true; 64230ce344307f8a8b00054021307015571f83c7364Chris Lattner } 6431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 64430ce344307f8a8b00054021307015571f83c7364Chris Lattner // Verify that the second argument to the builtin is the last argument of the 64530ce344307f8a8b00054021307015571f83c7364Chris Lattner // current function or method. 64630ce344307f8a8b00054021307015571f83c7364Chris Lattner bool SecondArgIsLastNamedArgument = false; 647e2c14103dec39cbd24dac9d7b3e91277b109c14fAnders Carlsson const Expr *Arg = TheCall->getArg(1)->IgnoreParenCasts(); 6481eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 64988cf226caee50956ef47edd4d44cf7b80703a26cAnders Carlsson if (const DeclRefExpr *DR = dyn_cast<DeclRefExpr>(Arg)) { 65088cf226caee50956ef47edd4d44cf7b80703a26cAnders Carlsson if (const ParmVarDecl *PV = dyn_cast<ParmVarDecl>(DR->getDecl())) { 65130ce344307f8a8b00054021307015571f83c7364Chris Lattner // FIXME: This isn't correct for methods (results in bogus warning). 65230ce344307f8a8b00054021307015571f83c7364Chris Lattner // Get the last formal in the current function. 65388cf226caee50956ef47edd4d44cf7b80703a26cAnders Carlsson const ParmVarDecl *LastArg; 654cd9c51433c06705645d1ee5a13da3c9a72d7d025Steve Naroff if (CurBlock) 655cd9c51433c06705645d1ee5a13da3c9a72d7d025Steve Naroff LastArg = *(CurBlock->TheDecl->param_end()-1); 656cd9c51433c06705645d1ee5a13da3c9a72d7d025Steve Naroff else if (FunctionDecl *FD = getCurFunctionDecl()) 657371f258e61e1365b951b17931a3c5ac1530fd1a0Chris Lattner LastArg = *(FD->param_end()-1); 65830ce344307f8a8b00054021307015571f83c7364Chris Lattner else 65953d0ea5f5bfa647ec23418bf3a3b7c183b51e4bdArgyrios Kyrtzidis LastArg = *(getCurMethodDecl()->param_end()-1); 66030ce344307f8a8b00054021307015571f83c7364Chris Lattner SecondArgIsLastNamedArgument = PV == LastArg; 66130ce344307f8a8b00054021307015571f83c7364Chris Lattner } 66230ce344307f8a8b00054021307015571f83c7364Chris Lattner } 6631eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 66430ce344307f8a8b00054021307015571f83c7364Chris Lattner if (!SecondArgIsLastNamedArgument) 6651eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump Diag(TheCall->getArg(1)->getLocStart(), 66630ce344307f8a8b00054021307015571f83c7364Chris Lattner diag::warn_second_parameter_of_va_start_not_last_named_argument); 66730ce344307f8a8b00054021307015571f83c7364Chris Lattner return false; 6686cfda23b3768f93a6eb0b2a9135c8334a20125bbEli Friedman} 66930ce344307f8a8b00054021307015571f83c7364Chris Lattner 6701b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner/// SemaBuiltinUnorderedCompare - Handle functions like __builtin_isgreater and 6711b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner/// friends. This is declared to take (...), so we have to check everything. 672925e60d3fa706f31886027c876989af79eb0e0d2Chris Lattnerbool Sema::SemaBuiltinUnorderedCompare(CallExpr *TheCall) { 673925e60d3fa706f31886027c876989af79eb0e0d2Chris Lattner if (TheCall->getNumArgs() < 2) 6742c21a073525cdfa68e4439b7af551385dc2796abChris Lattner return Diag(TheCall->getLocEnd(), diag::err_typecheck_call_too_few_args) 675d77b9a29651d748f0e30a8dad8969635fc04f725Eric Christopher << 0 << 2 << TheCall->getNumArgs()/*function call*/; 676925e60d3fa706f31886027c876989af79eb0e0d2Chris Lattner if (TheCall->getNumArgs() > 2) 6771eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump return Diag(TheCall->getArg(2)->getLocStart(), 678fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner diag::err_typecheck_call_too_many_args) 679ccfa9639f8d09733bcf1c2572c5bd3daba5bd632Eric Christopher << 0 /*function call*/ << 2 << TheCall->getNumArgs() 680fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner << SourceRange(TheCall->getArg(2)->getLocStart(), 681fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner (*(TheCall->arg_end()-1))->getLocEnd()); 6821eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 683925e60d3fa706f31886027c876989af79eb0e0d2Chris Lattner Expr *OrigArg0 = TheCall->getArg(0); 684925e60d3fa706f31886027c876989af79eb0e0d2Chris Lattner Expr *OrigArg1 = TheCall->getArg(1); 685cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor 6861b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner // Do standard promotions between the two arguments, returning their common 6871b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner // type. 688925e60d3fa706f31886027c876989af79eb0e0d2Chris Lattner QualType Res = UsualArithmeticConversions(OrigArg0, OrigArg1, false); 689403bc2bd9edffe51d73776643fa87696c9417678Daniel Dunbar 690403bc2bd9edffe51d73776643fa87696c9417678Daniel Dunbar // Make sure any conversions are pushed back into the call; this is 691403bc2bd9edffe51d73776643fa87696c9417678Daniel Dunbar // type safe since unordered compare builtins are declared as "_Bool 692403bc2bd9edffe51d73776643fa87696c9417678Daniel Dunbar // foo(...)". 693403bc2bd9edffe51d73776643fa87696c9417678Daniel Dunbar TheCall->setArg(0, OrigArg0); 694403bc2bd9edffe51d73776643fa87696c9417678Daniel Dunbar TheCall->setArg(1, OrigArg1); 6951eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 696cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor if (OrigArg0->isTypeDependent() || OrigArg1->isTypeDependent()) 697cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor return false; 698cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor 6991b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner // If the common type isn't a real floating type, then the arguments were 7001b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner // invalid for this operation. 7011b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner if (!Res->isRealFloatingType()) 7021eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump return Diag(OrigArg0->getLocStart(), 703fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner diag::err_typecheck_call_invalid_ordered_compare) 704d162584991885ab004a02573a73ce06422b921fcChris Lattner << OrigArg0->getType() << OrigArg1->getType() 705fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner << SourceRange(OrigArg0->getLocStart(), OrigArg1->getLocEnd()); 7061eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 7071b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner return false; 7081b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner} 7091b9a0793955070738cac6f04b5abe9496be9b317Chris Lattner 710e771a7ac11fb27f0e734e5de4d858f2c268895e5Benjamin Kramer/// SemaBuiltinSemaBuiltinFPClassification - Handle functions like 711e771a7ac11fb27f0e734e5de4d858f2c268895e5Benjamin Kramer/// __builtin_isnan and friends. This is declared to take (...), so we have 7123b1e26b708e8d00d4ba10ff857201bae2aff6baeBenjamin Kramer/// to check everything. We expect the last argument to be a floating point 7133b1e26b708e8d00d4ba10ff857201bae2aff6baeBenjamin Kramer/// value. 7143b1e26b708e8d00d4ba10ff857201bae2aff6baeBenjamin Kramerbool Sema::SemaBuiltinFPClassification(CallExpr *TheCall, unsigned NumArgs) { 7153b1e26b708e8d00d4ba10ff857201bae2aff6baeBenjamin Kramer if (TheCall->getNumArgs() < NumArgs) 7169ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman return Diag(TheCall->getLocEnd(), diag::err_typecheck_call_too_few_args) 717d77b9a29651d748f0e30a8dad8969635fc04f725Eric Christopher << 0 << NumArgs << TheCall->getNumArgs()/*function call*/; 7183b1e26b708e8d00d4ba10ff857201bae2aff6baeBenjamin Kramer if (TheCall->getNumArgs() > NumArgs) 7193b1e26b708e8d00d4ba10ff857201bae2aff6baeBenjamin Kramer return Diag(TheCall->getArg(NumArgs)->getLocStart(), 7209ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman diag::err_typecheck_call_too_many_args) 721ccfa9639f8d09733bcf1c2572c5bd3daba5bd632Eric Christopher << 0 /*function call*/ << NumArgs << TheCall->getNumArgs() 7223b1e26b708e8d00d4ba10ff857201bae2aff6baeBenjamin Kramer << SourceRange(TheCall->getArg(NumArgs)->getLocStart(), 7239ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman (*(TheCall->arg_end()-1))->getLocEnd()); 7249ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman 7253b1e26b708e8d00d4ba10ff857201bae2aff6baeBenjamin Kramer Expr *OrigArg = TheCall->getArg(NumArgs-1); 7261eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 7279ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman if (OrigArg->isTypeDependent()) 7289ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman return false; 7299ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman 73081368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner // This operation requires a non-_Complex floating-point number. 7319ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman if (!OrigArg->getType()->isRealFloatingType()) 7321eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump return Diag(OrigArg->getLocStart(), 7339ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman diag::err_typecheck_call_invalid_unary_fp) 7349ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman << OrigArg->getType() << OrigArg->getSourceRange(); 7351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 73681368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner // If this is an implicit conversion from float -> double, remove it. 73781368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner if (ImplicitCastExpr *Cast = dyn_cast<ImplicitCastExpr>(OrigArg)) { 73881368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner Expr *CastArg = Cast->getSubExpr(); 73981368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner if (CastArg->getType()->isSpecificBuiltinType(BuiltinType::Float)) { 74081368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner assert(Cast->getType()->isSpecificBuiltinType(BuiltinType::Double) && 74181368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner "promotion from float to double is the only expected cast here"); 74281368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner Cast->setSubExpr(0); 74381368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner TheCall->setArg(NumArgs-1, CastArg); 74481368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner OrigArg = CastArg; 74581368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner } 74681368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner } 74781368fbfd6d57150f66c993dc9041d62a7a32c4fChris Lattner 7489ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman return false; 7499ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman} 7509ac6f62a77be5b281a7ddc24a16669b457ac47c2Eli Friedman 751d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman/// SemaBuiltinShuffleVector - Handle __builtin_shufflevector. 752d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman// This is declared to take (...), so we have to check everything. 7530eb23307222bda7ad95d968eac4e1ab30864b213Sebastian RedlAction::OwningExprResult Sema::SemaBuiltinShuffleVector(CallExpr *TheCall) { 75437b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman if (TheCall->getNumArgs() < 2) 7550eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl return ExprError(Diag(TheCall->getLocEnd(), 756d77b9a29651d748f0e30a8dad8969635fc04f725Eric Christopher diag::err_typecheck_call_too_few_args_at_least) 75737b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman << 0 /*function call*/ << 2 << TheCall->getNumArgs() 758d77b9a29651d748f0e30a8dad8969635fc04f725Eric Christopher << TheCall->getSourceRange()); 759d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman 76037b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman // Determine which of the following types of shufflevector we're checking: 76137b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman // 1) unary, vector mask: (lhs, mask) 76237b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman // 2) binary, vector mask: (lhs, rhs, mask) 76337b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman // 3) binary, scalar mask: (lhs, rhs, index, ..., index) 76437b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman QualType resType = TheCall->getArg(0)->getType(); 76537b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman unsigned numElements = 0; 76637b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman 767cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor if (!TheCall->getArg(0)->isTypeDependent() && 768cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor !TheCall->getArg(1)->isTypeDependent()) { 76937b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman QualType LHSType = TheCall->getArg(0)->getType(); 77037b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman QualType RHSType = TheCall->getArg(1)->getType(); 77137b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman 77237b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman if (!LHSType->isVectorType() || !RHSType->isVectorType()) { 773cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor Diag(TheCall->getLocStart(), diag::err_shufflevector_non_vector) 7741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump << SourceRange(TheCall->getArg(0)->getLocStart(), 775cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor TheCall->getArg(1)->getLocEnd()); 776cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor return ExprError(); 777cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor } 77837b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman 77937b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman numElements = LHSType->getAs<VectorType>()->getNumElements(); 78037b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman unsigned numResElements = TheCall->getNumArgs() - 2; 78137b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman 78237b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman // Check to see if we have a call with 2 vector arguments, the unary shuffle 78337b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman // with mask. If so, verify that RHS is an integer vector type with the 78437b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman // same number of elts as lhs. 78537b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman if (TheCall->getNumArgs() == 2) { 786f60946222721d9ba3c059563935c17b84703187aDouglas Gregor if (!RHSType->hasIntegerRepresentation() || 78737b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman RHSType->getAs<VectorType>()->getNumElements() != numElements) 78837b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman Diag(TheCall->getLocStart(), diag::err_shufflevector_incompatible_vector) 78937b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman << SourceRange(TheCall->getArg(1)->getLocStart(), 79037b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman TheCall->getArg(1)->getLocEnd()); 79137b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman numResElements = numElements; 79237b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman } 79337b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman else if (!Context.hasSameUnqualifiedType(LHSType, RHSType)) { 794cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor Diag(TheCall->getLocStart(), diag::err_shufflevector_incompatible_vector) 7951eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump << SourceRange(TheCall->getArg(0)->getLocStart(), 796cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor TheCall->getArg(1)->getLocEnd()); 797cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor return ExprError(); 79837b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman } else if (numElements != numResElements) { 79937b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman QualType eltType = LHSType->getAs<VectorType>()->getElementType(); 800788b0fd67e1992f23555454efcdb16a19dfefac3Chris Lattner resType = Context.getVectorType(eltType, numResElements, 801788b0fd67e1992f23555454efcdb16a19dfefac3Chris Lattner VectorType::NotAltiVec); 802cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor } 803d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman } 804d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman 805d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman for (unsigned i = 2; i < TheCall->getNumArgs(); i++) { 806cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor if (TheCall->getArg(i)->isTypeDependent() || 807cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor TheCall->getArg(i)->isValueDependent()) 808cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor continue; 809cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor 81037b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman llvm::APSInt Result(32); 81137b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman if (!TheCall->getArg(i)->isIntegerConstantExpr(Result, Context)) 81237b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman return ExprError(Diag(TheCall->getLocStart(), 81337b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman diag::err_shufflevector_nonconstant_argument) 81437b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman << TheCall->getArg(i)->getSourceRange()); 8150eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl 816d1a0b6d3dfb208f638d3d750b588d9c0daa49289Chris Lattner if (Result.getActiveBits() > 64 || Result.getZExtValue() >= numElements*2) 8170eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl return ExprError(Diag(TheCall->getLocStart(), 818fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner diag::err_shufflevector_argument_too_large) 8190eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl << TheCall->getArg(i)->getSourceRange()); 820d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman } 821d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman 822d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman llvm::SmallVector<Expr*, 32> exprs; 823d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman 824d1a0b6d3dfb208f638d3d750b588d9c0daa49289Chris Lattner for (unsigned i = 0, e = TheCall->getNumArgs(); i != e; i++) { 825d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman exprs.push_back(TheCall->getArg(i)); 826d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman TheCall->setArg(i, 0); 827d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman } 828d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman 829a88dc3079bedf70a5cfc39791727e43a10383006Nate Begeman return Owned(new (Context) ShuffleVectorExpr(Context, exprs.begin(), 83037b6a5731a47f811d754f0d48aa93edf30e30513Nate Begeman exprs.size(), resType, 8318189cde56b4f6f938cd65f53c932fe1860d0204cTed Kremenek TheCall->getCallee()->getLocStart(), 8328189cde56b4f6f938cd65f53c932fe1860d0204cTed Kremenek TheCall->getRParenLoc())); 833d38617c8a50f9729c254ab76cd359af797c6739bEli Friedman} 83430ce344307f8a8b00054021307015571f83c7364Chris Lattner 8354493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar/// SemaBuiltinPrefetch - Handle __builtin_prefetch. 8364493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar// This is declared to take (const void*, ...) and can take two 8374493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar// optional constant int args. 8384493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbarbool Sema::SemaBuiltinPrefetch(CallExpr *TheCall) { 839fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner unsigned NumArgs = TheCall->getNumArgs(); 8404493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar 841fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner if (NumArgs > 3) 842ccfa9639f8d09733bcf1c2572c5bd3daba5bd632Eric Christopher return Diag(TheCall->getLocEnd(), 843ccfa9639f8d09733bcf1c2572c5bd3daba5bd632Eric Christopher diag::err_typecheck_call_too_many_args_at_most) 844ccfa9639f8d09733bcf1c2572c5bd3daba5bd632Eric Christopher << 0 /*function call*/ << 3 << NumArgs 845ccfa9639f8d09733bcf1c2572c5bd3daba5bd632Eric Christopher << TheCall->getSourceRange(); 8464493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar 8474493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar // Argument 0 is checked for us and the remaining arguments must be 8484493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar // constant integers. 849fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner for (unsigned i = 1; i != NumArgs; ++i) { 8504493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar Expr *Arg = TheCall->getArg(i); 851691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher 8529aef7263d84d9224575e113878cfbb06b8343cbfEli Friedman llvm::APSInt Result; 853691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher if (SemaBuiltinConstantArg(TheCall, i, Result)) 854691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher return true; 8551eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 8564493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar // FIXME: gcc issues a warning and rewrites these to 0. These 8574493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar // seems especially odd for the third argument since the default 8584493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar // is 3. 859fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner if (i == 1) { 8609aef7263d84d9224575e113878cfbb06b8343cbfEli Friedman if (Result.getLimitedValue() > 1) 861fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner return Diag(TheCall->getLocStart(), diag::err_argument_invalid_range) 86221fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner << "0" << "1" << Arg->getSourceRange(); 8634493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar } else { 8649aef7263d84d9224575e113878cfbb06b8343cbfEli Friedman if (Result.getLimitedValue() > 3) 865fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner return Diag(TheCall->getLocStart(), diag::err_argument_invalid_range) 86621fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner << "0" << "3" << Arg->getSourceRange(); 8674493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar } 8684493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar } 8694493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar 870fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner return false; 8714493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar} 8724493f79fce48cd9cbd9f55fa9d452cde736747a0Daniel Dunbar 873691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher/// SemaBuiltinConstantArg - Handle a check if argument ArgNum of CallExpr 874691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher/// TheCall is a constant expression. 875691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopherbool Sema::SemaBuiltinConstantArg(CallExpr *TheCall, int ArgNum, 876691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher llvm::APSInt &Result) { 877691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher Expr *Arg = TheCall->getArg(ArgNum); 878691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher DeclRefExpr *DRE =cast<DeclRefExpr>(TheCall->getCallee()->IgnoreParenCasts()); 879691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher FunctionDecl *FDecl = cast<FunctionDecl>(DRE->getDecl()); 880691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher 881691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher if (Arg->isTypeDependent() || Arg->isValueDependent()) return false; 882691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher 883691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher if (!Arg->isIntegerConstantExpr(Result, Context)) 884691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher return Diag(TheCall->getLocStart(), diag::err_constant_integer_arg_type) 8855e8965525282a48fd34af05183b8c3705a5b00d5Eric Christopher << FDecl->getDeclName() << Arg->getSourceRange(); 886691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher 88721fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner return false; 88821fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner} 88921fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner 890d5f8a4fd4d6dfb0415b93bb7ab721bba5cab1332Daniel Dunbar/// SemaBuiltinObjectSize - Handle __builtin_object_size(void *ptr, 891d5f8a4fd4d6dfb0415b93bb7ab721bba5cab1332Daniel Dunbar/// int type). This simply type checks that type is one of the defined 892d5f8a4fd4d6dfb0415b93bb7ab721bba5cab1332Daniel Dunbar/// constants (0-3). 893fee667f35e64751baa7fefe70b4e7bab06c8cd86Eric Christopher// For compatability check 0-3, llvm only handles 0 and 2. 894d5f8a4fd4d6dfb0415b93bb7ab721bba5cab1332Daniel Dunbarbool Sema::SemaBuiltinObjectSize(CallExpr *TheCall) { 895691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher llvm::APSInt Result; 896691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher 897691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher // Check constant-ness first. 898691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher if (SemaBuiltinConstantArg(TheCall, 1, Result)) 899691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher return true; 900d5f8a4fd4d6dfb0415b93bb7ab721bba5cab1332Daniel Dunbar 901691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher Expr *Arg = TheCall->getArg(1); 902d5f8a4fd4d6dfb0415b93bb7ab721bba5cab1332Daniel Dunbar if (Result.getSExtValue() < 0 || Result.getSExtValue() > 3) { 903fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner return Diag(TheCall->getLocStart(), diag::err_argument_invalid_range) 904fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner << "0" << "3" << SourceRange(Arg->getLocStart(), Arg->getLocEnd()); 905d5f8a4fd4d6dfb0415b93bb7ab721bba5cab1332Daniel Dunbar } 906d5f8a4fd4d6dfb0415b93bb7ab721bba5cab1332Daniel Dunbar 907d5f8a4fd4d6dfb0415b93bb7ab721bba5cab1332Daniel Dunbar return false; 908d5f8a4fd4d6dfb0415b93bb7ab721bba5cab1332Daniel Dunbar} 909d5f8a4fd4d6dfb0415b93bb7ab721bba5cab1332Daniel Dunbar 910586d6a81428da2d1ce70bcb98df29d749361cbf3Eli Friedman/// SemaBuiltinLongjmp - Handle __builtin_longjmp(void *env[5], int val). 911d875fed28578835de89cd407e9db4be788596d7cEli Friedman/// This checks that val is a constant 1. 912d875fed28578835de89cd407e9db4be788596d7cEli Friedmanbool Sema::SemaBuiltinLongjmp(CallExpr *TheCall) { 913d875fed28578835de89cd407e9db4be788596d7cEli Friedman Expr *Arg = TheCall->getArg(1); 914691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher llvm::APSInt Result; 915cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor 916691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher // TODO: This is less than ideal. Overload this to take a value. 917691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher if (SemaBuiltinConstantArg(TheCall, 1, Result)) 918691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher return true; 919691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher 920691ebc3f3225542e5abd85e107ebdbec907cf510Eric Christopher if (Result != 1) 921d875fed28578835de89cd407e9db4be788596d7cEli Friedman return Diag(TheCall->getLocStart(), diag::err_builtin_longjmp_invalid_val) 922d875fed28578835de89cd407e9db4be788596d7cEli Friedman << SourceRange(Arg->getLocStart(), Arg->getLocEnd()); 923d875fed28578835de89cd407e9db4be788596d7cEli Friedman 924d875fed28578835de89cd407e9db4be788596d7cEli Friedman return false; 925d875fed28578835de89cd407e9db4be788596d7cEli Friedman} 926d875fed28578835de89cd407e9db4be788596d7cEli Friedman 927d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek// Handle i > 1 ? "x" : "y", recursivelly 928082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenekbool Sema::SemaCheckStringLiteral(const Expr *E, const CallExpr *TheCall, 929082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek bool HasVAListArg, 930826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned format_idx, unsigned firstDataArg, 931826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek bool isPrintf) { 932826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 933cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor if (E->isTypeDependent() || E->isValueDependent()) 934cde01739dffe574c53a6ba1def1a57a2cc7b4a8bDouglas Gregor return false; 935d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek 936d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek switch (E->getStmtClass()) { 937d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek case Stmt::ConditionalOperatorClass: { 938082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek const ConditionalOperator *C = cast<ConditionalOperator>(E); 939826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek return SemaCheckStringLiteral(C->getTrueExpr(), TheCall, HasVAListArg, 940826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek format_idx, firstDataArg, isPrintf) 941826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek && SemaCheckStringLiteral(C->getRHS(), TheCall, HasVAListArg, 942826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek format_idx, firstDataArg, isPrintf); 943d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek } 944d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek 945d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek case Stmt::ImplicitCastExprClass: { 946082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek const ImplicitCastExpr *Expr = cast<ImplicitCastExpr>(E); 947d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek return SemaCheckStringLiteral(Expr->getSubExpr(), TheCall, HasVAListArg, 948826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek format_idx, firstDataArg, isPrintf); 949d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek } 950d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek 951d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek case Stmt::ParenExprClass: { 952082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek const ParenExpr *Expr = cast<ParenExpr>(E); 953d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek return SemaCheckStringLiteral(Expr->getSubExpr(), TheCall, HasVAListArg, 954826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek format_idx, firstDataArg, isPrintf); 955d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek } 9561eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 957082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek case Stmt::DeclRefExprClass: { 958082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek const DeclRefExpr *DR = cast<DeclRefExpr>(E); 9591eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 960082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek // As an exception, do not flag errors for variables binding to 961082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek // const string literals. 962082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek if (const VarDecl *VD = dyn_cast<VarDecl>(DR->getDecl())) { 963082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek bool isConstant = false; 964082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek QualType T = DR->getType(); 965082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek 966082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek if (const ArrayType *AT = Context.getAsArrayType(T)) { 967082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek isConstant = AT->getElementType().isConstant(Context); 968ac5fc7c6bcb494b60fee7ce615ac931c5db6135eMike Stump } else if (const PointerType *PT = T->getAs<PointerType>()) { 9691eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump isConstant = T.isConstant(Context) && 970082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek PT->getPointeeType().isConstant(Context); 971082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek } 9721eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 973082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek if (isConstant) { 97431310a21fb2a9f13950f864f681c86080b05d5b2Sebastian Redl if (const Expr *Init = VD->getAnyInitializer()) 975082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek return SemaCheckStringLiteral(Init, TheCall, 976826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek HasVAListArg, format_idx, firstDataArg, 977826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek isPrintf); 978082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek } 9791eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 980d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // For vprintf* functions (i.e., HasVAListArg==true), we add a 981d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // special check to see if the format string is a function parameter 982d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // of the function calling the printf function. If the function 983d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // has an attribute indicating it is a printf-like function, then we 984d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // should suppress warnings concerning non-literals being used in a call 985d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // to a vprintf function. For example: 986d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // 987d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // void 988d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // logmessage(char const *fmt __attribute__ (format (printf, 1, 2)), ...){ 989d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // va_list ap; 990d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // va_start(ap, fmt); 991d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // vprintf(fmt, ap); // Do NOT emit a warning about "fmt". 992d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // ... 993d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // 994d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // 995d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // FIXME: We don't have full attribute support yet, so just check to see 996d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // if the argument is a DeclRefExpr that references a parameter. We'll 997d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson // add proper support for checking the attribute later. 998d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson if (HasVAListArg) 999d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson if (isa<ParmVarDecl>(VD)) 1000d966a55bccae13f34d18958877c5e71dd643a125Anders Carlsson return true; 1001082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek } 10021eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1003082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek return false; 1004082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek } 1005d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek 10068f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson case Stmt::CallExprClass: { 10078f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson const CallExpr *CE = cast<CallExpr>(E); 10081eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump if (const ImplicitCastExpr *ICE 10098f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson = dyn_cast<ImplicitCastExpr>(CE->getCallee())) { 10108f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson if (const DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(ICE->getSubExpr())) { 10118f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(DRE->getDecl())) { 101240b598eea1310ec9ed554d56ce3e25b34c585458Argyrios Kyrtzidis if (const FormatArgAttr *FA = FD->getAttr<FormatArgAttr>()) { 10138f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson unsigned ArgIndex = FA->getFormatIdx(); 10148f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson const Expr *Arg = CE->getArg(ArgIndex - 1); 10151eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 10161eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump return SemaCheckStringLiteral(Arg, TheCall, HasVAListArg, 1017826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek format_idx, firstDataArg, isPrintf); 10188f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson } 10198f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson } 10208f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson } 10218f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson } 10221eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 10238f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson return false; 10248f031b3b14e726b093fb8693c2be4ab6d779e331Anders Carlsson } 1025082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek case Stmt::ObjCStringLiteralClass: 1026082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek case Stmt::StringLiteralClass: { 1027082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek const StringLiteral *StrE = NULL; 10281eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1029082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek if (const ObjCStringLiteral *ObjCFExpr = dyn_cast<ObjCStringLiteral>(E)) 1030d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek StrE = ObjCFExpr->getString(); 1031d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek else 1032082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek StrE = cast<StringLiteral>(E); 10331eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1034d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek if (StrE) { 1035826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek CheckFormatString(StrE, E, TheCall, HasVAListArg, format_idx, 1036826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek firstDataArg, isPrintf); 1037d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek return true; 1038d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek } 10391eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1040d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek return false; 1041d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek } 10421eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1043082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek default: 1044082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek return false; 1045d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek } 1046d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek} 1047d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek 1048e898f8a94947c6074d76ff83943b47d5bbdf210dFariborz Jahanianvoid 10491eb4433ac451dc16f4133a88af2d002ac26c58efMike StumpSema::CheckNonNullArguments(const NonNullAttr *NonNull, 10501eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump const CallExpr *TheCall) { 1051e898f8a94947c6074d76ff83943b47d5bbdf210dFariborz Jahanian for (NonNullAttr::iterator i = NonNull->begin(), e = NonNull->end(); 1052e898f8a94947c6074d76ff83943b47d5bbdf210dFariborz Jahanian i != e; ++i) { 105312b97ff9ce1412e388444f03049bfa6ad1bb5eb9Chris Lattner const Expr *ArgExpr = TheCall->getArg(*i); 10544e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek if (ArgExpr->isNullPointerConstant(Context, 1055ce94049b69f75b44c18584fe79cd238978b6b0d5Douglas Gregor Expr::NPC_ValueDependentIsNotNull)) 105612b97ff9ce1412e388444f03049bfa6ad1bb5eb9Chris Lattner Diag(TheCall->getCallee()->getLocStart(), diag::warn_null_arg) 105712b97ff9ce1412e388444f03049bfa6ad1bb5eb9Chris Lattner << ArgExpr->getSourceRange(); 1058e898f8a94947c6074d76ff83943b47d5bbdf210dFariborz Jahanian } 1059e898f8a94947c6074d76ff83943b47d5bbdf210dFariborz Jahanian} 1060d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek 1061826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek/// CheckPrintfScanfArguments - Check calls to printf and scanf (and similar 1062826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek/// functions) for correct use of format strings. 106359907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattnervoid 1064826a3457f737f1fc45a22954fd1bfde38160c165Ted KremenekSema::CheckPrintfScanfArguments(const CallExpr *TheCall, bool HasVAListArg, 1065826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned format_idx, unsigned firstDataArg, 1066826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek bool isPrintf) { 1067826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1068082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek const Expr *Fn = TheCall->getCallee(); 1069925e60d3fa706f31886027c876989af79eb0e0d2Chris Lattner 10704a2614e94672c47395abcde60518776fbebec589Sebastian Redl // The way the format attribute works in GCC, the implicit this argument 10714a2614e94672c47395abcde60518776fbebec589Sebastian Redl // of member functions is counted. However, it doesn't appear in our own 10724a2614e94672c47395abcde60518776fbebec589Sebastian Redl // lists, so decrement format_idx in that case. 10734a2614e94672c47395abcde60518776fbebec589Sebastian Redl if (isa<CXXMemberCallExpr>(TheCall)) { 10744a2614e94672c47395abcde60518776fbebec589Sebastian Redl // Catch a format attribute mistakenly referring to the object argument. 10754a2614e94672c47395abcde60518776fbebec589Sebastian Redl if (format_idx == 0) 10764a2614e94672c47395abcde60518776fbebec589Sebastian Redl return; 10774a2614e94672c47395abcde60518776fbebec589Sebastian Redl --format_idx; 10784a2614e94672c47395abcde60518776fbebec589Sebastian Redl if(firstDataArg != 0) 10794a2614e94672c47395abcde60518776fbebec589Sebastian Redl --firstDataArg; 10804a2614e94672c47395abcde60518776fbebec589Sebastian Redl } 10814a2614e94672c47395abcde60518776fbebec589Sebastian Redl 1082826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // CHECK: printf/scanf-like function is called with no format string. 1083925e60d3fa706f31886027c876989af79eb0e0d2Chris Lattner if (format_idx >= TheCall->getNumArgs()) { 1084826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek Diag(TheCall->getRParenLoc(), diag::warn_missing_format_string) 1085dcd5ef12488e4c7ea844327835896ca86b609a97Chris Lattner << Fn->getSourceRange(); 108671895b9aa3ad71957359497e136b50fcb6136bdfTed Kremenek return; 108771895b9aa3ad71957359497e136b50fcb6136bdfTed Kremenek } 10881eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1089082d936a5b8323ac2c04558d8bca277a647831a3Ted Kremenek const Expr *OrigFormatExpr = TheCall->getArg(format_idx)->IgnoreParenCasts(); 10901eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 109159907c4d8f6fc8aacfdaa0273bd7a9c140fbb45fChris Lattner // CHECK: format string is not a string literal. 10921eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // 109371895b9aa3ad71957359497e136b50fcb6136bdfTed Kremenek // Dynamically generated format strings are difficult to 109471895b9aa3ad71957359497e136b50fcb6136bdfTed Kremenek // automatically vet at compile time. Requiring that format strings 109571895b9aa3ad71957359497e136b50fcb6136bdfTed Kremenek // are string literals: (1) permits the checking of format strings by 109671895b9aa3ad71957359497e136b50fcb6136bdfTed Kremenek // the compiler and thereby (2) can practically remove the source of 109771895b9aa3ad71957359497e136b50fcb6136bdfTed Kremenek // many format string exploits. 10987ff22b259d4d4729f701679e3a7f0e242365e07fTed Kremenek 10991eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // Format string can be either ObjC string (e.g. @"%d") or 11007ff22b259d4d4729f701679e3a7f0e242365e07fTed Kremenek // C string (e.g. "%d") 11011eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // ObjC string uses the same format specifiers as C string, so we can use 11027ff22b259d4d4729f701679e3a7f0e242365e07fTed Kremenek // the same format string checking logic for both ObjC and C strings. 11031cd3e1f72c3a1c256fb6a5c3d4512bca1f1b751dChris Lattner if (SemaCheckStringLiteral(OrigFormatExpr, TheCall, HasVAListArg, format_idx, 1104826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek firstDataArg, isPrintf)) 11051cd3e1f72c3a1c256fb6a5c3d4512bca1f1b751dChris Lattner return; // Literal format string found, check done! 11061cd3e1f72c3a1c256fb6a5c3d4512bca1f1b751dChris Lattner 1107655f141f4d4c92eeebcc880211313e84c0a8b2f2Chris Lattner // If there are no arguments specified, warn with -Wformat-security, otherwise 1108655f141f4d4c92eeebcc880211313e84c0a8b2f2Chris Lattner // warn only with -Wformat-nonliteral. 1109655f141f4d4c92eeebcc880211313e84c0a8b2f2Chris Lattner if (TheCall->getNumArgs() == format_idx+1) 11101eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump Diag(TheCall->getArg(format_idx)->getLocStart(), 1111826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek diag::warn_format_nonliteral_noargs) 1112655f141f4d4c92eeebcc880211313e84c0a8b2f2Chris Lattner << OrigFormatExpr->getSourceRange(); 1113655f141f4d4c92eeebcc880211313e84c0a8b2f2Chris Lattner else 11141eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump Diag(TheCall->getArg(format_idx)->getLocStart(), 1115826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek diag::warn_format_nonliteral) 1116655f141f4d4c92eeebcc880211313e84c0a8b2f2Chris Lattner << OrigFormatExpr->getSourceRange(); 1117d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek} 1118d30ef87f34015d18bde20b9632032d0063d761aaTed Kremenek 1119e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremeneknamespace { 1120826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekclass CheckFormatHandler : public analyze_format_string::FormatStringHandler { 1121826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekprotected: 1122e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek Sema &S; 1123e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek const StringLiteral *FExpr; 1124e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek const Expr *OrigFormatExpr; 11256ee765348b2855c702fa593fb030ef6abe0d01f6Ted Kremenek const unsigned FirstDataArg; 1126e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek const unsigned NumDataArgs; 1127e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek const bool IsObjCLiteral; 1128e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek const char *Beg; // Start of format string. 11290d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek const bool HasVAListArg; 11300d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek const CallExpr *TheCall; 11310d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek unsigned FormatIdx; 11327f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek llvm::BitVector CoveredArgs; 1133efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek bool usesPositionalArgs; 1134efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek bool atFirstArg; 11354e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenekpublic: 1136826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek CheckFormatHandler(Sema &s, const StringLiteral *fexpr, 11376ee765348b2855c702fa593fb030ef6abe0d01f6Ted Kremenek const Expr *origFormatExpr, unsigned firstDataArg, 1138e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek unsigned numDataArgs, bool isObjCLiteral, 11390d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek const char *beg, bool hasVAListArg, 11400d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek const CallExpr *theCall, unsigned formatIdx) 1141e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek : S(s), FExpr(fexpr), OrigFormatExpr(origFormatExpr), 11426ee765348b2855c702fa593fb030ef6abe0d01f6Ted Kremenek FirstDataArg(firstDataArg), 11437f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek NumDataArgs(numDataArgs), 11440d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek IsObjCLiteral(isObjCLiteral), Beg(beg), 11450d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek HasVAListArg(hasVAListArg), 1146efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek TheCall(theCall), FormatIdx(formatIdx), 1147efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek usesPositionalArgs(false), atFirstArg(true) { 11487f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek CoveredArgs.resize(numDataArgs); 11497f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek CoveredArgs.reset(); 11507f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek } 11514e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 115207d161f38e708a91486bf1c031d525faebbb249dTed Kremenek void DoneProcessing(); 11534e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 1154826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek void HandleIncompleteSpecifier(const char *startSpecifier, 1155826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned specifierLen); 1156826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1157efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek virtual void HandleInvalidPosition(const char *startSpecifier, 1158efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek unsigned specifierLen, 1159826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek analyze_format_string::PositionContext p); 1160efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek 1161efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek virtual void HandleZeroPosition(const char *startPos, unsigned posLen); 1162efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek 1163e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek void HandleNullChar(const char *nullCharacter); 11644e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 1165826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekprotected: 1166c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek bool HandleInvalidConversionSpecifier(unsigned argIndex, SourceLocation Loc, 1167c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek const char *startSpec, 1168c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek unsigned specifierLen, 1169c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek const char *csStart, unsigned csLen); 1170c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek 1171f88c8e02da48afea6a04091f675af5c4facd99f1Ted Kremenek SourceRange getFormatStringRange(); 1172826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek CharSourceRange getSpecifierRange(const char *startSpecifier, 1173826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned specifierLen); 1174e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek SourceLocation getLocationOfByte(const char *x); 11754e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 11760d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek const Expr *getDataArg(unsigned i) const; 1177666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek 1178666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek bool CheckNumArgs(const analyze_format_string::FormatSpecifier &FS, 1179666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek const analyze_format_string::ConversionSpecifier &CS, 1180666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek const char *startSpecifier, unsigned specifierLen, 1181666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek unsigned argIndex); 1182e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek}; 1183e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek} 1184e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek 1185826a3457f737f1fc45a22954fd1bfde38160c165Ted KremenekSourceRange CheckFormatHandler::getFormatStringRange() { 1186e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek return OrigFormatExpr->getSourceRange(); 1187e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek} 1188e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek 1189826a3457f737f1fc45a22954fd1bfde38160c165Ted KremenekCharSourceRange CheckFormatHandler:: 1190826a3457f737f1fc45a22954fd1bfde38160c165Ted KremenekgetSpecifierRange(const char *startSpecifier, unsigned specifierLen) { 119145f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care SourceLocation Start = getLocationOfByte(startSpecifier); 119245f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care SourceLocation End = getLocationOfByte(startSpecifier + specifierLen - 1); 119345f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care 119445f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care // Advance the end SourceLocation by one due to half-open ranges. 119545f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care End = End.getFileLocWithOffset(1); 119645f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care 119745f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care return CharSourceRange::getCharRange(Start, End); 1198f88c8e02da48afea6a04091f675af5c4facd99f1Ted Kremenek} 1199f88c8e02da48afea6a04091f675af5c4facd99f1Ted Kremenek 1200826a3457f737f1fc45a22954fd1bfde38160c165Ted KremenekSourceLocation CheckFormatHandler::getLocationOfByte(const char *x) { 12014e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek return S.getLocationOfStringLiteralByte(FExpr, x - Beg); 1202e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek} 1203e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek 1204826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekvoid CheckFormatHandler::HandleIncompleteSpecifier(const char *startSpecifier, 1205826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned specifierLen){ 1206808015a18bd97781ce437831a95a92fdfc8d5136Ted Kremenek SourceLocation Loc = getLocationOfByte(startSpecifier); 1207808015a18bd97781ce437831a95a92fdfc8d5136Ted Kremenek S.Diag(Loc, diag::warn_printf_incomplete_specifier) 1208826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen); 1209808015a18bd97781ce437831a95a92fdfc8d5136Ted Kremenek} 1210808015a18bd97781ce437831a95a92fdfc8d5136Ted Kremenek 1211efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenekvoid 1212826a3457f737f1fc45a22954fd1bfde38160c165Ted KremenekCheckFormatHandler::HandleInvalidPosition(const char *startPos, unsigned posLen, 1213826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek analyze_format_string::PositionContext p) { 1214efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek SourceLocation Loc = getLocationOfByte(startPos); 1215826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek S.Diag(Loc, diag::warn_format_invalid_positional_specifier) 1216826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << (unsigned) p << getSpecifierRange(startPos, posLen); 1217efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek} 1218efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek 1219826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekvoid CheckFormatHandler::HandleZeroPosition(const char *startPos, 1220efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek unsigned posLen) { 1221efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek SourceLocation Loc = getLocationOfByte(startPos); 1222826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek S.Diag(Loc, diag::warn_format_zero_positional_specifier) 1223826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << getSpecifierRange(startPos, posLen); 1224efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek} 1225efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek 1226826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekvoid CheckFormatHandler::HandleNullChar(const char *nullCharacter) { 1227826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // The presence of a null character is likely an error. 1228826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek S.Diag(getLocationOfByte(nullCharacter), 1229826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek diag::warn_printf_format_string_contains_null_char) 1230826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << getFormatStringRange(); 1231826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek} 1232826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1233826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekconst Expr *CheckFormatHandler::getDataArg(unsigned i) const { 1234826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek return TheCall->getArg(FirstDataArg + i); 1235826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek} 12364e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 1237826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekvoid CheckFormatHandler::DoneProcessing() { 1238826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // Does the number of data arguments exceed the number of 1239826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // format conversions in the format string? 1240826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek if (!HasVAListArg) { 1241826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // Find any arguments that weren't covered. 1242826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek CoveredArgs.flip(); 1243826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek signed notCoveredArg = CoveredArgs.find_first(); 1244826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek if (notCoveredArg >= 0) { 1245826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek assert((unsigned)notCoveredArg < NumDataArgs); 1246826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek S.Diag(getDataArg((unsigned) notCoveredArg)->getLocStart(), 1247826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek diag::warn_printf_data_arg_not_used) 1248826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << getFormatStringRange(); 1249826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek } 1250826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek } 1251826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek} 1252826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1253c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenekbool 1254c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted KremenekCheckFormatHandler::HandleInvalidConversionSpecifier(unsigned argIndex, 1255c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek SourceLocation Loc, 1256c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek const char *startSpec, 1257c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek unsigned specifierLen, 1258c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek const char *csStart, 1259c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek unsigned csLen) { 1260c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek 1261c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek bool keepGoing = true; 1262c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek if (argIndex < NumDataArgs) { 1263c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek // Consider the argument coverered, even though the specifier doesn't 1264c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek // make sense. 1265c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek CoveredArgs.set(argIndex); 1266c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek } 1267c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek else { 1268c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek // If argIndex exceeds the number of data arguments we 1269c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek // don't issue a warning because that is just a cascade of warnings (and 1270c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek // they may have intended '%%' anyway). We don't want to continue processing 1271c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek // the format string after this point, however, as we will like just get 1272c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek // gibberish when trying to match arguments. 1273c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek keepGoing = false; 1274c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek } 1275c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek 1276c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek S.Diag(Loc, diag::warn_format_invalid_conversion) 1277c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek << llvm::StringRef(csStart, csLen) 1278c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek << getSpecifierRange(startSpec, specifierLen); 1279c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek 1280c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek return keepGoing; 1281c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek} 1282c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek 1283666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenekbool 1284666a197deb75d95c78ddd39274af1a54240828d8Ted KremenekCheckFormatHandler::CheckNumArgs( 1285666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek const analyze_format_string::FormatSpecifier &FS, 1286666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek const analyze_format_string::ConversionSpecifier &CS, 1287666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek const char *startSpecifier, unsigned specifierLen, unsigned argIndex) { 1288666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek 1289666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek if (argIndex >= NumDataArgs) { 1290666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek if (FS.usesPositionalArg()) { 1291666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek S.Diag(getLocationOfByte(CS.getStart()), 1292666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek diag::warn_printf_positional_arg_exceeds_data_args) 1293666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek << (argIndex+1) << NumDataArgs 1294666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen); 1295666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek } 1296666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek else { 1297666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek S.Diag(getLocationOfByte(CS.getStart()), 1298666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek diag::warn_printf_insufficient_data_args) 1299666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen); 1300666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek } 1301666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek 1302666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek return false; 1303666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek } 1304666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek return true; 1305666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek} 1306666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek 1307826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek//===--- CHECK: Printf format string checking ------------------------------===// 1308826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1309826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremeneknamespace { 1310826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekclass CheckPrintfHandler : public CheckFormatHandler { 1311826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekpublic: 1312826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek CheckPrintfHandler(Sema &s, const StringLiteral *fexpr, 1313826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const Expr *origFormatExpr, unsigned firstDataArg, 1314826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned numDataArgs, bool isObjCLiteral, 1315826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const char *beg, bool hasVAListArg, 1316826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const CallExpr *theCall, unsigned formatIdx) 1317826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek : CheckFormatHandler(s, fexpr, origFormatExpr, firstDataArg, 1318826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek numDataArgs, isObjCLiteral, beg, hasVAListArg, 1319826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek theCall, formatIdx) {} 1320826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1321826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1322826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek bool HandleInvalidPrintfConversionSpecifier( 1323826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const analyze_printf::PrintfSpecifier &FS, 1324826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const char *startSpecifier, 1325826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned specifierLen); 1326826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1327826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek bool HandlePrintfSpecifier(const analyze_printf::PrintfSpecifier &FS, 1328826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const char *startSpecifier, 1329826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned specifierLen); 1330826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1331826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek bool HandleAmount(const analyze_format_string::OptionalAmount &Amt, unsigned k, 1332826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const char *startSpecifier, unsigned specifierLen); 1333826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek void HandleInvalidAmount(const analyze_printf::PrintfSpecifier &FS, 1334826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const analyze_printf::OptionalAmount &Amt, 1335826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned type, 1336826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const char *startSpecifier, unsigned specifierLen); 1337826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek void HandleFlag(const analyze_printf::PrintfSpecifier &FS, 1338826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const analyze_printf::OptionalFlag &flag, 1339826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const char *startSpecifier, unsigned specifierLen); 1340826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek void HandleIgnoredFlag(const analyze_printf::PrintfSpecifier &FS, 1341826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const analyze_printf::OptionalFlag &ignoredFlag, 1342826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const analyze_printf::OptionalFlag &flag, 1343826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const char *startSpecifier, unsigned specifierLen); 1344826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek}; 1345826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek} 1346826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1347826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekbool CheckPrintfHandler::HandleInvalidPrintfConversionSpecifier( 1348826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const analyze_printf::PrintfSpecifier &FS, 1349826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const char *startSpecifier, 1350826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned specifierLen) { 13516ecb950c65329f8d6ce9ad0514632df35a5ab61fTed Kremenek const analyze_printf::PrintfConversionSpecifier &CS = 1352c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek FS.getConversionSpecifier(); 1353826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1354c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek return HandleInvalidConversionSpecifier(FS.getArgIndex(), 1355c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek getLocationOfByte(CS.getStart()), 1356c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek startSpecifier, specifierLen, 1357c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek CS.getStart(), CS.getLength()); 135826ac2e07b46bfb4d4f00752c96481c0a98c79c69Ted Kremenek} 135926ac2e07b46bfb4d4f00752c96481c0a98c79c69Ted Kremenek 1360826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekbool CheckPrintfHandler::HandleAmount( 1361826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const analyze_format_string::OptionalAmount &Amt, 1362826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned k, const char *startSpecifier, 1363826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned specifierLen) { 13640d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek 13650d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek if (Amt.hasDataArgument()) { 13660d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek if (!HasVAListArg) { 13677f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek unsigned argIndex = Amt.getArgIndex(); 13687f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek if (argIndex >= NumDataArgs) { 1369efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek S.Diag(getLocationOfByte(Amt.getStart()), 1370efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek diag::warn_printf_asterisk_missing_arg) 1371826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << k << getSpecifierRange(startSpecifier, specifierLen); 13720d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek // Don't do any more checking. We will just emit 13730d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek // spurious errors. 13740d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek return false; 13750d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek } 13764e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 13770d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek // Type check the data argument. It should be an 'int'. 137831f8e32788adb299acad455363eb7fd244642c82Ted Kremenek // Although not in conformance with C99, we also allow the argument to be 137931f8e32788adb299acad455363eb7fd244642c82Ted Kremenek // an 'unsigned int' as that is a reasonably safe case. GCC also 138031f8e32788adb299acad455363eb7fd244642c82Ted Kremenek // doesn't emit a warning for that case. 13817f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek CoveredArgs.set(argIndex); 13827f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek const Expr *Arg = getDataArg(argIndex); 13830d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek QualType T = Arg->getType(); 13844e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 13854e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek const analyze_printf::ArgTypeResult &ATR = Amt.getArgType(S.Context); 13864e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek assert(ATR.isValid()); 13874e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 13884e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek if (!ATR.matchesType(S.Context, T)) { 1389efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek S.Diag(getLocationOfByte(Amt.getStart()), 1390efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek diag::warn_printf_asterisk_wrong_type) 1391efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek << k 13924e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek << ATR.getRepresentativeType(S.Context) << T 1393826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen) 1394d635c5fcc45c952b75743dd2f4c86d6950e4954eTed Kremenek << Arg->getSourceRange(); 13950d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek // Don't do any more checking. We will just emit 13960d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek // spurious errors. 13970d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek return false; 13980d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek } 13990d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek } 14000d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek } 14010d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek return true; 14020d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek} 14030d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek 1404e4ee9663168dfb2b4122c768091e30217328c9faTom Carevoid CheckPrintfHandler::HandleInvalidAmount( 1405826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const analyze_printf::PrintfSpecifier &FS, 1406e4ee9663168dfb2b4122c768091e30217328c9faTom Care const analyze_printf::OptionalAmount &Amt, 1407e4ee9663168dfb2b4122c768091e30217328c9faTom Care unsigned type, 1408e4ee9663168dfb2b4122c768091e30217328c9faTom Care const char *startSpecifier, 1409e4ee9663168dfb2b4122c768091e30217328c9faTom Care unsigned specifierLen) { 14106ecb950c65329f8d6ce9ad0514632df35a5ab61fTed Kremenek const analyze_printf::PrintfConversionSpecifier &CS = 14116ecb950c65329f8d6ce9ad0514632df35a5ab61fTed Kremenek FS.getConversionSpecifier(); 1412e4ee9663168dfb2b4122c768091e30217328c9faTom Care switch (Amt.getHowSpecified()) { 1413e4ee9663168dfb2b4122c768091e30217328c9faTom Care case analyze_printf::OptionalAmount::Constant: 1414e4ee9663168dfb2b4122c768091e30217328c9faTom Care S.Diag(getLocationOfByte(Amt.getStart()), 1415e4ee9663168dfb2b4122c768091e30217328c9faTom Care diag::warn_printf_nonsensical_optional_amount) 1416e4ee9663168dfb2b4122c768091e30217328c9faTom Care << type 1417e4ee9663168dfb2b4122c768091e30217328c9faTom Care << CS.toString() 1418826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen) 1419826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << FixItHint::CreateRemoval(getSpecifierRange(Amt.getStart(), 1420e4ee9663168dfb2b4122c768091e30217328c9faTom Care Amt.getConstantLength())); 1421e4ee9663168dfb2b4122c768091e30217328c9faTom Care break; 1422e4ee9663168dfb2b4122c768091e30217328c9faTom Care 1423e4ee9663168dfb2b4122c768091e30217328c9faTom Care default: 1424e4ee9663168dfb2b4122c768091e30217328c9faTom Care S.Diag(getLocationOfByte(Amt.getStart()), 1425e4ee9663168dfb2b4122c768091e30217328c9faTom Care diag::warn_printf_nonsensical_optional_amount) 1426e4ee9663168dfb2b4122c768091e30217328c9faTom Care << type 1427e4ee9663168dfb2b4122c768091e30217328c9faTom Care << CS.toString() 1428826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen); 1429e4ee9663168dfb2b4122c768091e30217328c9faTom Care break; 1430e4ee9663168dfb2b4122c768091e30217328c9faTom Care } 1431e4ee9663168dfb2b4122c768091e30217328c9faTom Care} 1432e4ee9663168dfb2b4122c768091e30217328c9faTom Care 1433826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekvoid CheckPrintfHandler::HandleFlag(const analyze_printf::PrintfSpecifier &FS, 1434e4ee9663168dfb2b4122c768091e30217328c9faTom Care const analyze_printf::OptionalFlag &flag, 1435e4ee9663168dfb2b4122c768091e30217328c9faTom Care const char *startSpecifier, 1436e4ee9663168dfb2b4122c768091e30217328c9faTom Care unsigned specifierLen) { 1437e4ee9663168dfb2b4122c768091e30217328c9faTom Care // Warn about pointless flag with a fixit removal. 14386ecb950c65329f8d6ce9ad0514632df35a5ab61fTed Kremenek const analyze_printf::PrintfConversionSpecifier &CS = 14396ecb950c65329f8d6ce9ad0514632df35a5ab61fTed Kremenek FS.getConversionSpecifier(); 1440e4ee9663168dfb2b4122c768091e30217328c9faTom Care S.Diag(getLocationOfByte(flag.getPosition()), 1441e4ee9663168dfb2b4122c768091e30217328c9faTom Care diag::warn_printf_nonsensical_flag) 1442e4ee9663168dfb2b4122c768091e30217328c9faTom Care << flag.toString() << CS.toString() 1443826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen) 1444826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << FixItHint::CreateRemoval(getSpecifierRange(flag.getPosition(), 1)); 1445e4ee9663168dfb2b4122c768091e30217328c9faTom Care} 1446e4ee9663168dfb2b4122c768091e30217328c9faTom Care 1447e4ee9663168dfb2b4122c768091e30217328c9faTom Carevoid CheckPrintfHandler::HandleIgnoredFlag( 1448826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const analyze_printf::PrintfSpecifier &FS, 1449e4ee9663168dfb2b4122c768091e30217328c9faTom Care const analyze_printf::OptionalFlag &ignoredFlag, 1450e4ee9663168dfb2b4122c768091e30217328c9faTom Care const analyze_printf::OptionalFlag &flag, 1451e4ee9663168dfb2b4122c768091e30217328c9faTom Care const char *startSpecifier, 1452e4ee9663168dfb2b4122c768091e30217328c9faTom Care unsigned specifierLen) { 1453e4ee9663168dfb2b4122c768091e30217328c9faTom Care // Warn about ignored flag with a fixit removal. 1454e4ee9663168dfb2b4122c768091e30217328c9faTom Care S.Diag(getLocationOfByte(ignoredFlag.getPosition()), 1455e4ee9663168dfb2b4122c768091e30217328c9faTom Care diag::warn_printf_ignored_flag) 1456e4ee9663168dfb2b4122c768091e30217328c9faTom Care << ignoredFlag.toString() << flag.toString() 1457826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen) 1458826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << FixItHint::CreateRemoval(getSpecifierRange( 1459e4ee9663168dfb2b4122c768091e30217328c9faTom Care ignoredFlag.getPosition(), 1)); 1460e4ee9663168dfb2b4122c768091e30217328c9faTom Care} 1461e4ee9663168dfb2b4122c768091e30217328c9faTom Care 1462e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenekbool 1463826a3457f737f1fc45a22954fd1bfde38160c165Ted KremenekCheckPrintfHandler::HandlePrintfSpecifier(const analyze_printf::PrintfSpecifier 14645c41ee8c49995fb4fd76d686b239c15cbab261eaTed Kremenek &FS, 1465e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek const char *startSpecifier, 1466e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek unsigned specifierLen) { 1467e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek 14686ecb950c65329f8d6ce9ad0514632df35a5ab61fTed Kremenek using namespace analyze_format_string; 1469efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek using namespace analyze_printf; 14706ecb950c65329f8d6ce9ad0514632df35a5ab61fTed Kremenek const PrintfConversionSpecifier &CS = FS.getConversionSpecifier(); 1471e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek 1472baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek if (FS.consumesDataArgument()) { 1473baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek if (atFirstArg) { 1474baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek atFirstArg = false; 1475baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek usesPositionalArgs = FS.usesPositionalArg(); 1476baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek } 1477baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek else if (usesPositionalArgs != FS.usesPositionalArg()) { 1478baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek // Cannot mix-and-match positional and non-positional arguments. 1479baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek S.Diag(getLocationOfByte(CS.getStart()), 1480baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek diag::warn_format_mix_positional_nonpositional_args) 1481baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen); 1482baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek return false; 1483baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek } 1484efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek } 1485efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek 14860d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek // First check if the field width, precision, and conversion specifier 14870d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek // have matching data arguments. 1488efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek if (!HandleAmount(FS.getFieldWidth(), /* field width */ 0, 1489efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek startSpecifier, specifierLen)) { 14900d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek return false; 14910d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek } 14924e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 1493efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek if (!HandleAmount(FS.getPrecision(), /* precision */ 1, 1494efaff195ba1fa55b6fe0b0b2435b81451387d241Ted Kremenek startSpecifier, specifierLen)) { 14950d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek return false; 14960d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek } 14970d27735c51f5bd392e673cf39a675e14e9442387Ted Kremenek 1498f88c8e02da48afea6a04091f675af5c4facd99f1Ted Kremenek if (!CS.consumesDataArgument()) { 1499f88c8e02da48afea6a04091f675af5c4facd99f1Ted Kremenek // FIXME: Technically specifying a precision or field width here 1500f88c8e02da48afea6a04091f675af5c4facd99f1Ted Kremenek // makes no sense. Worth issuing a warning at some point. 15010e5675de2b67eeca754754ae8d3dacba425a38e8Ted Kremenek return true; 1502f88c8e02da48afea6a04091f675af5c4facd99f1Ted Kremenek } 15034e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 15047f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek // Consume the argument. 15057f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek unsigned argIndex = FS.getArgIndex(); 1506e3fc54790250076e33ad25b14e5be293514fe5eaTed Kremenek if (argIndex < NumDataArgs) { 1507e3fc54790250076e33ad25b14e5be293514fe5eaTed Kremenek // The check to see if the argIndex is valid will come later. 1508e3fc54790250076e33ad25b14e5be293514fe5eaTed Kremenek // We set the bit here because we may exit early from this 1509e3fc54790250076e33ad25b14e5be293514fe5eaTed Kremenek // function if we encounter some other error. 1510e3fc54790250076e33ad25b14e5be293514fe5eaTed Kremenek CoveredArgs.set(argIndex); 1511e3fc54790250076e33ad25b14e5be293514fe5eaTed Kremenek } 15127f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek 15137f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek // Check for using an Objective-C specific conversion specifier 15147f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek // in a non-ObjC literal. 15157f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek if (!IsObjCLiteral && CS.isObjCArg()) { 1516826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek return HandleInvalidPrintfConversionSpecifier(FS, startSpecifier, 1517826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek specifierLen); 15187f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek } 15194e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 1520e4ee9663168dfb2b4122c768091e30217328c9faTom Care // Check for invalid use of field width 1521e4ee9663168dfb2b4122c768091e30217328c9faTom Care if (!FS.hasValidFieldWidth()) { 152245f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care HandleInvalidAmount(FS, FS.getFieldWidth(), /* field width */ 0, 1523e4ee9663168dfb2b4122c768091e30217328c9faTom Care startSpecifier, specifierLen); 1524e4ee9663168dfb2b4122c768091e30217328c9faTom Care } 1525e4ee9663168dfb2b4122c768091e30217328c9faTom Care 1526e4ee9663168dfb2b4122c768091e30217328c9faTom Care // Check for invalid use of precision 1527e4ee9663168dfb2b4122c768091e30217328c9faTom Care if (!FS.hasValidPrecision()) { 1528e4ee9663168dfb2b4122c768091e30217328c9faTom Care HandleInvalidAmount(FS, FS.getPrecision(), /* precision */ 1, 1529e4ee9663168dfb2b4122c768091e30217328c9faTom Care startSpecifier, specifierLen); 1530e4ee9663168dfb2b4122c768091e30217328c9faTom Care } 1531e4ee9663168dfb2b4122c768091e30217328c9faTom Care 1532e4ee9663168dfb2b4122c768091e30217328c9faTom Care // Check each flag does not conflict with any other component. 1533e4ee9663168dfb2b4122c768091e30217328c9faTom Care if (!FS.hasValidLeadingZeros()) 1534e4ee9663168dfb2b4122c768091e30217328c9faTom Care HandleFlag(FS, FS.hasLeadingZeros(), startSpecifier, specifierLen); 1535e4ee9663168dfb2b4122c768091e30217328c9faTom Care if (!FS.hasValidPlusPrefix()) 1536e4ee9663168dfb2b4122c768091e30217328c9faTom Care HandleFlag(FS, FS.hasPlusPrefix(), startSpecifier, specifierLen); 153745f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care if (!FS.hasValidSpacePrefix()) 153845f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care HandleFlag(FS, FS.hasSpacePrefix(), startSpecifier, specifierLen); 1539e4ee9663168dfb2b4122c768091e30217328c9faTom Care if (!FS.hasValidAlternativeForm()) 1540e4ee9663168dfb2b4122c768091e30217328c9faTom Care HandleFlag(FS, FS.hasAlternativeForm(), startSpecifier, specifierLen); 1541e4ee9663168dfb2b4122c768091e30217328c9faTom Care if (!FS.hasValidLeftJustified()) 1542e4ee9663168dfb2b4122c768091e30217328c9faTom Care HandleFlag(FS, FS.isLeftJustified(), startSpecifier, specifierLen); 1543e4ee9663168dfb2b4122c768091e30217328c9faTom Care 1544e4ee9663168dfb2b4122c768091e30217328c9faTom Care // Check that flags are not ignored by another flag 154545f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care if (FS.hasSpacePrefix() && FS.hasPlusPrefix()) // ' ' ignored by '+' 154645f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care HandleIgnoredFlag(FS, FS.hasSpacePrefix(), FS.hasPlusPrefix(), 154745f9b7e8f23072d662ee1cc758f4ecb0da5e3322Tom Care startSpecifier, specifierLen); 1548e4ee9663168dfb2b4122c768091e30217328c9faTom Care if (FS.hasLeadingZeros() && FS.isLeftJustified()) // '0' ignored by '-' 1549e4ee9663168dfb2b4122c768091e30217328c9faTom Care HandleIgnoredFlag(FS, FS.hasLeadingZeros(), FS.isLeftJustified(), 1550e4ee9663168dfb2b4122c768091e30217328c9faTom Care startSpecifier, specifierLen); 1551e4ee9663168dfb2b4122c768091e30217328c9faTom Care 1552e4ee9663168dfb2b4122c768091e30217328c9faTom Care // Check the length modifier is valid with the given conversion specifier. 1553e4ee9663168dfb2b4122c768091e30217328c9faTom Care const LengthModifier &LM = FS.getLengthModifier(); 1554e4ee9663168dfb2b4122c768091e30217328c9faTom Care if (!FS.hasValidLengthModifier()) 1555e4ee9663168dfb2b4122c768091e30217328c9faTom Care S.Diag(getLocationOfByte(LM.getStart()), 1556649aecf55670682efb2a04a85810eef4d038c527Ted Kremenek diag::warn_format_nonsensical_length) 1557e4ee9663168dfb2b4122c768091e30217328c9faTom Care << LM.toString() << CS.toString() 1558826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen) 1559826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << FixItHint::CreateRemoval(getSpecifierRange(LM.getStart(), 1560e4ee9663168dfb2b4122c768091e30217328c9faTom Care LM.getLength())); 1561e4ee9663168dfb2b4122c768091e30217328c9faTom Care 1562e4ee9663168dfb2b4122c768091e30217328c9faTom Care // Are we using '%n'? 156335d353b47bce29200b910371dd9b8ba7f3058ab8Ted Kremenek if (CS.getKind() == ConversionSpecifier::nArg) { 1564e4ee9663168dfb2b4122c768091e30217328c9faTom Care // Issue a warning about this being a possible security issue. 1565e82d804ee761006250543d6fe6e98ee7896cd756Ted Kremenek S.Diag(getLocationOfByte(CS.getStart()), diag::warn_printf_write_back) 1566826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen); 1567e82d804ee761006250543d6fe6e98ee7896cd756Ted Kremenek // Continue checking the other format specifiers. 1568e82d804ee761006250543d6fe6e98ee7896cd756Ted Kremenek return true; 1569e82d804ee761006250543d6fe6e98ee7896cd756Ted Kremenek } 15705c41ee8c49995fb4fd76d686b239c15cbab261eaTed Kremenek 1571da51f0d136df131a0137c0ec1069fb586d8a296aTed Kremenek // The remaining checks depend on the data arguments. 1572da51f0d136df131a0137c0ec1069fb586d8a296aTed Kremenek if (HasVAListArg) 1573da51f0d136df131a0137c0ec1069fb586d8a296aTed Kremenek return true; 15744e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 1575666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek if (!CheckNumArgs(FS, CS, startSpecifier, specifierLen, argIndex)) 1576da51f0d136df131a0137c0ec1069fb586d8a296aTed Kremenek return false; 15774e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 157896827eb52405a71c65c200949f3e644368e86454Michael J. Spencer // Now type check the data expression that matches the 157996827eb52405a71c65c200949f3e644368e86454Michael J. Spencer // format specifier. 158096827eb52405a71c65c200949f3e644368e86454Michael J. Spencer const Expr *Ex = getDataArg(argIndex); 158196827eb52405a71c65c200949f3e644368e86454Michael J. Spencer const analyze_printf::ArgTypeResult &ATR = FS.getArgType(S.Context); 158296827eb52405a71c65c200949f3e644368e86454Michael J. Spencer if (ATR.isValid() && !ATR.matchesType(S.Context, Ex->getType())) { 158396827eb52405a71c65c200949f3e644368e86454Michael J. Spencer // Check if we didn't match because of an implicit cast from a 'char' 158496827eb52405a71c65c200949f3e644368e86454Michael J. Spencer // or 'short' to an 'int'. This is done because printf is a varargs 158596827eb52405a71c65c200949f3e644368e86454Michael J. Spencer // function. 158696827eb52405a71c65c200949f3e644368e86454Michael J. Spencer if (const ImplicitCastExpr *ICE = dyn_cast<ImplicitCastExpr>(Ex)) 158796827eb52405a71c65c200949f3e644368e86454Michael J. Spencer if (ICE->getType() == S.Context.IntTy) 158896827eb52405a71c65c200949f3e644368e86454Michael J. Spencer if (ATR.matchesType(S.Context, ICE->getSubExpr()->getType())) 158996827eb52405a71c65c200949f3e644368e86454Michael J. Spencer return true; 159096827eb52405a71c65c200949f3e644368e86454Michael J. Spencer 159196827eb52405a71c65c200949f3e644368e86454Michael J. Spencer // We may be able to offer a FixItHint if it is a supported type. 159296827eb52405a71c65c200949f3e644368e86454Michael J. Spencer PrintfSpecifier fixedFS = FS; 159396827eb52405a71c65c200949f3e644368e86454Michael J. Spencer bool success = fixedFS.fixType(Ex->getType()); 159496827eb52405a71c65c200949f3e644368e86454Michael J. Spencer 159596827eb52405a71c65c200949f3e644368e86454Michael J. Spencer if (success) { 159696827eb52405a71c65c200949f3e644368e86454Michael J. Spencer // Get the fix string from the fixed format specifier 159796827eb52405a71c65c200949f3e644368e86454Michael J. Spencer llvm::SmallString<128> buf; 159896827eb52405a71c65c200949f3e644368e86454Michael J. Spencer llvm::raw_svector_ostream os(buf); 159996827eb52405a71c65c200949f3e644368e86454Michael J. Spencer fixedFS.toString(os); 160096827eb52405a71c65c200949f3e644368e86454Michael J. Spencer 160196827eb52405a71c65c200949f3e644368e86454Michael J. Spencer S.Diag(getLocationOfByte(CS.getStart()), 160296827eb52405a71c65c200949f3e644368e86454Michael J. Spencer diag::warn_printf_conversion_argument_type_mismatch) 160396827eb52405a71c65c200949f3e644368e86454Michael J. Spencer << ATR.getRepresentativeType(S.Context) << Ex->getType() 160496827eb52405a71c65c200949f3e644368e86454Michael J. Spencer << getSpecifierRange(startSpecifier, specifierLen) 160596827eb52405a71c65c200949f3e644368e86454Michael J. Spencer << Ex->getSourceRange() 160696827eb52405a71c65c200949f3e644368e86454Michael J. Spencer << FixItHint::CreateReplacement( 160796827eb52405a71c65c200949f3e644368e86454Michael J. Spencer getSpecifierRange(startSpecifier, specifierLen), 160896827eb52405a71c65c200949f3e644368e86454Michael J. Spencer os.str()); 160996827eb52405a71c65c200949f3e644368e86454Michael J. Spencer } 161096827eb52405a71c65c200949f3e644368e86454Michael J. Spencer else { 161196827eb52405a71c65c200949f3e644368e86454Michael J. Spencer S.Diag(getLocationOfByte(CS.getStart()), 161296827eb52405a71c65c200949f3e644368e86454Michael J. Spencer diag::warn_printf_conversion_argument_type_mismatch) 161396827eb52405a71c65c200949f3e644368e86454Michael J. Spencer << ATR.getRepresentativeType(S.Context) << Ex->getType() 161496827eb52405a71c65c200949f3e644368e86454Michael J. Spencer << getSpecifierRange(startSpecifier, specifierLen) 161596827eb52405a71c65c200949f3e644368e86454Michael J. Spencer << Ex->getSourceRange(); 161696827eb52405a71c65c200949f3e644368e86454Michael J. Spencer } 161796827eb52405a71c65c200949f3e644368e86454Michael J. Spencer } 161896827eb52405a71c65c200949f3e644368e86454Michael J. Spencer 1619e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek return true; 1620e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek} 1621e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek 1622826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek//===--- CHECK: Scanf format string checking ------------------------------===// 1623826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1624826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremeneknamespace { 1625826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekclass CheckScanfHandler : public CheckFormatHandler { 1626826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekpublic: 1627826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek CheckScanfHandler(Sema &s, const StringLiteral *fexpr, 1628826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const Expr *origFormatExpr, unsigned firstDataArg, 1629826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned numDataArgs, bool isObjCLiteral, 1630826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const char *beg, bool hasVAListArg, 1631826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const CallExpr *theCall, unsigned formatIdx) 1632826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek : CheckFormatHandler(s, fexpr, origFormatExpr, firstDataArg, 1633826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek numDataArgs, isObjCLiteral, beg, hasVAListArg, 1634826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek theCall, formatIdx) {} 1635826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1636826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek bool HandleScanfSpecifier(const analyze_scanf::ScanfSpecifier &FS, 1637826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const char *startSpecifier, 1638826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned specifierLen); 1639c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek 1640c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek bool HandleInvalidScanfConversionSpecifier( 1641c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek const analyze_scanf::ScanfSpecifier &FS, 1642c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek const char *startSpecifier, 1643c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek unsigned specifierLen); 1644b7c21018ec1049580cf6df88db09e606550a7baaTed Kremenek 1645b7c21018ec1049580cf6df88db09e606550a7baaTed Kremenek void HandleIncompleteScanList(const char *start, const char *end); 1646826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek}; 1647826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek} 1648826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1649b7c21018ec1049580cf6df88db09e606550a7baaTed Kremenekvoid CheckScanfHandler::HandleIncompleteScanList(const char *start, 1650b7c21018ec1049580cf6df88db09e606550a7baaTed Kremenek const char *end) { 1651b7c21018ec1049580cf6df88db09e606550a7baaTed Kremenek S.Diag(getLocationOfByte(end), diag::warn_scanf_scanlist_incomplete) 1652b7c21018ec1049580cf6df88db09e606550a7baaTed Kremenek << getSpecifierRange(start, end - start); 1653b7c21018ec1049580cf6df88db09e606550a7baaTed Kremenek} 1654b7c21018ec1049580cf6df88db09e606550a7baaTed Kremenek 1655c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenekbool CheckScanfHandler::HandleInvalidScanfConversionSpecifier( 1656c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek const analyze_scanf::ScanfSpecifier &FS, 1657c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek const char *startSpecifier, 1658c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek unsigned specifierLen) { 1659c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek 16606ecb950c65329f8d6ce9ad0514632df35a5ab61fTed Kremenek const analyze_scanf::ScanfConversionSpecifier &CS = 1661c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek FS.getConversionSpecifier(); 1662c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek 1663c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek return HandleInvalidConversionSpecifier(FS.getArgIndex(), 1664c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek getLocationOfByte(CS.getStart()), 1665c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek startSpecifier, specifierLen, 1666c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek CS.getStart(), CS.getLength()); 1667c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek} 1668c09b6a59e02ae265fce51b8c11e2a045bcdaa888Ted Kremenek 1669826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekbool CheckScanfHandler::HandleScanfSpecifier( 1670826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const analyze_scanf::ScanfSpecifier &FS, 1671826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const char *startSpecifier, 1672826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned specifierLen) { 1673826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1674826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek using namespace analyze_scanf; 1675826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek using namespace analyze_format_string; 1676826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 16776ecb950c65329f8d6ce9ad0514632df35a5ab61fTed Kremenek const ScanfConversionSpecifier &CS = FS.getConversionSpecifier(); 1678826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1679baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek // Handle case where '%' and '*' don't consume an argument. These shouldn't 1680baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek // be used to decide if we are using positional arguments consistently. 1681baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek if (FS.consumesDataArgument()) { 1682baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek if (atFirstArg) { 1683baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek atFirstArg = false; 1684baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek usesPositionalArgs = FS.usesPositionalArg(); 1685baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek } 1686baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek else if (usesPositionalArgs != FS.usesPositionalArg()) { 1687baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek // Cannot mix-and-match positional and non-positional arguments. 1688baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek S.Diag(getLocationOfByte(CS.getStart()), 1689baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek diag::warn_format_mix_positional_nonpositional_args) 1690baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen); 1691baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek return false; 1692baa400654bd6f8396f9a07188445ae7955b060a3Ted Kremenek } 1693826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek } 1694826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1695826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // Check if the field with is non-zero. 1696826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const OptionalAmount &Amt = FS.getFieldWidth(); 1697826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek if (Amt.getHowSpecified() == OptionalAmount::Constant) { 1698826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek if (Amt.getConstantAmount() == 0) { 1699826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek const CharSourceRange &R = getSpecifierRange(Amt.getStart(), 1700826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek Amt.getConstantLength()); 1701826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek S.Diag(getLocationOfByte(Amt.getStart()), 1702826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek diag::warn_scanf_nonzero_width) 1703826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek << R << FixItHint::CreateRemoval(R); 17047f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek } 17057f70dc85d5055c19c8003f43a59135de211ad1b9Ted Kremenek } 1706826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1707826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek if (!FS.consumesDataArgument()) { 1708826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // FIXME: Technically specifying a precision or field width here 1709826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // makes no sense. Worth issuing a warning at some point. 1710826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek return true; 1711826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek } 1712826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1713826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // Consume the argument. 1714826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned argIndex = FS.getArgIndex(); 1715826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek if (argIndex < NumDataArgs) { 1716826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // The check to see if the argIndex is valid will come later. 1717826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // We set the bit here because we may exit early from this 1718826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // function if we encounter some other error. 1719826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek CoveredArgs.set(argIndex); 1720826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek } 1721826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 17221e51c200b17cb6b0238c10a8760ae04765688f16Ted Kremenek // Check the length modifier is valid with the given conversion specifier. 17231e51c200b17cb6b0238c10a8760ae04765688f16Ted Kremenek const LengthModifier &LM = FS.getLengthModifier(); 17241e51c200b17cb6b0238c10a8760ae04765688f16Ted Kremenek if (!FS.hasValidLengthModifier()) { 17251e51c200b17cb6b0238c10a8760ae04765688f16Ted Kremenek S.Diag(getLocationOfByte(LM.getStart()), 17261e51c200b17cb6b0238c10a8760ae04765688f16Ted Kremenek diag::warn_format_nonsensical_length) 17271e51c200b17cb6b0238c10a8760ae04765688f16Ted Kremenek << LM.toString() << CS.toString() 17281e51c200b17cb6b0238c10a8760ae04765688f16Ted Kremenek << getSpecifierRange(startSpecifier, specifierLen) 17291e51c200b17cb6b0238c10a8760ae04765688f16Ted Kremenek << FixItHint::CreateRemoval(getSpecifierRange(LM.getStart(), 17301e51c200b17cb6b0238c10a8760ae04765688f16Ted Kremenek LM.getLength())); 17311e51c200b17cb6b0238c10a8760ae04765688f16Ted Kremenek } 17321e51c200b17cb6b0238c10a8760ae04765688f16Ted Kremenek 1733826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // The remaining checks depend on the data arguments. 1734826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek if (HasVAListArg) 1735826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek return true; 1736826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1737666a197deb75d95c78ddd39274af1a54240828d8Ted Kremenek if (!CheckNumArgs(FS, CS, startSpecifier, specifierLen, argIndex)) 1738826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek return false; 1739826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1740826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek // FIXME: Check that the argument type matches the format specifier. 1741826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1742826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek return true; 174307d161f38e708a91486bf1c031d525faebbb249dTed Kremenek} 1744e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek 1745826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenekvoid Sema::CheckFormatString(const StringLiteral *FExpr, 17460e5675de2b67eeca754754ae8d3dacba425a38e8Ted Kremenek const Expr *OrigFormatExpr, 17470e5675de2b67eeca754754ae8d3dacba425a38e8Ted Kremenek const CallExpr *TheCall, bool HasVAListArg, 1748826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek unsigned format_idx, unsigned firstDataArg, 1749826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek bool isPrintf) { 1750826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1751e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek // CHECK: is the format string a wide literal? 1752e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek if (FExpr->isWide()) { 1753e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek Diag(FExpr->getLocStart(), 1754826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek diag::warn_format_string_is_wide_literal) 1755e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek << OrigFormatExpr->getSourceRange(); 1756e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek return; 1757e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek } 1758826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1759e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek // Str - The format string. NOTE: this is NOT null-terminated! 1760e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek const char *Str = FExpr->getStrData(); 1761826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1762e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek // CHECK: empty format string? 1763e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek unsigned StrLen = FExpr->getByteLength(); 1764826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1765e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek if (StrLen == 0) { 1766826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek Diag(FExpr->getLocStart(), diag::warn_empty_format_string) 1767e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek << OrigFormatExpr->getSourceRange(); 1768e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek return; 1769e0e5313c25f3870d0d18fc67e1b3a3a0e1ef8e07Ted Kremenek } 1770826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1771826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek if (isPrintf) { 1772826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek CheckPrintfHandler H(*this, FExpr, OrigFormatExpr, firstDataArg, 1773826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek TheCall->getNumArgs() - firstDataArg, 1774826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek isa<ObjCStringLiteral>(OrigFormatExpr), Str, 1775826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek HasVAListArg, TheCall, format_idx); 1776826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1777826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek if (!analyze_format_string::ParsePrintfString(H, Str, Str + StrLen)) 1778826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek H.DoneProcessing(); 1779826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek } 1780826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek else { 1781826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek CheckScanfHandler H(*this, FExpr, OrigFormatExpr, firstDataArg, 1782826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek TheCall->getNumArgs() - firstDataArg, 1783826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek isa<ObjCStringLiteral>(OrigFormatExpr), Str, 1784826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek HasVAListArg, TheCall, format_idx); 1785826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek 1786826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek if (!analyze_format_string::ParseScanfString(H, Str, Str + StrLen)) 1787826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek H.DoneProcessing(); 1788826a3457f737f1fc45a22954fd1bfde38160c165Ted Kremenek } 1789ce7024e8a3793b05861a4904ecdb1272924ada14Ted Kremenek} 1790ce7024e8a3793b05861a4904ecdb1272924ada14Ted Kremenek 179106de276fff91264437fa75111ed76de43097e089Ted Kremenek//===--- CHECK: Return Address of Stack Variable --------------------------===// 179206de276fff91264437fa75111ed76de43097e089Ted Kremenek 179306de276fff91264437fa75111ed76de43097e089Ted Kremenekstatic DeclRefExpr* EvalVal(Expr *E); 179406de276fff91264437fa75111ed76de43097e089Ted Kremenekstatic DeclRefExpr* EvalAddr(Expr* E); 179506de276fff91264437fa75111ed76de43097e089Ted Kremenek 179606de276fff91264437fa75111ed76de43097e089Ted Kremenek/// CheckReturnStackAddr - Check if a return statement returns the address 179706de276fff91264437fa75111ed76de43097e089Ted Kremenek/// of a stack variable. 179806de276fff91264437fa75111ed76de43097e089Ted Kremenekvoid 179906de276fff91264437fa75111ed76de43097e089Ted KremenekSema::CheckReturnStackAddr(Expr *RetValExp, QualType lhsType, 180006de276fff91264437fa75111ed76de43097e089Ted Kremenek SourceLocation ReturnLoc) { 18011eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 180206de276fff91264437fa75111ed76de43097e089Ted Kremenek // Perform checking for returned stack addresses. 1803dd972f20dc2bd3609d833893e5c6544ac09b59a9Steve Naroff if (lhsType->isPointerType() || lhsType->isBlockPointerType()) { 180406de276fff91264437fa75111ed76de43097e089Ted Kremenek if (DeclRefExpr *DR = EvalAddr(RetValExp)) 18053c73c41cefcfe76f36b7bed72c9f1ec195490951Chris Lattner Diag(DR->getLocStart(), diag::warn_ret_stack_addr) 180608631c5fa053867146b5ee8be658c229f6bf127cChris Lattner << DR->getDecl()->getDeclName() << RetValExp->getSourceRange(); 18071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1808c50a4a5f2eac14ac4c631d50b0a55cadc87700ceSteve Naroff // Skip over implicit cast expressions when checking for block expressions. 18094ca606e898293ae58f1793f988500e2218c7a9beChris Lattner RetValExp = RetValExp->IgnoreParenCasts(); 1810c50a4a5f2eac14ac4c631d50b0a55cadc87700ceSteve Naroff 18119e6b37a9f1d499e7ca0950edacd0b6569e491d7fChris Lattner if (BlockExpr *C = dyn_cast<BlockExpr>(RetValExp)) 1812397195bf3077fb42789b326f69f7d417227a0588Mike Stump if (C->hasBlockDeclRefExprs()) 1813397195bf3077fb42789b326f69f7d417227a0588Mike Stump Diag(C->getLocStart(), diag::err_ret_local_block) 1814397195bf3077fb42789b326f69f7d417227a0588Mike Stump << C->getSourceRange(); 18154e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 18169e6b37a9f1d499e7ca0950edacd0b6569e491d7fChris Lattner if (AddrLabelExpr *ALE = dyn_cast<AddrLabelExpr>(RetValExp)) 18179e6b37a9f1d499e7ca0950edacd0b6569e491d7fChris Lattner Diag(ALE->getLocStart(), diag::warn_ret_addr_label) 18189e6b37a9f1d499e7ca0950edacd0b6569e491d7fChris Lattner << ALE->getSourceRange(); 18194e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 1820ac5fc7c6bcb494b60fee7ce615ac931c5db6135eMike Stump } else if (lhsType->isReferenceType()) { 1821ac5fc7c6bcb494b60fee7ce615ac931c5db6135eMike Stump // Perform checking for stack values returned by reference. 182249badde06e066d058d6c7fcf4e628a72999b65a9Douglas Gregor // Check for a reference to the stack 182349badde06e066d058d6c7fcf4e628a72999b65a9Douglas Gregor if (DeclRefExpr *DR = EvalVal(RetValExp)) 1824dcd5ef12488e4c7ea844327835896ca86b609a97Chris Lattner Diag(DR->getLocStart(), diag::warn_ret_stack_ref) 182508631c5fa053867146b5ee8be658c229f6bf127cChris Lattner << DR->getDecl()->getDeclName() << RetValExp->getSourceRange(); 182606de276fff91264437fa75111ed76de43097e089Ted Kremenek } 182706de276fff91264437fa75111ed76de43097e089Ted Kremenek} 182806de276fff91264437fa75111ed76de43097e089Ted Kremenek 182906de276fff91264437fa75111ed76de43097e089Ted Kremenek/// EvalAddr - EvalAddr and EvalVal are mutually recursive functions that 183006de276fff91264437fa75111ed76de43097e089Ted Kremenek/// check if the expression in a return statement evaluates to an address 183106de276fff91264437fa75111ed76de43097e089Ted Kremenek/// to a location on the stack. The recursion is used to traverse the 183206de276fff91264437fa75111ed76de43097e089Ted Kremenek/// AST of the return expression, with recursion backtracking when we 183306de276fff91264437fa75111ed76de43097e089Ted Kremenek/// encounter a subexpression that (1) clearly does not lead to the address 183406de276fff91264437fa75111ed76de43097e089Ted Kremenek/// of a stack variable or (2) is something we cannot determine leads to 183506de276fff91264437fa75111ed76de43097e089Ted Kremenek/// the address of a stack variable based on such local checking. 183606de276fff91264437fa75111ed76de43097e089Ted Kremenek/// 1837e8c600f9fedf2cfd69cdd2cb4bde4a9b39ce2873Ted Kremenek/// EvalAddr processes expressions that are pointers that are used as 1838e8c600f9fedf2cfd69cdd2cb4bde4a9b39ce2873Ted Kremenek/// references (and not L-values). EvalVal handles all other values. 18391eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// At the base case of the recursion is a check for a DeclRefExpr* in 184006de276fff91264437fa75111ed76de43097e089Ted Kremenek/// the refers to a stack variable. 184106de276fff91264437fa75111ed76de43097e089Ted Kremenek/// 184206de276fff91264437fa75111ed76de43097e089Ted Kremenek/// This implementation handles: 184306de276fff91264437fa75111ed76de43097e089Ted Kremenek/// 184406de276fff91264437fa75111ed76de43097e089Ted Kremenek/// * pointer-to-pointer casts 184506de276fff91264437fa75111ed76de43097e089Ted Kremenek/// * implicit conversions from array references to pointers 184606de276fff91264437fa75111ed76de43097e089Ted Kremenek/// * taking the address of fields 184706de276fff91264437fa75111ed76de43097e089Ted Kremenek/// * arbitrary interplay between "&" and "*" operators 184806de276fff91264437fa75111ed76de43097e089Ted Kremenek/// * pointer arithmetic from an address of a stack variable 184906de276fff91264437fa75111ed76de43097e089Ted Kremenek/// * taking the address of an array element where the array is on the stack 185006de276fff91264437fa75111ed76de43097e089Ted Kremenekstatic DeclRefExpr* EvalAddr(Expr *E) { 185106de276fff91264437fa75111ed76de43097e089Ted Kremenek // We should only be called for evaluating pointer expressions. 18520f436560640a1cff5b6d96f80f540770f139453fDavid Chisnall assert((E->getType()->isAnyPointerType() || 1853dd972f20dc2bd3609d833893e5c6544ac09b59a9Steve Naroff E->getType()->isBlockPointerType() || 1854a526c5c67e5a0473c340903ee542ce570119665fTed Kremenek E->getType()->isObjCQualifiedIdType()) && 1855fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner "EvalAddr only works on pointers"); 18561eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 185706de276fff91264437fa75111ed76de43097e089Ted Kremenek // Our "symbolic interpreter" is just a dispatch off the currently 185806de276fff91264437fa75111ed76de43097e089Ted Kremenek // viewed AST node. We then recursively traverse the AST by calling 185906de276fff91264437fa75111ed76de43097e089Ted Kremenek // EvalAddr and EvalVal appropriately. 186006de276fff91264437fa75111ed76de43097e089Ted Kremenek switch (E->getStmtClass()) { 1861fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner case Stmt::ParenExprClass: 1862fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // Ignore parentheses. 1863fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner return EvalAddr(cast<ParenExpr>(E)->getSubExpr()); 186406de276fff91264437fa75111ed76de43097e089Ted Kremenek 1865fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner case Stmt::UnaryOperatorClass: { 1866fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // The only unary operator that make sense to handle here 1867fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // is AddrOf. All others don't make sense as pointers. 1868fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner UnaryOperator *U = cast<UnaryOperator>(E); 18691eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1870fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner if (U->getOpcode() == UnaryOperator::AddrOf) 1871fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner return EvalVal(U->getSubExpr()); 1872fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner else 1873fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner return NULL; 1874fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner } 18751eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1876fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner case Stmt::BinaryOperatorClass: { 1877fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // Handle pointer arithmetic. All other binary operators are not valid 1878fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // in this context. 1879fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner BinaryOperator *B = cast<BinaryOperator>(E); 1880fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner BinaryOperator::Opcode op = B->getOpcode(); 18811eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1882fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner if (op != BinaryOperator::Add && op != BinaryOperator::Sub) 1883fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner return NULL; 18841eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1885fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner Expr *Base = B->getLHS(); 18863907323dd6665c0c4e383435cb145233f4533406Anders Carlsson 1887fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // Determine which argument is the real pointer base. It could be 1888fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // the RHS argument instead of the LHS. 1889fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner if (!Base->getType()->isPointerType()) Base = B->getRHS(); 18901eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1891fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner assert (Base->getType()->isPointerType()); 1892fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner return EvalAddr(Base); 1893fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner } 189461f40a2b67fc2046768e14f66b617e564cbcc3d8Steve Naroff 1895fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // For conditional operators we need to see if either the LHS or RHS are 1896fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // valid DeclRefExpr*s. If one of them is valid, we return it. 1897fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner case Stmt::ConditionalOperatorClass: { 1898fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner ConditionalOperator *C = cast<ConditionalOperator>(E); 18991eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1900fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // Handle the GNU extension for missing LHS. 1901fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner if (Expr *lhsExpr = C->getLHS()) 1902fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner if (DeclRefExpr* LHS = EvalAddr(lhsExpr)) 1903fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner return LHS; 190406de276fff91264437fa75111ed76de43097e089Ted Kremenek 1905fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner return EvalAddr(C->getRHS()); 1906fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner } 19071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 190854b5274f2c190331438375ad114dad12ae098b57Ted Kremenek // For casts, we need to handle conversions from arrays to 190954b5274f2c190331438375ad114dad12ae098b57Ted Kremenek // pointer values, and pointer-to-pointer conversions. 191049badde06e066d058d6c7fcf4e628a72999b65a9Douglas Gregor case Stmt::ImplicitCastExprClass: 19116eec8e883de118b431e3ead5b1e604a6ac68ff6bDouglas Gregor case Stmt::CStyleCastExprClass: 191249badde06e066d058d6c7fcf4e628a72999b65a9Douglas Gregor case Stmt::CXXFunctionalCastExprClass: { 19130835a3cdeefe714b4959d31127ea155e56393125Argyrios Kyrtzidis Expr* SubExpr = cast<CastExpr>(E)->getSubExpr(); 191454b5274f2c190331438375ad114dad12ae098b57Ted Kremenek QualType T = SubExpr->getType(); 19151eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1916dd972f20dc2bd3609d833893e5c6544ac09b59a9Steve Naroff if (SubExpr->getType()->isPointerType() || 1917dd972f20dc2bd3609d833893e5c6544ac09b59a9Steve Naroff SubExpr->getType()->isBlockPointerType() || 1918dd972f20dc2bd3609d833893e5c6544ac09b59a9Steve Naroff SubExpr->getType()->isObjCQualifiedIdType()) 1919fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner return EvalAddr(SubExpr); 192054b5274f2c190331438375ad114dad12ae098b57Ted Kremenek else if (T->isArrayType()) 192154b5274f2c190331438375ad114dad12ae098b57Ted Kremenek return EvalVal(SubExpr); 1922fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner else 192354b5274f2c190331438375ad114dad12ae098b57Ted Kremenek return 0; 1924fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner } 19251eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1926fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // C++ casts. For dynamic casts, static casts, and const casts, we 1927fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // are always converting from a pointer-to-pointer, so we just blow 192849badde06e066d058d6c7fcf4e628a72999b65a9Douglas Gregor // through the cast. In the case the dynamic cast doesn't fail (and 192949badde06e066d058d6c7fcf4e628a72999b65a9Douglas Gregor // return NULL), we take the conservative route and report cases 1930fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // where we return the address of a stack variable. For Reinterpre 193149badde06e066d058d6c7fcf4e628a72999b65a9Douglas Gregor // FIXME: The comment about is wrong; we're not always converting 193249badde06e066d058d6c7fcf4e628a72999b65a9Douglas Gregor // from pointer to pointer. I'm guessing that this code should also 19331eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // handle references to objects. 19341eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump case Stmt::CXXStaticCastExprClass: 19351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump case Stmt::CXXDynamicCastExprClass: 193649badde06e066d058d6c7fcf4e628a72999b65a9Douglas Gregor case Stmt::CXXConstCastExprClass: 193749badde06e066d058d6c7fcf4e628a72999b65a9Douglas Gregor case Stmt::CXXReinterpretCastExprClass: { 193849badde06e066d058d6c7fcf4e628a72999b65a9Douglas Gregor Expr *S = cast<CXXNamedCastExpr>(E)->getSubExpr(); 1939dd972f20dc2bd3609d833893e5c6544ac09b59a9Steve Naroff if (S->getType()->isPointerType() || S->getType()->isBlockPointerType()) 1940fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner return EvalAddr(S); 194106de276fff91264437fa75111ed76de43097e089Ted Kremenek else 194206de276fff91264437fa75111ed76de43097e089Ted Kremenek return NULL; 1943fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner } 19441eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1945fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner // Everything else: we simply don't reason about them. 1946fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner default: 1947fae3f1f6565c74d3238747b58357a6e56fbb0e9cChris Lattner return NULL; 194806de276fff91264437fa75111ed76de43097e089Ted Kremenek } 194906de276fff91264437fa75111ed76de43097e089Ted Kremenek} 19501eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 195106de276fff91264437fa75111ed76de43097e089Ted Kremenek 195206de276fff91264437fa75111ed76de43097e089Ted Kremenek/// EvalVal - This function is complements EvalAddr in the mutual recursion. 195306de276fff91264437fa75111ed76de43097e089Ted Kremenek/// See the comments for EvalAddr for more details. 195406de276fff91264437fa75111ed76de43097e089Ted Kremenekstatic DeclRefExpr* EvalVal(Expr *E) { 195568957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenekdo { 1956e8c600f9fedf2cfd69cdd2cb4bde4a9b39ce2873Ted Kremenek // We should only be called for evaluating non-pointer expressions, or 1957e8c600f9fedf2cfd69cdd2cb4bde4a9b39ce2873Ted Kremenek // expressions with a pointer type that are not used as references but instead 1958e8c600f9fedf2cfd69cdd2cb4bde4a9b39ce2873Ted Kremenek // are l-values (e.g., DeclRefExpr with a pointer type). 19591eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 196006de276fff91264437fa75111ed76de43097e089Ted Kremenek // Our "symbolic interpreter" is just a dispatch off the currently 196106de276fff91264437fa75111ed76de43097e089Ted Kremenek // viewed AST node. We then recursively traverse the AST by calling 196206de276fff91264437fa75111ed76de43097e089Ted Kremenek // EvalAddr and EvalVal appropriately. 196306de276fff91264437fa75111ed76de43097e089Ted Kremenek switch (E->getStmtClass()) { 196468957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek case Stmt::ImplicitCastExprClass: { 196568957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek ImplicitCastExpr *IE = cast<ImplicitCastExpr>(E); 196668957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek if (IE->getCategory() == ImplicitCastExpr::LValue) { 196768957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek E = IE->getSubExpr(); 196868957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek continue; 196968957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek } 197068957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek return NULL; 197168957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek } 197268957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek 1973a2813cec2605ce7878d1b13471d685f689b251afDouglas Gregor case Stmt::DeclRefExprClass: { 197406de276fff91264437fa75111ed76de43097e089Ted Kremenek // DeclRefExpr: the base case. When we hit a DeclRefExpr we are looking 197506de276fff91264437fa75111ed76de43097e089Ted Kremenek // at code that refers to a variable's name. We check if it has local 197606de276fff91264437fa75111ed76de43097e089Ted Kremenek // storage within the function, and if so, return the expression. 197706de276fff91264437fa75111ed76de43097e089Ted Kremenek DeclRefExpr *DR = cast<DeclRefExpr>(E); 19781eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 197906de276fff91264437fa75111ed76de43097e089Ted Kremenek if (VarDecl *V = dyn_cast<VarDecl>(DR->getDecl())) 19801eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump if (V->hasLocalStorage() && !V->getType()->isReferenceType()) return DR; 19811eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 198206de276fff91264437fa75111ed76de43097e089Ted Kremenek return NULL; 198306de276fff91264437fa75111ed76de43097e089Ted Kremenek } 19841eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 198568957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek case Stmt::ParenExprClass: { 198606de276fff91264437fa75111ed76de43097e089Ted Kremenek // Ignore parentheses. 198768957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek E = cast<ParenExpr>(E)->getSubExpr(); 198868957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek continue; 198968957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek } 19901eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 199106de276fff91264437fa75111ed76de43097e089Ted Kremenek case Stmt::UnaryOperatorClass: { 199206de276fff91264437fa75111ed76de43097e089Ted Kremenek // The only unary operator that make sense to handle here 199306de276fff91264437fa75111ed76de43097e089Ted Kremenek // is Deref. All others don't resolve to a "name." This includes 199406de276fff91264437fa75111ed76de43097e089Ted Kremenek // handling all sorts of rvalues passed to a unary operator. 199506de276fff91264437fa75111ed76de43097e089Ted Kremenek UnaryOperator *U = cast<UnaryOperator>(E); 19961eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 199706de276fff91264437fa75111ed76de43097e089Ted Kremenek if (U->getOpcode() == UnaryOperator::Deref) 199806de276fff91264437fa75111ed76de43097e089Ted Kremenek return EvalAddr(U->getSubExpr()); 199906de276fff91264437fa75111ed76de43097e089Ted Kremenek 200006de276fff91264437fa75111ed76de43097e089Ted Kremenek return NULL; 200106de276fff91264437fa75111ed76de43097e089Ted Kremenek } 20021eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 200306de276fff91264437fa75111ed76de43097e089Ted Kremenek case Stmt::ArraySubscriptExprClass: { 200406de276fff91264437fa75111ed76de43097e089Ted Kremenek // Array subscripts are potential references to data on the stack. We 200506de276fff91264437fa75111ed76de43097e089Ted Kremenek // retrieve the DeclRefExpr* for the array variable if it indeed 200606de276fff91264437fa75111ed76de43097e089Ted Kremenek // has local storage. 20072324512285caac0332bbbc6e4cab6245d2a370a1Ted Kremenek return EvalAddr(cast<ArraySubscriptExpr>(E)->getBase()); 200806de276fff91264437fa75111ed76de43097e089Ted Kremenek } 20091eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 201006de276fff91264437fa75111ed76de43097e089Ted Kremenek case Stmt::ConditionalOperatorClass: { 201106de276fff91264437fa75111ed76de43097e089Ted Kremenek // For conditional operators we need to see if either the LHS or RHS are 201206de276fff91264437fa75111ed76de43097e089Ted Kremenek // non-NULL DeclRefExpr's. If one is non-NULL, we return it. 201306de276fff91264437fa75111ed76de43097e089Ted Kremenek ConditionalOperator *C = cast<ConditionalOperator>(E); 201406de276fff91264437fa75111ed76de43097e089Ted Kremenek 20153907323dd6665c0c4e383435cb145233f4533406Anders Carlsson // Handle the GNU extension for missing LHS. 20163907323dd6665c0c4e383435cb145233f4533406Anders Carlsson if (Expr *lhsExpr = C->getLHS()) 20173907323dd6665c0c4e383435cb145233f4533406Anders Carlsson if (DeclRefExpr *LHS = EvalVal(lhsExpr)) 20183907323dd6665c0c4e383435cb145233f4533406Anders Carlsson return LHS; 20193907323dd6665c0c4e383435cb145233f4533406Anders Carlsson 20203907323dd6665c0c4e383435cb145233f4533406Anders Carlsson return EvalVal(C->getRHS()); 202106de276fff91264437fa75111ed76de43097e089Ted Kremenek } 20221eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 202306de276fff91264437fa75111ed76de43097e089Ted Kremenek // Accesses to members are potential references to data on the stack. 202483f6faf37d9bf58986bedc9bc0ea897a56b4dbadDouglas Gregor case Stmt::MemberExprClass: { 202506de276fff91264437fa75111ed76de43097e089Ted Kremenek MemberExpr *M = cast<MemberExpr>(E); 20261eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 202706de276fff91264437fa75111ed76de43097e089Ted Kremenek // Check for indirect access. We only want direct field accesses. 202806de276fff91264437fa75111ed76de43097e089Ted Kremenek if (!M->isArrow()) 202906de276fff91264437fa75111ed76de43097e089Ted Kremenek return EvalVal(M->getBase()); 203006de276fff91264437fa75111ed76de43097e089Ted Kremenek else 203106de276fff91264437fa75111ed76de43097e089Ted Kremenek return NULL; 203206de276fff91264437fa75111ed76de43097e089Ted Kremenek } 20331eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 203406de276fff91264437fa75111ed76de43097e089Ted Kremenek // Everything else: we simply don't reason about them. 203506de276fff91264437fa75111ed76de43097e089Ted Kremenek default: 203606de276fff91264437fa75111ed76de43097e089Ted Kremenek return NULL; 203706de276fff91264437fa75111ed76de43097e089Ted Kremenek } 203868957a919084ab8bbd1f01d534db1d6f31d0f459Ted Kremenek} while (true); 203906de276fff91264437fa75111ed76de43097e089Ted Kremenek} 2040588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek 2041588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek//===--- CHECK: Floating-Point comparisons (-Wfloat-equal) ---------------===// 2042588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek 2043588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek/// Check for comparisons of floating point operands using != and ==. 2044588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek/// Issue a warning if these are no self-comparisons, as they are not likely 2045588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek/// to do what the programmer intended. 2046588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenekvoid Sema::CheckFloatComparison(SourceLocation loc, Expr* lex, Expr *rex) { 2047588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek bool EmitWarning = true; 20481eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 20494e99a5fc3b203397a91136c6e695e405fb8fc606Ted Kremenek Expr* LeftExprSansParen = lex->IgnoreParens(); 205032e97b66bbce16c9e81c877794fb7a0aeeb66ccbTed Kremenek Expr* RightExprSansParen = rex->IgnoreParens(); 2051588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek 2052588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek // Special case: check for x == x (which is OK). 2053588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek // Do not emit warnings for such cases. 2054588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek if (DeclRefExpr* DRL = dyn_cast<DeclRefExpr>(LeftExprSansParen)) 2055588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek if (DeclRefExpr* DRR = dyn_cast<DeclRefExpr>(RightExprSansParen)) 2056588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek if (DRL->getDecl() == DRR->getDecl()) 2057588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek EmitWarning = false; 20581eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 20591eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 20601b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek // Special case: check for comparisons against literals that can be exactly 20611b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek // represented by APFloat. In such cases, do not emit a warning. This 20621b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek // is a heuristic: often comparison against such literals are used to 20631b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek // detect if a value in a variable has not changed. This clearly can 20641b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek // lead to false negatives. 20651b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek if (EmitWarning) { 20661b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek if (FloatingLiteral* FLL = dyn_cast<FloatingLiteral>(LeftExprSansParen)) { 20671b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek if (FLL->isExact()) 20681b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek EmitWarning = false; 2069ac5fc7c6bcb494b60fee7ce615ac931c5db6135eMike Stump } else 20701b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek if (FloatingLiteral* FLR = dyn_cast<FloatingLiteral>(RightExprSansParen)){ 20711b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek if (FLR->isExact()) 20721b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek EmitWarning = false; 20731b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek } 20741b500bb0d40aa3ebf1ace47340bb5f401a9ae99cTed Kremenek } 20751eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2076588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek // Check for comparisons with builtin types. 20770eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl if (EmitWarning) 2078588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek if (CallExpr* CL = dyn_cast<CallExpr>(LeftExprSansParen)) 20793c385e5f8d9008fff18597ca302be19fa86e51f6Douglas Gregor if (CL->isBuiltinCall(Context)) 2080588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek EmitWarning = false; 20811eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 20820eb23307222bda7ad95d968eac4e1ab30864b213Sebastian Redl if (EmitWarning) 2083588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek if (CallExpr* CR = dyn_cast<CallExpr>(RightExprSansParen)) 20843c385e5f8d9008fff18597ca302be19fa86e51f6Douglas Gregor if (CR->isBuiltinCall(Context)) 2085588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek EmitWarning = false; 20861eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2087588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek // Emit the diagnostic. 2088588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek if (EmitWarning) 2089fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner Diag(loc, diag::warn_floatingpoint_eq) 2090fa25bbb351f4fdd977f51254119cdfc2b525ce90Chris Lattner << lex->getSourceRange() << rex->getSourceRange(); 2091588e5ebee2db045c3611e0c8f601bc4495ebd0f3Ted Kremenek} 2092ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall 2093f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall//===--- CHECK: Integer mixed-sign comparisons (-Wsign-compare) --------===// 2094f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall//===--- CHECK: Lossy implicit conversions (-Wconversion) --------------===// 2095ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall 2096f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCallnamespace { 2097ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall 2098f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// Structure recording the 'active' range of an integer-valued 2099f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// expression. 2100f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCallstruct IntRange { 2101f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall /// The number of bits active in the int. 2102f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall unsigned Width; 2103ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall 2104f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall /// True if the int is known not to have negative values. 2105f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall bool NonNegative; 210651313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2107f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall IntRange() {} 2108f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall IntRange(unsigned Width, bool NonNegative) 2109f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall : Width(Width), NonNegative(NonNegative) 2110f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall {} 211151313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2112f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // Returns the range of the bool type. 2113f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall static IntRange forBoolType() { 2114f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange(1, true); 2115f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall } 211651313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2117f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // Returns the range of an integral type. 2118f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall static IntRange forType(ASTContext &C, QualType T) { 2119f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return forCanonicalType(C, T->getCanonicalTypeInternal().getTypePtr()); 212051313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 212151313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2122f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // Returns the range of an integeral type based on its canonical 2123f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // representation. 2124f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall static IntRange forCanonicalType(ASTContext &C, const Type *T) { 2125f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall assert(T->isCanonicalUnqualified()); 212651313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2127f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (const VectorType *VT = dyn_cast<VectorType>(T)) 2128f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall T = VT->getElementType().getTypePtr(); 2129f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (const ComplexType *CT = dyn_cast<ComplexType>(T)) 2130f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall T = CT->getElementType().getTypePtr(); 2131323ed74658bc8375278eabf074b4777458376540John McCall 2132323ed74658bc8375278eabf074b4777458376540John McCall if (const EnumType *ET = dyn_cast<EnumType>(T)) { 2133323ed74658bc8375278eabf074b4777458376540John McCall EnumDecl *Enum = ET->getDecl(); 2134323ed74658bc8375278eabf074b4777458376540John McCall unsigned NumPositive = Enum->getNumPositiveBits(); 2135323ed74658bc8375278eabf074b4777458376540John McCall unsigned NumNegative = Enum->getNumNegativeBits(); 2136323ed74658bc8375278eabf074b4777458376540John McCall 2137323ed74658bc8375278eabf074b4777458376540John McCall return IntRange(std::max(NumPositive, NumNegative), NumNegative == 0); 2138323ed74658bc8375278eabf074b4777458376540John McCall } 213951313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2140f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall const BuiltinType *BT = cast<BuiltinType>(T); 2141f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall assert(BT->isInteger()); 214251313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2143f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange(C.getIntWidth(QualType(T, 0)), BT->isUnsignedInteger()); 214451313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 214551313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2146f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // Returns the supremum of two ranges: i.e. their conservative merge. 2147c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall static IntRange join(IntRange L, IntRange R) { 2148f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange(std::max(L.Width, R.Width), 214960fad45739b764886f707bd204eae9ecce6db1f2John McCall L.NonNegative && R.NonNegative); 215060fad45739b764886f707bd204eae9ecce6db1f2John McCall } 215160fad45739b764886f707bd204eae9ecce6db1f2John McCall 215260fad45739b764886f707bd204eae9ecce6db1f2John McCall // Returns the infinum of two ranges: i.e. their aggressive merge. 2153c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall static IntRange meet(IntRange L, IntRange R) { 215460fad45739b764886f707bd204eae9ecce6db1f2John McCall return IntRange(std::min(L.Width, R.Width), 215560fad45739b764886f707bd204eae9ecce6db1f2John McCall L.NonNegative || R.NonNegative); 215651313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 2157f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall}; 215851313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2159f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCallIntRange GetValueRange(ASTContext &C, llvm::APSInt &value, unsigned MaxWidth) { 2160f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (value.isSigned() && value.isNegative()) 2161f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange(value.getMinSignedBits(), false); 216251313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2163f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (value.getBitWidth() > MaxWidth) 2164f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall value.trunc(MaxWidth); 216551313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2166f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // isNonNegative() just checks the sign bit without considering 2167f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // signedness. 2168f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange(value.getActiveBits(), true); 216951313c39c84407dd6a323be99a8c322bf8d052a9John McCall} 217051313c39c84407dd6a323be99a8c322bf8d052a9John McCall 21710acc311bf73c85fd34ce6f89a4e786b7ecd214aaJohn McCallIntRange GetValueRange(ASTContext &C, APValue &result, QualType Ty, 2172f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall unsigned MaxWidth) { 2173f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (result.isInt()) 2174f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return GetValueRange(C, result.getInt(), MaxWidth); 217551313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2176f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (result.isVector()) { 21770acc311bf73c85fd34ce6f89a4e786b7ecd214aaJohn McCall IntRange R = GetValueRange(C, result.getVectorElt(0), Ty, MaxWidth); 21780acc311bf73c85fd34ce6f89a4e786b7ecd214aaJohn McCall for (unsigned i = 1, e = result.getVectorLength(); i != e; ++i) { 21790acc311bf73c85fd34ce6f89a4e786b7ecd214aaJohn McCall IntRange El = GetValueRange(C, result.getVectorElt(i), Ty, MaxWidth); 21800acc311bf73c85fd34ce6f89a4e786b7ecd214aaJohn McCall R = IntRange::join(R, El); 21810acc311bf73c85fd34ce6f89a4e786b7ecd214aaJohn McCall } 2182f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return R; 218351313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 218451313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2185f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (result.isComplexInt()) { 2186f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall IntRange R = GetValueRange(C, result.getComplexIntReal(), MaxWidth); 2187f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall IntRange I = GetValueRange(C, result.getComplexIntImag(), MaxWidth); 2188f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange::join(R, I); 2189f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall } 2190f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2191f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // This can happen with lossless casts to intptr_t of "based" lvalues. 2192f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // Assume it might use arbitrary bits. 21930acc311bf73c85fd34ce6f89a4e786b7ecd214aaJohn McCall // FIXME: The only reason we need to pass the type in here is to get 21940acc311bf73c85fd34ce6f89a4e786b7ecd214aaJohn McCall // the sign right on this one case. It would be nice if APValue 21950acc311bf73c85fd34ce6f89a4e786b7ecd214aaJohn McCall // preserved this. 2196f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall assert(result.isLValue()); 21970acc311bf73c85fd34ce6f89a4e786b7ecd214aaJohn McCall return IntRange(MaxWidth, Ty->isUnsignedIntegerType()); 219851313c39c84407dd6a323be99a8c322bf8d052a9John McCall} 219951313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2200f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// Pseudo-evaluate the given integer expression, estimating the 2201f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// range of values it might take. 2202f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// 2203f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// \param MaxWidth - the width to which the value will be truncated 2204f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCallIntRange GetExprRange(ASTContext &C, Expr *E, unsigned MaxWidth) { 220551313c39c84407dd6a323be99a8c322bf8d052a9John McCall E = E->IgnoreParens(); 220651313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2207f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // Try a full evaluation first. 2208f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall Expr::EvalResult result; 2209f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (E->Evaluate(result, C)) 22100acc311bf73c85fd34ce6f89a4e786b7ecd214aaJohn McCall return GetValueRange(C, result.Val, E->getType(), MaxWidth); 221151313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2212f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // I think we only want to look through implicit casts here; if the 2213f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // user has an explicit widening cast, we should treat the value as 2214f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // being of the new, wider type. 2215f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (ImplicitCastExpr *CE = dyn_cast<ImplicitCastExpr>(E)) { 2216f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (CE->getCastKind() == CastExpr::CK_NoOp) 2217f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return GetExprRange(C, CE->getSubExpr(), MaxWidth); 221851313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2219f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall IntRange OutputTypeRange = IntRange::forType(C, CE->getType()); 222051313c39c84407dd6a323be99a8c322bf8d052a9John McCall 222160fad45739b764886f707bd204eae9ecce6db1f2John McCall bool isIntegerCast = (CE->getCastKind() == CastExpr::CK_IntegralCast); 222260fad45739b764886f707bd204eae9ecce6db1f2John McCall if (!isIntegerCast && CE->getCastKind() == CastExpr::CK_Unknown) 222360fad45739b764886f707bd204eae9ecce6db1f2John McCall isIntegerCast = CE->getSubExpr()->getType()->isIntegerType(); 222460fad45739b764886f707bd204eae9ecce6db1f2John McCall 2225f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // Assume that non-integer casts can span the full range of the type. 222660fad45739b764886f707bd204eae9ecce6db1f2John McCall if (!isIntegerCast) 2227f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return OutputTypeRange; 222851313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2229f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall IntRange SubRange 2230f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall = GetExprRange(C, CE->getSubExpr(), 2231f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall std::min(MaxWidth, OutputTypeRange.Width)); 223251313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2233f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // Bail out if the subexpr's range is as wide as the cast type. 2234f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (SubRange.Width >= OutputTypeRange.Width) 2235f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return OutputTypeRange; 223651313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2237f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // Otherwise, we take the smaller width, and we're non-negative if 2238f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // either the output type or the subexpr is. 2239f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange(SubRange.Width, 2240f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall SubRange.NonNegative || OutputTypeRange.NonNegative); 2241f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall } 2242f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2243f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (ConditionalOperator *CO = dyn_cast<ConditionalOperator>(E)) { 2244f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // If we can fold the condition, just take that operand. 2245f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall bool CondResult; 2246f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (CO->getCond()->EvaluateAsBooleanCondition(CondResult, C)) 2247f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return GetExprRange(C, CondResult ? CO->getTrueExpr() 2248f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall : CO->getFalseExpr(), 2249f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall MaxWidth); 2250f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2251f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // Otherwise, conservatively merge. 2252f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall IntRange L = GetExprRange(C, CO->getTrueExpr(), MaxWidth); 2253f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall IntRange R = GetExprRange(C, CO->getFalseExpr(), MaxWidth); 2254f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange::join(L, R); 225551313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 225651313c39c84407dd6a323be99a8c322bf8d052a9John McCall 225751313c39c84407dd6a323be99a8c322bf8d052a9John McCall if (BinaryOperator *BO = dyn_cast<BinaryOperator>(E)) { 225851313c39c84407dd6a323be99a8c322bf8d052a9John McCall switch (BO->getOpcode()) { 225951313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2260f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // Boolean-valued operations are single-bit and positive. 226151313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::LAnd: 226251313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::LOr: 226351313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::LT: 226451313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::GT: 226551313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::LE: 226651313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::GE: 226751313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::EQ: 226851313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::NE: 2269f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange::forBoolType(); 227051313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2271c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall // The type of these compound assignments is the type of the LHS, 2272c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall // so the RHS is not necessarily an integer. 2273c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall case BinaryOperator::MulAssign: 2274c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall case BinaryOperator::DivAssign: 2275c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall case BinaryOperator::RemAssign: 2276c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall case BinaryOperator::AddAssign: 2277c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall case BinaryOperator::SubAssign: 2278c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall return IntRange::forType(C, E->getType()); 2279c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall 228051313c39c84407dd6a323be99a8c322bf8d052a9John McCall // Operations with opaque sources are black-listed. 228151313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::PtrMemD: 228251313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::PtrMemI: 2283f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange::forType(C, E->getType()); 228451313c39c84407dd6a323be99a8c322bf8d052a9John McCall 228560fad45739b764886f707bd204eae9ecce6db1f2John McCall // Bitwise-and uses the *infinum* of the two source ranges. 228660fad45739b764886f707bd204eae9ecce6db1f2John McCall case BinaryOperator::And: 2287c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall case BinaryOperator::AndAssign: 228860fad45739b764886f707bd204eae9ecce6db1f2John McCall return IntRange::meet(GetExprRange(C, BO->getLHS(), MaxWidth), 228960fad45739b764886f707bd204eae9ecce6db1f2John McCall GetExprRange(C, BO->getRHS(), MaxWidth)); 229060fad45739b764886f707bd204eae9ecce6db1f2John McCall 229151313c39c84407dd6a323be99a8c322bf8d052a9John McCall // Left shift gets black-listed based on a judgement call. 229251313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::Shl: 22933aae6093dd8f3aecb66d7ff1f4b44e6a86765db4John McCall // ...except that we want to treat '1 << (blah)' as logically 22943aae6093dd8f3aecb66d7ff1f4b44e6a86765db4John McCall // positive. It's an important idiom. 22953aae6093dd8f3aecb66d7ff1f4b44e6a86765db4John McCall if (IntegerLiteral *I 22963aae6093dd8f3aecb66d7ff1f4b44e6a86765db4John McCall = dyn_cast<IntegerLiteral>(BO->getLHS()->IgnoreParenCasts())) { 22973aae6093dd8f3aecb66d7ff1f4b44e6a86765db4John McCall if (I->getValue() == 1) { 22983aae6093dd8f3aecb66d7ff1f4b44e6a86765db4John McCall IntRange R = IntRange::forType(C, E->getType()); 22993aae6093dd8f3aecb66d7ff1f4b44e6a86765db4John McCall return IntRange(R.Width, /*NonNegative*/ true); 23003aae6093dd8f3aecb66d7ff1f4b44e6a86765db4John McCall } 23013aae6093dd8f3aecb66d7ff1f4b44e6a86765db4John McCall } 23023aae6093dd8f3aecb66d7ff1f4b44e6a86765db4John McCall // fallthrough 23033aae6093dd8f3aecb66d7ff1f4b44e6a86765db4John McCall 2304c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall case BinaryOperator::ShlAssign: 2305f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange::forType(C, E->getType()); 230651313c39c84407dd6a323be99a8c322bf8d052a9John McCall 230760fad45739b764886f707bd204eae9ecce6db1f2John McCall // Right shift by a constant can narrow its left argument. 2308c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall case BinaryOperator::Shr: 2309c0cd21d2a3301a7a88e0052aebdd09c2441f826dJohn McCall case BinaryOperator::ShrAssign: { 231060fad45739b764886f707bd204eae9ecce6db1f2John McCall IntRange L = GetExprRange(C, BO->getLHS(), MaxWidth); 231160fad45739b764886f707bd204eae9ecce6db1f2John McCall 231260fad45739b764886f707bd204eae9ecce6db1f2John McCall // If the shift amount is a positive constant, drop the width by 231360fad45739b764886f707bd204eae9ecce6db1f2John McCall // that much. 231460fad45739b764886f707bd204eae9ecce6db1f2John McCall llvm::APSInt shift; 231560fad45739b764886f707bd204eae9ecce6db1f2John McCall if (BO->getRHS()->isIntegerConstantExpr(shift, C) && 231660fad45739b764886f707bd204eae9ecce6db1f2John McCall shift.isNonNegative()) { 231760fad45739b764886f707bd204eae9ecce6db1f2John McCall unsigned zext = shift.getZExtValue(); 231860fad45739b764886f707bd204eae9ecce6db1f2John McCall if (zext >= L.Width) 231960fad45739b764886f707bd204eae9ecce6db1f2John McCall L.Width = (L.NonNegative ? 0 : 1); 232060fad45739b764886f707bd204eae9ecce6db1f2John McCall else 232160fad45739b764886f707bd204eae9ecce6db1f2John McCall L.Width -= zext; 232260fad45739b764886f707bd204eae9ecce6db1f2John McCall } 232360fad45739b764886f707bd204eae9ecce6db1f2John McCall 232460fad45739b764886f707bd204eae9ecce6db1f2John McCall return L; 232560fad45739b764886f707bd204eae9ecce6db1f2John McCall } 232660fad45739b764886f707bd204eae9ecce6db1f2John McCall 232760fad45739b764886f707bd204eae9ecce6db1f2John McCall // Comma acts as its right operand. 232851313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::Comma: 2329f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return GetExprRange(C, BO->getRHS(), MaxWidth); 2330f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 233160fad45739b764886f707bd204eae9ecce6db1f2John McCall // Black-list pointer subtractions. 233251313c39c84407dd6a323be99a8c322bf8d052a9John McCall case BinaryOperator::Sub: 233351313c39c84407dd6a323be99a8c322bf8d052a9John McCall if (BO->getLHS()->getType()->isPointerType()) 2334f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange::forType(C, E->getType()); 233551313c39c84407dd6a323be99a8c322bf8d052a9John McCall // fallthrough 23364e4b30ec62d78b24e6556fea2624855c193d0e3eTed Kremenek 233751313c39c84407dd6a323be99a8c322bf8d052a9John McCall default: 2338f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall break; 233951313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 2340f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2341f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // Treat every other operator as if it were closed on the 2342f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall // narrowest type that encompasses both operands. 2343f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall IntRange L = GetExprRange(C, BO->getLHS(), MaxWidth); 2344f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall IntRange R = GetExprRange(C, BO->getRHS(), MaxWidth); 2345f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange::join(L, R); 234651313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 234751313c39c84407dd6a323be99a8c322bf8d052a9John McCall 234851313c39c84407dd6a323be99a8c322bf8d052a9John McCall if (UnaryOperator *UO = dyn_cast<UnaryOperator>(E)) { 234951313c39c84407dd6a323be99a8c322bf8d052a9John McCall switch (UO->getOpcode()) { 235051313c39c84407dd6a323be99a8c322bf8d052a9John McCall // Boolean-valued operations are white-listed. 235151313c39c84407dd6a323be99a8c322bf8d052a9John McCall case UnaryOperator::LNot: 2352f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange::forBoolType(); 235351313c39c84407dd6a323be99a8c322bf8d052a9John McCall 235451313c39c84407dd6a323be99a8c322bf8d052a9John McCall // Operations with opaque sources are black-listed. 235551313c39c84407dd6a323be99a8c322bf8d052a9John McCall case UnaryOperator::Deref: 235651313c39c84407dd6a323be99a8c322bf8d052a9John McCall case UnaryOperator::AddrOf: // should be impossible 235751313c39c84407dd6a323be99a8c322bf8d052a9John McCall case UnaryOperator::OffsetOf: 2358f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange::forType(C, E->getType()); 235951313c39c84407dd6a323be99a8c322bf8d052a9John McCall 236051313c39c84407dd6a323be99a8c322bf8d052a9John McCall default: 2361f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return GetExprRange(C, UO->getSubExpr(), MaxWidth); 236251313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 236351313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 23648ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor 23658ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor if (dyn_cast<OffsetOfExpr>(E)) { 23668ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor IntRange::forType(C, E->getType()); 23678ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor } 236851313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2369f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall FieldDecl *BitField = E->getBitField(); 2370f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (BitField) { 2371f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall llvm::APSInt BitWidthAP = BitField->getBitWidth()->EvaluateAsInt(C); 2372f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall unsigned BitWidth = BitWidthAP.getZExtValue(); 237351313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2374f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange(BitWidth, BitField->getType()->isUnsignedIntegerType()); 2375f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall } 2376f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2377f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IntRange::forType(C, E->getType()); 2378f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall} 2379f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2380323ed74658bc8375278eabf074b4777458376540John McCallIntRange GetExprRange(ASTContext &C, Expr *E) { 2381323ed74658bc8375278eabf074b4777458376540John McCall return GetExprRange(C, E, C.getIntWidth(E->getType())); 2382323ed74658bc8375278eabf074b4777458376540John McCall} 2383323ed74658bc8375278eabf074b4777458376540John McCall 2384f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// Checks whether the given value, which currently has the given 2385f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// source semantics, has the same value when coerced through the 2386f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// target semantics. 2387f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCallbool IsSameFloatAfterCast(const llvm::APFloat &value, 2388f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall const llvm::fltSemantics &Src, 2389f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall const llvm::fltSemantics &Tgt) { 2390f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall llvm::APFloat truncated = value; 2391f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2392f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall bool ignored; 2393f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall truncated.convert(Src, llvm::APFloat::rmNearestTiesToEven, &ignored); 2394f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall truncated.convert(Tgt, llvm::APFloat::rmNearestTiesToEven, &ignored); 2395f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2396f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return truncated.bitwiseIsEqual(value); 239751313c39c84407dd6a323be99a8c322bf8d052a9John McCall} 239851313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2399f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// Checks whether the given value, which currently has the given 2400f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// source semantics, has the same value when coerced through the 2401f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// target semantics. 2402f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// 2403f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall/// The value might be a vector of floats (or a complex number). 2404f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCallbool IsSameFloatAfterCast(const APValue &value, 2405f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall const llvm::fltSemantics &Src, 2406f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall const llvm::fltSemantics &Tgt) { 2407f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (value.isFloat()) 2408f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return IsSameFloatAfterCast(value.getFloat(), Src, Tgt); 2409f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2410f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (value.isVector()) { 2411f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall for (unsigned i = 0, e = value.getVectorLength(); i != e; ++i) 2412f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (!IsSameFloatAfterCast(value.getVectorElt(i), Src, Tgt)) 2413f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return false; 2414f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return true; 2415f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall } 2416f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2417f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall assert(value.isComplexFloat()); 2418f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall return (IsSameFloatAfterCast(value.getComplexFloatReal(), Src, Tgt) && 2419f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall IsSameFloatAfterCast(value.getComplexFloatImag(), Src, Tgt)); 2420f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall} 2421f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2422323ed74658bc8375278eabf074b4777458376540John McCallvoid AnalyzeImplicitConversions(Sema &S, Expr *E); 2423323ed74658bc8375278eabf074b4777458376540John McCall 2424323ed74658bc8375278eabf074b4777458376540John McCallbool IsZero(Sema &S, Expr *E) { 2425323ed74658bc8375278eabf074b4777458376540John McCall llvm::APSInt Value; 2426323ed74658bc8375278eabf074b4777458376540John McCall return E->isIntegerConstantExpr(Value, S.Context) && Value == 0; 2427323ed74658bc8375278eabf074b4777458376540John McCall} 2428323ed74658bc8375278eabf074b4777458376540John McCall 2429323ed74658bc8375278eabf074b4777458376540John McCallvoid CheckTrivialUnsignedComparison(Sema &S, BinaryOperator *E) { 2430323ed74658bc8375278eabf074b4777458376540John McCall BinaryOperator::Opcode op = E->getOpcode(); 2431323ed74658bc8375278eabf074b4777458376540John McCall if (op == BinaryOperator::LT && IsZero(S, E->getRHS())) { 2432323ed74658bc8375278eabf074b4777458376540John McCall S.Diag(E->getOperatorLoc(), diag::warn_lunsigned_always_true_comparison) 2433323ed74658bc8375278eabf074b4777458376540John McCall << "< 0" << "false" 2434323ed74658bc8375278eabf074b4777458376540John McCall << E->getLHS()->getSourceRange() << E->getRHS()->getSourceRange(); 2435323ed74658bc8375278eabf074b4777458376540John McCall } else if (op == BinaryOperator::GE && IsZero(S, E->getRHS())) { 2436323ed74658bc8375278eabf074b4777458376540John McCall S.Diag(E->getOperatorLoc(), diag::warn_lunsigned_always_true_comparison) 2437323ed74658bc8375278eabf074b4777458376540John McCall << ">= 0" << "true" 2438323ed74658bc8375278eabf074b4777458376540John McCall << E->getLHS()->getSourceRange() << E->getRHS()->getSourceRange(); 2439323ed74658bc8375278eabf074b4777458376540John McCall } else if (op == BinaryOperator::GT && IsZero(S, E->getLHS())) { 2440323ed74658bc8375278eabf074b4777458376540John McCall S.Diag(E->getOperatorLoc(), diag::warn_runsigned_always_true_comparison) 2441323ed74658bc8375278eabf074b4777458376540John McCall << "0 >" << "false" 2442323ed74658bc8375278eabf074b4777458376540John McCall << E->getLHS()->getSourceRange() << E->getRHS()->getSourceRange(); 2443323ed74658bc8375278eabf074b4777458376540John McCall } else if (op == BinaryOperator::LE && IsZero(S, E->getLHS())) { 2444323ed74658bc8375278eabf074b4777458376540John McCall S.Diag(E->getOperatorLoc(), diag::warn_runsigned_always_true_comparison) 2445323ed74658bc8375278eabf074b4777458376540John McCall << "0 <=" << "true" 2446323ed74658bc8375278eabf074b4777458376540John McCall << E->getLHS()->getSourceRange() << E->getRHS()->getSourceRange(); 2447323ed74658bc8375278eabf074b4777458376540John McCall } 2448323ed74658bc8375278eabf074b4777458376540John McCall} 2449323ed74658bc8375278eabf074b4777458376540John McCall 2450323ed74658bc8375278eabf074b4777458376540John McCall/// Analyze the operands of the given comparison. Implements the 2451323ed74658bc8375278eabf074b4777458376540John McCall/// fallback case from AnalyzeComparison. 2452323ed74658bc8375278eabf074b4777458376540John McCallvoid AnalyzeImpConvsInComparison(Sema &S, BinaryOperator *E) { 2453323ed74658bc8375278eabf074b4777458376540John McCall AnalyzeImplicitConversions(S, E->getLHS()); 2454323ed74658bc8375278eabf074b4777458376540John McCall AnalyzeImplicitConversions(S, E->getRHS()); 2455323ed74658bc8375278eabf074b4777458376540John McCall} 2456f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2457ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall/// \brief Implements -Wsign-compare. 2458ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall/// 2459ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall/// \param lex the left-hand expression 2460ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall/// \param rex the right-hand expression 2461ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall/// \param OpLoc the location of the joining operator 2462d1b47bf17fde73fac67d8664bd65273742c00ecdJohn McCall/// \param BinOpc binary opcode or 0 2463323ed74658bc8375278eabf074b4777458376540John McCallvoid AnalyzeComparison(Sema &S, BinaryOperator *E) { 2464323ed74658bc8375278eabf074b4777458376540John McCall // The type the comparison is being performed in. 2465323ed74658bc8375278eabf074b4777458376540John McCall QualType T = E->getLHS()->getType(); 2466323ed74658bc8375278eabf074b4777458376540John McCall assert(S.Context.hasSameUnqualifiedType(T, E->getRHS()->getType()) 2467323ed74658bc8375278eabf074b4777458376540John McCall && "comparison with mismatched types"); 2468323ed74658bc8375278eabf074b4777458376540John McCall 2469323ed74658bc8375278eabf074b4777458376540John McCall // We don't do anything special if this isn't an unsigned integral 2470323ed74658bc8375278eabf074b4777458376540John McCall // comparison: we're only interested in integral comparisons, and 2471323ed74658bc8375278eabf074b4777458376540John McCall // signed comparisons only happen in cases we don't care to warn about. 2472f60946222721d9ba3c059563935c17b84703187aDouglas Gregor if (!T->hasUnsignedIntegerRepresentation()) 2473323ed74658bc8375278eabf074b4777458376540John McCall return AnalyzeImpConvsInComparison(S, E); 2474323ed74658bc8375278eabf074b4777458376540John McCall 2475323ed74658bc8375278eabf074b4777458376540John McCall Expr *lex = E->getLHS()->IgnoreParenImpCasts(); 2476323ed74658bc8375278eabf074b4777458376540John McCall Expr *rex = E->getRHS()->IgnoreParenImpCasts(); 2477323ed74658bc8375278eabf074b4777458376540John McCall 2478323ed74658bc8375278eabf074b4777458376540John McCall // Check to see if one of the (unmodified) operands is of different 2479323ed74658bc8375278eabf074b4777458376540John McCall // signedness. 2480323ed74658bc8375278eabf074b4777458376540John McCall Expr *signedOperand, *unsignedOperand; 2481f60946222721d9ba3c059563935c17b84703187aDouglas Gregor if (lex->getType()->hasSignedIntegerRepresentation()) { 2482f60946222721d9ba3c059563935c17b84703187aDouglas Gregor assert(!rex->getType()->hasSignedIntegerRepresentation() && 2483323ed74658bc8375278eabf074b4777458376540John McCall "unsigned comparison between two signed integer expressions?"); 2484323ed74658bc8375278eabf074b4777458376540John McCall signedOperand = lex; 2485323ed74658bc8375278eabf074b4777458376540John McCall unsignedOperand = rex; 2486f60946222721d9ba3c059563935c17b84703187aDouglas Gregor } else if (rex->getType()->hasSignedIntegerRepresentation()) { 2487323ed74658bc8375278eabf074b4777458376540John McCall signedOperand = rex; 2488323ed74658bc8375278eabf074b4777458376540John McCall unsignedOperand = lex; 2489ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall } else { 2490323ed74658bc8375278eabf074b4777458376540John McCall CheckTrivialUnsignedComparison(S, E); 2491323ed74658bc8375278eabf074b4777458376540John McCall return AnalyzeImpConvsInComparison(S, E); 2492ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall } 2493ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall 2494323ed74658bc8375278eabf074b4777458376540John McCall // Otherwise, calculate the effective range of the signed operand. 2495323ed74658bc8375278eabf074b4777458376540John McCall IntRange signedRange = GetExprRange(S.Context, signedOperand); 2496f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall 2497323ed74658bc8375278eabf074b4777458376540John McCall // Go ahead and analyze implicit conversions in the operands. Note 2498323ed74658bc8375278eabf074b4777458376540John McCall // that we skip the implicit conversions on both sides. 2499323ed74658bc8375278eabf074b4777458376540John McCall AnalyzeImplicitConversions(S, lex); 2500323ed74658bc8375278eabf074b4777458376540John McCall AnalyzeImplicitConversions(S, rex); 2501ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall 2502323ed74658bc8375278eabf074b4777458376540John McCall // If the signed range is non-negative, -Wsign-compare won't fire, 2503323ed74658bc8375278eabf074b4777458376540John McCall // but we should still check for comparisons which are always true 2504323ed74658bc8375278eabf074b4777458376540John McCall // or false. 2505323ed74658bc8375278eabf074b4777458376540John McCall if (signedRange.NonNegative) 2506323ed74658bc8375278eabf074b4777458376540John McCall return CheckTrivialUnsignedComparison(S, E); 2507ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall 2508ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall // For (in)equality comparisons, if the unsigned operand is a 2509ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall // constant which cannot collide with a overflowed signed operand, 2510ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall // then reinterpreting the signed operand as unsigned will not 2511ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall // change the result of the comparison. 2512323ed74658bc8375278eabf074b4777458376540John McCall if (E->isEqualityOp()) { 2513323ed74658bc8375278eabf074b4777458376540John McCall unsigned comparisonWidth = S.Context.getIntWidth(T); 2514323ed74658bc8375278eabf074b4777458376540John McCall IntRange unsignedRange = GetExprRange(S.Context, unsignedOperand); 2515323ed74658bc8375278eabf074b4777458376540John McCall 2516323ed74658bc8375278eabf074b4777458376540John McCall // We should never be unable to prove that the unsigned operand is 2517323ed74658bc8375278eabf074b4777458376540John McCall // non-negative. 2518323ed74658bc8375278eabf074b4777458376540John McCall assert(unsignedRange.NonNegative && "unsigned range includes negative?"); 2519ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall 2520323ed74658bc8375278eabf074b4777458376540John McCall if (unsignedRange.Width < comparisonWidth) 2521323ed74658bc8375278eabf074b4777458376540John McCall return; 2522323ed74658bc8375278eabf074b4777458376540John McCall } 2523323ed74658bc8375278eabf074b4777458376540John McCall 2524323ed74658bc8375278eabf074b4777458376540John McCall S.Diag(E->getOperatorLoc(), diag::warn_mixed_sign_comparison) 2525323ed74658bc8375278eabf074b4777458376540John McCall << lex->getType() << rex->getType() 2526323ed74658bc8375278eabf074b4777458376540John McCall << lex->getSourceRange() << rex->getSourceRange(); 2527ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall} 2528ba26e58c64b4f6233dfc4bcd3ef6ce83aab47ffcJohn McCall 252951313c39c84407dd6a323be99a8c322bf8d052a9John McCall/// Diagnose an implicit cast; purely a helper for CheckImplicitConversion. 2530323ed74658bc8375278eabf074b4777458376540John McCallvoid DiagnoseImpCast(Sema &S, Expr *E, QualType T, unsigned diag) { 253151313c39c84407dd6a323be99a8c322bf8d052a9John McCall S.Diag(E->getExprLoc(), diag) << E->getType() << T << E->getSourceRange(); 253251313c39c84407dd6a323be99a8c322bf8d052a9John McCall} 253351313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2534323ed74658bc8375278eabf074b4777458376540John McCallvoid CheckImplicitConversion(Sema &S, Expr *E, QualType T, 2535323ed74658bc8375278eabf074b4777458376540John McCall bool *ICContext = 0) { 2536323ed74658bc8375278eabf074b4777458376540John McCall if (E->isTypeDependent() || E->isValueDependent()) return; 253751313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2538323ed74658bc8375278eabf074b4777458376540John McCall const Type *Source = S.Context.getCanonicalType(E->getType()).getTypePtr(); 2539323ed74658bc8375278eabf074b4777458376540John McCall const Type *Target = S.Context.getCanonicalType(T).getTypePtr(); 2540323ed74658bc8375278eabf074b4777458376540John McCall if (Source == Target) return; 2541323ed74658bc8375278eabf074b4777458376540John McCall if (Target->isDependentType()) return; 254251313c39c84407dd6a323be99a8c322bf8d052a9John McCall 254351313c39c84407dd6a323be99a8c322bf8d052a9John McCall // Never diagnose implicit casts to bool. 254451313c39c84407dd6a323be99a8c322bf8d052a9John McCall if (Target->isSpecificBuiltinType(BuiltinType::Bool)) 254551313c39c84407dd6a323be99a8c322bf8d052a9John McCall return; 254651313c39c84407dd6a323be99a8c322bf8d052a9John McCall 254751313c39c84407dd6a323be99a8c322bf8d052a9John McCall // Strip vector types. 254851313c39c84407dd6a323be99a8c322bf8d052a9John McCall if (isa<VectorType>(Source)) { 254951313c39c84407dd6a323be99a8c322bf8d052a9John McCall if (!isa<VectorType>(Target)) 2550323ed74658bc8375278eabf074b4777458376540John McCall return DiagnoseImpCast(S, E, T, diag::warn_impcast_vector_scalar); 255151313c39c84407dd6a323be99a8c322bf8d052a9John McCall 255251313c39c84407dd6a323be99a8c322bf8d052a9John McCall Source = cast<VectorType>(Source)->getElementType().getTypePtr(); 255351313c39c84407dd6a323be99a8c322bf8d052a9John McCall Target = cast<VectorType>(Target)->getElementType().getTypePtr(); 255451313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 255551313c39c84407dd6a323be99a8c322bf8d052a9John McCall 255651313c39c84407dd6a323be99a8c322bf8d052a9John McCall // Strip complex types. 255751313c39c84407dd6a323be99a8c322bf8d052a9John McCall if (isa<ComplexType>(Source)) { 255851313c39c84407dd6a323be99a8c322bf8d052a9John McCall if (!isa<ComplexType>(Target)) 2559323ed74658bc8375278eabf074b4777458376540John McCall return DiagnoseImpCast(S, E, T, diag::warn_impcast_complex_scalar); 256051313c39c84407dd6a323be99a8c322bf8d052a9John McCall 256151313c39c84407dd6a323be99a8c322bf8d052a9John McCall Source = cast<ComplexType>(Source)->getElementType().getTypePtr(); 256251313c39c84407dd6a323be99a8c322bf8d052a9John McCall Target = cast<ComplexType>(Target)->getElementType().getTypePtr(); 256351313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 256451313c39c84407dd6a323be99a8c322bf8d052a9John McCall 256551313c39c84407dd6a323be99a8c322bf8d052a9John McCall const BuiltinType *SourceBT = dyn_cast<BuiltinType>(Source); 256651313c39c84407dd6a323be99a8c322bf8d052a9John McCall const BuiltinType *TargetBT = dyn_cast<BuiltinType>(Target); 256751313c39c84407dd6a323be99a8c322bf8d052a9John McCall 256851313c39c84407dd6a323be99a8c322bf8d052a9John McCall // If the source is floating point... 256951313c39c84407dd6a323be99a8c322bf8d052a9John McCall if (SourceBT && SourceBT->isFloatingPoint()) { 257051313c39c84407dd6a323be99a8c322bf8d052a9John McCall // ...and the target is floating point... 257151313c39c84407dd6a323be99a8c322bf8d052a9John McCall if (TargetBT && TargetBT->isFloatingPoint()) { 257251313c39c84407dd6a323be99a8c322bf8d052a9John McCall // ...then warn if we're dropping FP rank. 257351313c39c84407dd6a323be99a8c322bf8d052a9John McCall 257451313c39c84407dd6a323be99a8c322bf8d052a9John McCall // Builtin FP kinds are ordered by increasing FP rank. 257551313c39c84407dd6a323be99a8c322bf8d052a9John McCall if (SourceBT->getKind() > TargetBT->getKind()) { 257651313c39c84407dd6a323be99a8c322bf8d052a9John McCall // Don't warn about float constants that are precisely 257751313c39c84407dd6a323be99a8c322bf8d052a9John McCall // representable in the target type. 257851313c39c84407dd6a323be99a8c322bf8d052a9John McCall Expr::EvalResult result; 2579323ed74658bc8375278eabf074b4777458376540John McCall if (E->Evaluate(result, S.Context)) { 258051313c39c84407dd6a323be99a8c322bf8d052a9John McCall // Value might be a float, a float vector, or a float complex. 258151313c39c84407dd6a323be99a8c322bf8d052a9John McCall if (IsSameFloatAfterCast(result.Val, 2582323ed74658bc8375278eabf074b4777458376540John McCall S.Context.getFloatTypeSemantics(QualType(TargetBT, 0)), 2583323ed74658bc8375278eabf074b4777458376540John McCall S.Context.getFloatTypeSemantics(QualType(SourceBT, 0)))) 258451313c39c84407dd6a323be99a8c322bf8d052a9John McCall return; 258551313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 258651313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2587323ed74658bc8375278eabf074b4777458376540John McCall DiagnoseImpCast(S, E, T, diag::warn_impcast_float_precision); 258851313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 258951313c39c84407dd6a323be99a8c322bf8d052a9John McCall return; 259051313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 259151313c39c84407dd6a323be99a8c322bf8d052a9John McCall 259251313c39c84407dd6a323be99a8c322bf8d052a9John McCall // If the target is integral, always warn. 259351313c39c84407dd6a323be99a8c322bf8d052a9John McCall if ((TargetBT && TargetBT->isInteger())) 259451313c39c84407dd6a323be99a8c322bf8d052a9John McCall // TODO: don't warn for integer values? 2595323ed74658bc8375278eabf074b4777458376540John McCall DiagnoseImpCast(S, E, T, diag::warn_impcast_float_integer); 259651313c39c84407dd6a323be99a8c322bf8d052a9John McCall 259751313c39c84407dd6a323be99a8c322bf8d052a9John McCall return; 259851313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 259951313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2600f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (!Source->isIntegerType() || !Target->isIntegerType()) 260151313c39c84407dd6a323be99a8c322bf8d052a9John McCall return; 260251313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2603323ed74658bc8375278eabf074b4777458376540John McCall IntRange SourceRange = GetExprRange(S.Context, E); 2604323ed74658bc8375278eabf074b4777458376540John McCall IntRange TargetRange = IntRange::forCanonicalType(S.Context, Target); 260551313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2606f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (SourceRange.Width > TargetRange.Width) { 260751313c39c84407dd6a323be99a8c322bf8d052a9John McCall // People want to build with -Wshorten-64-to-32 and not -Wconversion 260851313c39c84407dd6a323be99a8c322bf8d052a9John McCall // and by god we'll let them. 2609f2370c9b4aade940e2253b5b33262ba507d1d71fJohn McCall if (SourceRange.Width == 64 && TargetRange.Width == 32) 2610323ed74658bc8375278eabf074b4777458376540John McCall return DiagnoseImpCast(S, E, T, diag::warn_impcast_integer_64_32); 2611323ed74658bc8375278eabf074b4777458376540John McCall return DiagnoseImpCast(S, E, T, diag::warn_impcast_integer_precision); 2612323ed74658bc8375278eabf074b4777458376540John McCall } 2613323ed74658bc8375278eabf074b4777458376540John McCall 2614323ed74658bc8375278eabf074b4777458376540John McCall if ((TargetRange.NonNegative && !SourceRange.NonNegative) || 2615323ed74658bc8375278eabf074b4777458376540John McCall (!TargetRange.NonNegative && SourceRange.NonNegative && 2616323ed74658bc8375278eabf074b4777458376540John McCall SourceRange.Width == TargetRange.Width)) { 2617323ed74658bc8375278eabf074b4777458376540John McCall unsigned DiagID = diag::warn_impcast_integer_sign; 2618323ed74658bc8375278eabf074b4777458376540John McCall 2619323ed74658bc8375278eabf074b4777458376540John McCall // Traditionally, gcc has warned about this under -Wsign-compare. 2620323ed74658bc8375278eabf074b4777458376540John McCall // We also want to warn about it in -Wconversion. 2621323ed74658bc8375278eabf074b4777458376540John McCall // So if -Wconversion is off, use a completely identical diagnostic 2622323ed74658bc8375278eabf074b4777458376540John McCall // in the sign-compare group. 2623323ed74658bc8375278eabf074b4777458376540John McCall // The conditional-checking code will 2624323ed74658bc8375278eabf074b4777458376540John McCall if (ICContext) { 2625323ed74658bc8375278eabf074b4777458376540John McCall DiagID = diag::warn_impcast_integer_sign_conditional; 2626323ed74658bc8375278eabf074b4777458376540John McCall *ICContext = true; 2627323ed74658bc8375278eabf074b4777458376540John McCall } 2628323ed74658bc8375278eabf074b4777458376540John McCall 2629323ed74658bc8375278eabf074b4777458376540John McCall return DiagnoseImpCast(S, E, T, DiagID); 263051313c39c84407dd6a323be99a8c322bf8d052a9John McCall } 263151313c39c84407dd6a323be99a8c322bf8d052a9John McCall 263251313c39c84407dd6a323be99a8c322bf8d052a9John McCall return; 263351313c39c84407dd6a323be99a8c322bf8d052a9John McCall} 263451313c39c84407dd6a323be99a8c322bf8d052a9John McCall 2635323ed74658bc8375278eabf074b4777458376540John McCallvoid CheckConditionalOperator(Sema &S, ConditionalOperator *E, QualType T); 2636323ed74658bc8375278eabf074b4777458376540John McCall 2637323ed74658bc8375278eabf074b4777458376540John McCallvoid CheckConditionalOperand(Sema &S, Expr *E, QualType T, 2638323ed74658bc8375278eabf074b4777458376540John McCall bool &ICContext) { 2639323ed74658bc8375278eabf074b4777458376540John McCall E = E->IgnoreParenImpCasts(); 2640323ed74658bc8375278eabf074b4777458376540John McCall 2641323ed74658bc8375278eabf074b4777458376540John McCall if (isa<ConditionalOperator>(E)) 2642323ed74658bc8375278eabf074b4777458376540John McCall return CheckConditionalOperator(S, cast<ConditionalOperator>(E), T); 2643323ed74658bc8375278eabf074b4777458376540John McCall 2644323ed74658bc8375278eabf074b4777458376540John McCall AnalyzeImplicitConversions(S, E); 2645323ed74658bc8375278eabf074b4777458376540John McCall if (E->getType() != T) 2646323ed74658bc8375278eabf074b4777458376540John McCall return CheckImplicitConversion(S, E, T, &ICContext); 2647323ed74658bc8375278eabf074b4777458376540John McCall return; 2648323ed74658bc8375278eabf074b4777458376540John McCall} 2649323ed74658bc8375278eabf074b4777458376540John McCall 2650323ed74658bc8375278eabf074b4777458376540John McCallvoid CheckConditionalOperator(Sema &S, ConditionalOperator *E, QualType T) { 2651323ed74658bc8375278eabf074b4777458376540John McCall AnalyzeImplicitConversions(S, E->getCond()); 2652323ed74658bc8375278eabf074b4777458376540John McCall 2653323ed74658bc8375278eabf074b4777458376540John McCall bool Suspicious = false; 2654323ed74658bc8375278eabf074b4777458376540John McCall CheckConditionalOperand(S, E->getTrueExpr(), T, Suspicious); 2655323ed74658bc8375278eabf074b4777458376540John McCall CheckConditionalOperand(S, E->getFalseExpr(), T, Suspicious); 2656323ed74658bc8375278eabf074b4777458376540John McCall 2657323ed74658bc8375278eabf074b4777458376540John McCall // If -Wconversion would have warned about either of the candidates 2658323ed74658bc8375278eabf074b4777458376540John McCall // for a signedness conversion to the context type... 2659323ed74658bc8375278eabf074b4777458376540John McCall if (!Suspicious) return; 2660323ed74658bc8375278eabf074b4777458376540John McCall 2661323ed74658bc8375278eabf074b4777458376540John McCall // ...but it's currently ignored... 2662323ed74658bc8375278eabf074b4777458376540John McCall if (S.Diags.getDiagnosticLevel(diag::warn_impcast_integer_sign_conditional)) 2663323ed74658bc8375278eabf074b4777458376540John McCall return; 2664323ed74658bc8375278eabf074b4777458376540John McCall 2665323ed74658bc8375278eabf074b4777458376540John McCall // ...and -Wsign-compare isn't... 2666323ed74658bc8375278eabf074b4777458376540John McCall if (!S.Diags.getDiagnosticLevel(diag::warn_mixed_sign_conditional)) 2667323ed74658bc8375278eabf074b4777458376540John McCall return; 2668323ed74658bc8375278eabf074b4777458376540John McCall 2669323ed74658bc8375278eabf074b4777458376540John McCall // ...then check whether it would have warned about either of the 2670323ed74658bc8375278eabf074b4777458376540John McCall // candidates for a signedness conversion to the condition type. 2671323ed74658bc8375278eabf074b4777458376540John McCall if (E->getType() != T) { 2672323ed74658bc8375278eabf074b4777458376540John McCall Suspicious = false; 2673323ed74658bc8375278eabf074b4777458376540John McCall CheckImplicitConversion(S, E->getTrueExpr()->IgnoreParenImpCasts(), 2674323ed74658bc8375278eabf074b4777458376540John McCall E->getType(), &Suspicious); 2675323ed74658bc8375278eabf074b4777458376540John McCall if (!Suspicious) 2676323ed74658bc8375278eabf074b4777458376540John McCall CheckImplicitConversion(S, E->getFalseExpr()->IgnoreParenImpCasts(), 2677323ed74658bc8375278eabf074b4777458376540John McCall E->getType(), &Suspicious); 2678323ed74658bc8375278eabf074b4777458376540John McCall if (!Suspicious) 2679323ed74658bc8375278eabf074b4777458376540John McCall return; 2680323ed74658bc8375278eabf074b4777458376540John McCall } 2681323ed74658bc8375278eabf074b4777458376540John McCall 2682323ed74658bc8375278eabf074b4777458376540John McCall // If so, emit a diagnostic under -Wsign-compare. 2683323ed74658bc8375278eabf074b4777458376540John McCall Expr *lex = E->getTrueExpr()->IgnoreParenImpCasts(); 2684323ed74658bc8375278eabf074b4777458376540John McCall Expr *rex = E->getFalseExpr()->IgnoreParenImpCasts(); 2685323ed74658bc8375278eabf074b4777458376540John McCall S.Diag(E->getQuestionLoc(), diag::warn_mixed_sign_conditional) 2686323ed74658bc8375278eabf074b4777458376540John McCall << lex->getType() << rex->getType() 2687323ed74658bc8375278eabf074b4777458376540John McCall << lex->getSourceRange() << rex->getSourceRange(); 2688323ed74658bc8375278eabf074b4777458376540John McCall} 2689323ed74658bc8375278eabf074b4777458376540John McCall 2690323ed74658bc8375278eabf074b4777458376540John McCall/// AnalyzeImplicitConversions - Find and report any interesting 2691323ed74658bc8375278eabf074b4777458376540John McCall/// implicit conversions in the given expression. There are a couple 2692323ed74658bc8375278eabf074b4777458376540John McCall/// of competing diagnostics here, -Wconversion and -Wsign-compare. 2693323ed74658bc8375278eabf074b4777458376540John McCallvoid AnalyzeImplicitConversions(Sema &S, Expr *OrigE) { 2694323ed74658bc8375278eabf074b4777458376540John McCall QualType T = OrigE->getType(); 2695323ed74658bc8375278eabf074b4777458376540John McCall Expr *E = OrigE->IgnoreParenImpCasts(); 2696323ed74658bc8375278eabf074b4777458376540John McCall 2697323ed74658bc8375278eabf074b4777458376540John McCall // For conditional operators, we analyze the arguments as if they 2698323ed74658bc8375278eabf074b4777458376540John McCall // were being fed directly into the output. 2699323ed74658bc8375278eabf074b4777458376540John McCall if (isa<ConditionalOperator>(E)) { 2700323ed74658bc8375278eabf074b4777458376540John McCall ConditionalOperator *CO = cast<ConditionalOperator>(E); 2701323ed74658bc8375278eabf074b4777458376540John McCall CheckConditionalOperator(S, CO, T); 2702323ed74658bc8375278eabf074b4777458376540John McCall return; 2703323ed74658bc8375278eabf074b4777458376540John McCall } 2704323ed74658bc8375278eabf074b4777458376540John McCall 2705323ed74658bc8375278eabf074b4777458376540John McCall // Go ahead and check any implicit conversions we might have skipped. 2706323ed74658bc8375278eabf074b4777458376540John McCall // The non-canonical typecheck is just an optimization; 2707323ed74658bc8375278eabf074b4777458376540John McCall // CheckImplicitConversion will filter out dead implicit conversions. 2708323ed74658bc8375278eabf074b4777458376540John McCall if (E->getType() != T) 2709323ed74658bc8375278eabf074b4777458376540John McCall CheckImplicitConversion(S, E, T); 2710323ed74658bc8375278eabf074b4777458376540John McCall 2711323ed74658bc8375278eabf074b4777458376540John McCall // Now continue drilling into this expression. 2712323ed74658bc8375278eabf074b4777458376540John McCall 2713323ed74658bc8375278eabf074b4777458376540John McCall // Skip past explicit casts. 2714323ed74658bc8375278eabf074b4777458376540John McCall if (isa<ExplicitCastExpr>(E)) { 2715323ed74658bc8375278eabf074b4777458376540John McCall E = cast<ExplicitCastExpr>(E)->getSubExpr()->IgnoreParenImpCasts(); 2716323ed74658bc8375278eabf074b4777458376540John McCall return AnalyzeImplicitConversions(S, E); 2717323ed74658bc8375278eabf074b4777458376540John McCall } 2718323ed74658bc8375278eabf074b4777458376540John McCall 2719323ed74658bc8375278eabf074b4777458376540John McCall // Do a somewhat different check with comparison operators. 2720323ed74658bc8375278eabf074b4777458376540John McCall if (isa<BinaryOperator>(E) && cast<BinaryOperator>(E)->isComparisonOp()) 2721323ed74658bc8375278eabf074b4777458376540John McCall return AnalyzeComparison(S, cast<BinaryOperator>(E)); 2722323ed74658bc8375278eabf074b4777458376540John McCall 2723323ed74658bc8375278eabf074b4777458376540John McCall // These break the otherwise-useful invariant below. Fortunately, 2724323ed74658bc8375278eabf074b4777458376540John McCall // we don't really need to recurse into them, because any internal 2725323ed74658bc8375278eabf074b4777458376540John McCall // expressions should have been analyzed already when they were 2726323ed74658bc8375278eabf074b4777458376540John McCall // built into statements. 2727323ed74658bc8375278eabf074b4777458376540John McCall if (isa<StmtExpr>(E)) return; 2728323ed74658bc8375278eabf074b4777458376540John McCall 2729323ed74658bc8375278eabf074b4777458376540John McCall // Don't descend into unevaluated contexts. 2730323ed74658bc8375278eabf074b4777458376540John McCall if (isa<SizeOfAlignOfExpr>(E)) return; 2731323ed74658bc8375278eabf074b4777458376540John McCall 2732323ed74658bc8375278eabf074b4777458376540John McCall // Now just recurse over the expression's children. 2733323ed74658bc8375278eabf074b4777458376540John McCall for (Stmt::child_iterator I = E->child_begin(), IE = E->child_end(); 2734323ed74658bc8375278eabf074b4777458376540John McCall I != IE; ++I) 2735323ed74658bc8375278eabf074b4777458376540John McCall AnalyzeImplicitConversions(S, cast<Expr>(*I)); 2736323ed74658bc8375278eabf074b4777458376540John McCall} 2737323ed74658bc8375278eabf074b4777458376540John McCall 2738323ed74658bc8375278eabf074b4777458376540John McCall} // end anonymous namespace 2739323ed74658bc8375278eabf074b4777458376540John McCall 2740323ed74658bc8375278eabf074b4777458376540John McCall/// Diagnoses "dangerous" implicit conversions within the given 2741323ed74658bc8375278eabf074b4777458376540John McCall/// expression (which is a full expression). Implements -Wconversion 2742323ed74658bc8375278eabf074b4777458376540John McCall/// and -Wsign-compare. 2743323ed74658bc8375278eabf074b4777458376540John McCallvoid Sema::CheckImplicitConversions(Expr *E) { 2744323ed74658bc8375278eabf074b4777458376540John McCall // Don't diagnose in unevaluated contexts. 2745323ed74658bc8375278eabf074b4777458376540John McCall if (ExprEvalContexts.back().Context == Sema::Unevaluated) 2746323ed74658bc8375278eabf074b4777458376540John McCall return; 2747323ed74658bc8375278eabf074b4777458376540John McCall 2748323ed74658bc8375278eabf074b4777458376540John McCall // Don't diagnose for value- or type-dependent expressions. 2749323ed74658bc8375278eabf074b4777458376540John McCall if (E->isTypeDependent() || E->isValueDependent()) 2750323ed74658bc8375278eabf074b4777458376540John McCall return; 2751323ed74658bc8375278eabf074b4777458376540John McCall 2752323ed74658bc8375278eabf074b4777458376540John McCall AnalyzeImplicitConversions(*this, E); 2753323ed74658bc8375278eabf074b4777458376540John McCall} 2754323ed74658bc8375278eabf074b4777458376540John McCall 2755f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump/// CheckParmsForFunctionDef - Check that the parameters of the given 2756f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump/// function are appropriate for the definition of a function. This 2757f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump/// takes care of any checks that cannot be performed on the 2758f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump/// declaration itself, e.g., that the types of each of the function 2759f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump/// parameters are complete. 2760f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stumpbool Sema::CheckParmsForFunctionDef(FunctionDecl *FD) { 2761f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump bool HasInvalidParm = false; 2762f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump for (unsigned p = 0, NumParams = FD->getNumParams(); p < NumParams; ++p) { 2763f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump ParmVarDecl *Param = FD->getParamDecl(p); 2764f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump 2765f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump // C99 6.7.5.3p4: the parameters in a parameter type list in a 2766f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump // function declarator that is part of a function definition of 2767f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump // that function shall not have incomplete type. 2768f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump // 2769f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump // This is also C++ [dcl.fct]p6. 2770f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump if (!Param->isInvalidDecl() && 2771f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump RequireCompleteType(Param->getLocation(), Param->getType(), 2772f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump diag::err_typecheck_decl_incomplete_type)) { 2773f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump Param->setInvalidDecl(); 2774f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump HasInvalidParm = true; 2775f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump } 2776f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump 2777f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump // C99 6.9.1p5: If the declarator includes a parameter type list, the 2778f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump // declaration of each parameter shall include an identifier. 2779f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump if (Param->getIdentifier() == 0 && 2780f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump !Param->isImplicit() && 2781f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump !getLangOptions().CPlusPlus) 2782f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump Diag(Param->getLocation(), diag::err_parameter_name_omitted); 2783d17e340e2d516139931768697bf080f60920ba9dSam Weinig 2784d17e340e2d516139931768697bf080f60920ba9dSam Weinig // C99 6.7.5.3p12: 2785d17e340e2d516139931768697bf080f60920ba9dSam Weinig // If the function declarator is not part of a definition of that 2786d17e340e2d516139931768697bf080f60920ba9dSam Weinig // function, parameters may have incomplete type and may use the [*] 2787d17e340e2d516139931768697bf080f60920ba9dSam Weinig // notation in their sequences of declarator specifiers to specify 2788d17e340e2d516139931768697bf080f60920ba9dSam Weinig // variable length array types. 2789d17e340e2d516139931768697bf080f60920ba9dSam Weinig QualType PType = Param->getOriginalType(); 2790d17e340e2d516139931768697bf080f60920ba9dSam Weinig if (const ArrayType *AT = Context.getAsArrayType(PType)) { 2791d17e340e2d516139931768697bf080f60920ba9dSam Weinig if (AT->getSizeModifier() == ArrayType::Star) { 2792d17e340e2d516139931768697bf080f60920ba9dSam Weinig // FIXME: This diagnosic should point the the '[*]' if source-location 2793d17e340e2d516139931768697bf080f60920ba9dSam Weinig // information is added for it. 2794d17e340e2d516139931768697bf080f60920ba9dSam Weinig Diag(Param->getLocation(), diag::err_array_star_in_function_definition); 2795d17e340e2d516139931768697bf080f60920ba9dSam Weinig } 2796d17e340e2d516139931768697bf080f60920ba9dSam Weinig } 2797f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump } 2798f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump 2799f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump return HasInvalidParm; 2800f8c4921c73d73123e2b79221ad4f1775ce984cfdMike Stump} 2801