Add support for format string checking of object-size checking
versions of sprintf and friends.
 - Added FIXME that this mechanism should be generalized.


git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@56962 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/Sema/SemaChecking.cpp b/lib/Sema/SemaChecking.cpp
index f870e26..27f3abe 100644
--- a/lib/Sema/SemaChecking.cpp
+++ b/lib/Sema/SemaChecking.cpp
@@ -66,7 +66,11 @@
     if (SemaBuiltinObjectSize(TheCall.get()))
       return true;
   }
-  
+
+  // FIXME: This mechanism should be abstracted to be less fragile and
+  // more efficient. For example, just map function ids to custom
+  // handlers.
+
   // Search the KnownFunctionIDs for the identifier.
   unsigned i = 0, e = id_num_known_functions;
   for (; i != e; ++i) { if (KnownFunctionIDs[i] == FnInfo) break; }
@@ -81,17 +85,21 @@
     
     switch (i) {
     default: assert(false && "No format string argument index.");
-    case id_printf:    format_idx = 0; break;
-    case id_fprintf:   format_idx = 1; break;
-    case id_sprintf:   format_idx = 1; break;
-    case id_snprintf:  format_idx = 2; break;
-    case id_asprintf:  format_idx = 1; break;
-    case id_NSLog:     format_idx = 0; break;
-    case id_vsnprintf: format_idx = 2; HasVAListArg = true; break;
-    case id_vasprintf: format_idx = 1; HasVAListArg = true; break;
-    case id_vfprintf:  format_idx = 1; HasVAListArg = true; break;
-    case id_vsprintf:  format_idx = 1; HasVAListArg = true; break;
-    case id_vprintf:   format_idx = 0; HasVAListArg = true; break;
+    case id_NSLog:         format_idx = 0; break;
+    case id_asprintf:      format_idx = 1; break;
+    case id_fprintf:       format_idx = 1; break;
+    case id_printf:        format_idx = 0; break;
+    case id_snprintf:      format_idx = 2; break;
+    case id_snprintf_chk:  format_idx = 4; break;
+    case id_sprintf:       format_idx = 1; break;
+    case id_sprintf_chk:   format_idx = 3; break;
+    case id_vasprintf:     format_idx = 1; HasVAListArg = true; break;
+    case id_vfprintf:      format_idx = 1; HasVAListArg = true; break;
+    case id_vsnprintf:     format_idx = 2; HasVAListArg = true; break;
+    case id_vsnprintf_chk: format_idx = 4; HasVAListArg = true; break;
+    case id_vsprintf:      format_idx = 1; HasVAListArg = true; break;
+    case id_vsprintf_chk:  format_idx = 3; HasVAListArg = true; break;
+    case id_vprintf:       format_idx = 0; HasVAListArg = true; break;
     }
     
     CheckPrintfArguments(TheCall.get(), HasVAListArg, format_idx);