diff options
author | Ted Kremenek <kremenek@apple.com> | 2010-07-26 19:45:42 +0000 |
---|---|---|
committer | Ted Kremenek <kremenek@apple.com> | 2010-07-26 19:45:42 +0000 |
commit | 6adb7e35ab9a09a60f7088c757d30502c5a7b19a (patch) | |
tree | 9239bb668b0f420e390addf524693739b916b5dd /clang/lib/Sema/SemaChecking.cpp | |
parent | 6005082354ace9ad9be35f7e0134c9c9dd273471 (diff) | |
download | bcm5719-llvm-6adb7e35ab9a09a60f7088c757d30502c5a7b19a.tar.gz bcm5719-llvm-6adb7e35ab9a09a60f7088c757d30502c5a7b19a.zip |
Consolidate #args checking for scanf/printf format strings.
llvm-svn: 109427
Diffstat (limited to 'clang/lib/Sema/SemaChecking.cpp')
-rw-r--r-- | clang/lib/Sema/SemaChecking.cpp | 61 |
1 files changed, 31 insertions, 30 deletions
diff --git a/clang/lib/Sema/SemaChecking.cpp b/clang/lib/Sema/SemaChecking.cpp index cf22fcf5836..03ca084dd89 100644 --- a/clang/lib/Sema/SemaChecking.cpp +++ b/clang/lib/Sema/SemaChecking.cpp @@ -1169,6 +1169,11 @@ protected: SourceLocation getLocationOfByte(const char *x); const Expr *getDataArg(unsigned i) const; + + bool CheckNumArgs(const analyze_format_string::FormatSpecifier &FS, + const analyze_format_string::ConversionSpecifier &CS, + const char *startSpecifier, unsigned specifierLen, + unsigned argIndex); }; } @@ -1270,6 +1275,30 @@ CheckFormatHandler::HandleInvalidConversionSpecifier(unsigned argIndex, return keepGoing; } +bool +CheckFormatHandler::CheckNumArgs( + const analyze_format_string::FormatSpecifier &FS, + const analyze_format_string::ConversionSpecifier &CS, + const char *startSpecifier, unsigned specifierLen, unsigned argIndex) { + + if (argIndex >= NumDataArgs) { + if (FS.usesPositionalArg()) { + S.Diag(getLocationOfByte(CS.getStart()), + diag::warn_printf_positional_arg_exceeds_data_args) + << (argIndex+1) << NumDataArgs + << getSpecifierRange(startSpecifier, specifierLen); + } + else { + S.Diag(getLocationOfByte(CS.getStart()), + diag::warn_printf_insufficient_data_args) + << getSpecifierRange(startSpecifier, specifierLen); + } + + return false; + } + return true; +} + //===--- CHECK: Printf format string checking ------------------------------===// namespace { @@ -1538,22 +1567,8 @@ CheckPrintfHandler::HandlePrintfSpecifier(const analyze_printf::PrintfSpecifier if (HasVAListArg) return true; - if (argIndex >= NumDataArgs) { - if (FS.usesPositionalArg()) { - S.Diag(getLocationOfByte(CS.getStart()), - diag::warn_printf_positional_arg_exceeds_data_args) - << (argIndex+1) << NumDataArgs - << getSpecifierRange(startSpecifier, specifierLen); - } - else { - S.Diag(getLocationOfByte(CS.getStart()), - diag::warn_printf_insufficient_data_args) - << getSpecifierRange(startSpecifier, specifierLen); - } - - // Don't do any more checking. + if (!CheckNumArgs(FS, CS, startSpecifier, specifierLen, argIndex)) return false; - } // Now type check the data expression that matches the // format specifier. @@ -1714,22 +1729,8 @@ bool CheckScanfHandler::HandleScanfSpecifier( if (HasVAListArg) return true; - if (argIndex >= NumDataArgs) { - if (FS.usesPositionalArg()) { - S.Diag(getLocationOfByte(CS.getStart()), - diag::warn_printf_positional_arg_exceeds_data_args) - << (argIndex+1) << NumDataArgs - << getSpecifierRange(startSpecifier, specifierLen); - } - else { - S.Diag(getLocationOfByte(CS.getStart()), - diag::warn_printf_insufficient_data_args) - << getSpecifierRange(startSpecifier, specifierLen); - } - - // Don't do any more checking. + if (!CheckNumArgs(FS, CS, startSpecifier, specifierLen, argIndex)) return false; - } // FIXME: Check that the argument type matches the format specifier. |