================ @@ -0,0 +1,277 @@ +// RUN: %clang_cc1 -fsyntax-only -verify -Wmissing-format-attribute %s + +typedef unsigned short char16_t; +typedef unsigned int char32_t; +typedef __WCHAR_TYPE__ wchar_t; +typedef __SIZE_TYPE__ size_t; +typedef __builtin_va_list va_list; + +__attribute__((__format__(__printf__, 1, 2))) +int printf(const char *, ...); // #printf + +__attribute__((__format__(__scanf__, 1, 2))) +int scanf(const char *, ...); // #scanf + +__attribute__((__format__(__printf__, 1, 0))) +int vprintf(const char *, va_list); // #vprintf + +__attribute__((__format__(__scanf__, 1, 0))) +int vscanf(const char *, va_list); // #vscanf + +__attribute__((__format__(__printf__, 2, 0))) +int vsprintf(char *, const char *, va_list); // #vsprintf + +__attribute__((__format__(__printf__, 3, 0))) +int vsnprintf(char *ch, size_t, const char *, va_list); // #vsnprintf + +__attribute__((__format__(__scanf__, 1, 4))) +void f1(char *out, const size_t len, const char *format, ... /* args */) // #f1 +{ + va_list args; + vsnprintf(out, len, format, args); // expected-warning@#f1 {{diagnostic behavior may be improved by adding the 'printf' format attribute to the declaration of 'f1'}} + // CHECK-FIXES: __attribute__((format(printf, 3, 4))) +} + +__attribute__((__format__(__printf__, 1, 4))) +void f2(char *out, const size_t len, const char *format, ... /* args */) // #f2 +{ + va_list args; + vsnprintf(out, len, format, args); // expected-warning@#f2 {{diagnostic behavior may be improved by adding the 'printf' format attribute to the declaration of 'f2'}} + // CHECK-FIXES: __attribute__((format(printf, 3, 4))) +} + +void f3(char *out, va_list args) // #f3 +{ + vprintf(out, args); // expected-warning@#f3 {{diagnostic behavior may be improved by adding the 'printf' format attribute to the declaration of 'f3'}} + // CHECK-FIXES: __attribute__((format(printf, 1, 0))) + vscanf(out, args); // expected-warning@#f3 {{diagnostic behavior may be improved by adding the 'scanf' format attribute to the declaration of 'f3'}} + // CHECK-FIXES: __attribute__((format(scanf, 1, 0))) ---------------- AaronBallman wrote:
Oops, sorry that I missed your question! > My view of this comment is next: it refers to function which calls both > vprintf and vscanf format functions (let's call this function fn). Correct -- that's what I meant; a function that uses both printing and scanning functions. Concretely: ``` #include <stdio.h> void foo(const char *out, ...) { va_list args; va_start(args); vscanf(out, args); vprintf(out, args); va_end(args) } ``` there's no way for someone to call `foo("%d", ???)` that would work because the `???` would be of the wrong type for one of the formatted io calls, so I don't think such a function should have a suggestion to add both attributes (the way GCC does). https://github.com/llvm/llvm-project/pull/70024 _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits