OpenCL: Use length modifier for warning on vector printf arguments

Re-enable format string warnings on printf.

The warnings are still incomplete. Apparently it is undefined to use a
vector specifier without a length modifier, which is not currently
warned on. Additionally, type warnings appear to not be working with
the hh modifier, and aren't warning on all of the special restrictions
from c99 printf.

llvm-svn: 352540
This commit is contained in:
Matt Arsenault 2019-01-29 20:49:54 +00:00
parent 297afb14ec
commit 58fc8082a8
10 changed files with 246 additions and 34 deletions

View File

@ -67,6 +67,7 @@ public:
None,
AsChar, // 'hh'
AsShort, // 'h'
AsShortLong, // 'hl' (OpenCL float/int vector element)
AsLong, // 'l'
AsLongLong, // 'll'
AsQuad, // 'q' (BSD, deprecated, for 64-bit integer types)
@ -436,7 +437,8 @@ public:
bool usesPositionalArg() const { return UsesPositionalArg; }
bool hasValidLengthModifier(const TargetInfo &Target) const;
bool hasValidLengthModifier(const TargetInfo &Target,
const LangOptions &LO) const;
bool hasStandardLengthModifier() const;

View File

@ -223,6 +223,9 @@ clang::analyze_format_string::ParseLengthModifier(FormatSpecifier &FS,
if (I != E && *I == 'h') {
++I;
lmKind = LengthModifier::AsChar;
} else if (I != E && *I == 'l' && LO.OpenCL) {
++I;
lmKind = LengthModifier::AsShortLong;
} else {
lmKind = LengthModifier::AsShort;
}
@ -487,7 +490,8 @@ ArgType::matchesType(ASTContext &C, QualType argTy) const {
}
ArgType ArgType::makeVectorType(ASTContext &C, unsigned NumElts) const {
if (K != SpecificTy) // Won't be a valid vector element type.
// Check for valid vector element types.
if (T.isNull())
return ArgType::Invalid();
QualType Vec = C.getExtVectorType(T, NumElts);
@ -572,6 +576,8 @@ analyze_format_string::LengthModifier::toString() const {
return "hh";
case AsShort:
return "h";
case AsShortLong:
return "hl";
case AsLong: // or AsWideChar
return "l";
case AsLongLong:
@ -707,13 +713,18 @@ void OptionalAmount::toString(raw_ostream &os) const {
}
}
bool FormatSpecifier::hasValidLengthModifier(const TargetInfo &Target) const {
bool FormatSpecifier::hasValidLengthModifier(const TargetInfo &Target,
const LangOptions &LO) const {
switch (LM.getKind()) {
case LengthModifier::None:
return true;
// Handle most integer flags
case LengthModifier::AsShort:
// Length modifier only applies to FP vectors.
if (LO.OpenCL && CS.isDoubleArg())
return !VectorNumElts.isInvalid();
if (Target.getTriple().isOSMSVCRT()) {
switch (CS.getKind()) {
case ConversionSpecifier::cArg:
@ -752,8 +763,18 @@ bool FormatSpecifier::hasValidLengthModifier(const TargetInfo &Target) const {
return false;
}
case LengthModifier::AsShortLong:
return LO.OpenCL && !VectorNumElts.isInvalid();
// Handle 'l' flag
case LengthModifier::AsLong: // or AsWideChar
if (CS.isDoubleArg()) {
// Invalid for OpenCL FP scalars.
if (LO.OpenCL && VectorNumElts.isInvalid())
return false;
return true;
}
switch (CS.getKind()) {
case ConversionSpecifier::dArg:
case ConversionSpecifier::DArg:
@ -764,14 +785,6 @@ bool FormatSpecifier::hasValidLengthModifier(const TargetInfo &Target) const {
case ConversionSpecifier::UArg:
case ConversionSpecifier::xArg:
case ConversionSpecifier::XArg:
case ConversionSpecifier::aArg:
case ConversionSpecifier::AArg:
case ConversionSpecifier::fArg:
case ConversionSpecifier::FArg:
case ConversionSpecifier::eArg:
case ConversionSpecifier::EArg:
case ConversionSpecifier::gArg:
case ConversionSpecifier::GArg:
case ConversionSpecifier::nArg:
case ConversionSpecifier::cArg:
case ConversionSpecifier::sArg:
@ -878,6 +891,7 @@ bool FormatSpecifier::hasStandardLengthModifier() const {
case LengthModifier::AsInt3264:
case LengthModifier::AsInt64:
case LengthModifier::AsWide:
case LengthModifier::AsShortLong: // ???
return false;
}
llvm_unreachable("Invalid LengthModifier Kind!");

View File

@ -315,7 +315,11 @@ static PrintfSpecifierResult ParsePrintfSpecifier(FormatStringHandler &H,
case 'f': k = ConversionSpecifier::fArg; break;
case 'g': k = ConversionSpecifier::gArg; break;
case 'i': k = ConversionSpecifier::iArg; break;
case 'n': k = ConversionSpecifier::nArg; break;
case 'n':
// Not handled, but reserved in OpenCL.
if (!LO.OpenCL)
k = ConversionSpecifier::nArg;
break;
case 'o': k = ConversionSpecifier::oArg; break;
case 'p': k = ConversionSpecifier::pArg; break;
case 's': k = ConversionSpecifier::sArg; break;
@ -486,10 +490,12 @@ ArgType PrintfSpecifier::getScalarArgType(ASTContext &Ctx,
// GNU extension.
return Ctx.LongLongTy;
case LengthModifier::None:
case LengthModifier::AsShortLong:
return Ctx.IntTy;
case LengthModifier::AsInt32:
return ArgType(Ctx.IntTy, "__int32");
case LengthModifier::AsChar: return ArgType::AnyCharTy;
case LengthModifier::AsChar:
return ArgType::AnyCharTy;
case LengthModifier::AsShort: return Ctx.ShortTy;
case LengthModifier::AsLong: return Ctx.LongTy;
case LengthModifier::AsLongLong:
@ -520,6 +526,7 @@ ArgType PrintfSpecifier::getScalarArgType(ASTContext &Ctx,
// GNU extension.
return Ctx.UnsignedLongLongTy;
case LengthModifier::None:
case LengthModifier::AsShortLong:
return Ctx.UnsignedIntTy;
case LengthModifier::AsInt32:
return ArgType(Ctx.UnsignedIntTy, "unsigned __int32");
@ -549,6 +556,18 @@ ArgType PrintfSpecifier::getScalarArgType(ASTContext &Ctx,
}
if (CS.isDoubleArg()) {
if (!VectorNumElts.isInvalid()) {
switch (LM.getKind()) {
case LengthModifier::AsShort:
return Ctx.HalfTy;
case LengthModifier::AsShortLong:
return Ctx.FloatTy;
case LengthModifier::AsLong:
default:
return Ctx.DoubleTy;
}
}
if (LM.getKind() == LengthModifier::AsLongDouble)
return Ctx.LongDoubleTy;
return Ctx.DoubleTy;
@ -582,6 +601,8 @@ ArgType PrintfSpecifier::getScalarArgType(ASTContext &Ctx,
case LengthModifier::AsInt64:
case LengthModifier::AsWide:
return ArgType::Invalid();
case LengthModifier::AsShortLong:
llvm_unreachable("only used for OpenCL which doesn not handle nArg");
}
}
@ -760,10 +781,13 @@ bool PrintfSpecifier::fixType(QualType QT, const LangOptions &LangOpt,
case BuiltinType::UInt:
case BuiltinType::Int:
case BuiltinType::Float:
case BuiltinType::Double:
LM.setKind(LengthModifier::None);
LM.setKind(VectorNumElts.isInvalid() ?
LengthModifier::None : LengthModifier::AsShortLong);
break;
case BuiltinType::Double:
LM.setKind(VectorNumElts.isInvalid() ?
LengthModifier::None : LengthModifier::AsLong);
break;
case BuiltinType::Char_U:
case BuiltinType::UChar:
case BuiltinType::Char_S:
@ -796,7 +820,7 @@ bool PrintfSpecifier::fixType(QualType QT, const LangOptions &LangOpt,
namedTypeToLengthModifier(QT, LM);
// If fixing the length modifier was enough, we might be done.
if (hasValidLengthModifier(Ctx.getTargetInfo())) {
if (hasValidLengthModifier(Ctx.getTargetInfo(), LangOpt)) {
// If we're going to offer a fix anyway, make sure the sign matches.
switch (CS.getKind()) {
case ConversionSpecifier::uArg:

View File

@ -261,9 +261,10 @@ ArgType ScanfSpecifier::getArgType(ASTContext &Ctx) const {
case LengthModifier::AsInt32:
case LengthModifier::AsInt3264:
case LengthModifier::AsWide:
case LengthModifier::AsShortLong:
return ArgType::Invalid();
}
llvm_unreachable("Unsupported LenghtModifier Type");
llvm_unreachable("Unsupported LengthModifier Type");
// Unsigned int.
case ConversionSpecifier::oArg:
@ -301,9 +302,10 @@ ArgType ScanfSpecifier::getArgType(ASTContext &Ctx) const {
case LengthModifier::AsInt32:
case LengthModifier::AsInt3264:
case LengthModifier::AsWide:
case LengthModifier::AsShortLong:
return ArgType::Invalid();
}
llvm_unreachable("Unsupported LenghtModifier Type");
llvm_unreachable("Unsupported LengthModifier Type");
// Float.
case ConversionSpecifier::aArg:
@ -396,6 +398,7 @@ ArgType ScanfSpecifier::getArgType(ASTContext &Ctx) const {
case LengthModifier::AsInt32:
case LengthModifier::AsInt3264:
case LengthModifier::AsWide:
case LengthModifier::AsShortLong:
return ArgType::Invalid();
}
@ -501,7 +504,7 @@ bool ScanfSpecifier::fixType(QualType QT, QualType RawQT,
namedTypeToLengthModifier(PT, LM);
// If fixing the length modifier was enough, we are done.
if (hasValidLengthModifier(Ctx.getTargetInfo())) {
if (hasValidLengthModifier(Ctx.getTargetInfo(), LangOpt)) {
const analyze_scanf::ArgType &AT = getArgType(Ctx);
if (AT.isValid() && AT.matchesType(Ctx, QT))
return true;

View File

@ -14469,7 +14469,7 @@ half16 __ovld __cnfn shuffle2(half16 x, half16 y, ushort16 mask);
#if __OPENCL_C_VERSION__ >= CL_VERSION_1_2
// OpenCL v1.2 s6.12.13, v2.0 s6.13.13 - printf
int printf(__constant const char* st, ...);
int printf(__constant const char* st, ...) __attribute__((format(printf, 1, 2)));
#endif
// OpenCL v1.1 s6.11.3, v1.2 s6.12.14, v2.0 s6.13.14 - Image Read and Write Functions

View File

@ -7650,7 +7650,8 @@ CheckPrintfHandler::HandlePrintfSpecifier(const analyze_printf::PrintfSpecifier
startSpecifier, specifierLen);
// Check the length modifier is valid with the given conversion specifier.
if (!FS.hasValidLengthModifier(S.getASTContext().getTargetInfo()))
if (!FS.hasValidLengthModifier(S.getASTContext().getTargetInfo(),
S.getLangOpts()))
HandleInvalidLengthModifier(FS, CS, startSpecifier, specifierLen,
diag::warn_format_nonsensical_length);
else if (!FS.hasStandardLengthModifier())
@ -8154,7 +8155,8 @@ bool CheckScanfHandler::HandleScanfSpecifier(
}
// Check the length modifier is valid with the given conversion specifier.
if (!FS.hasValidLengthModifier(S.getASTContext().getTargetInfo()))
if (!FS.hasValidLengthModifier(S.getASTContext().getTargetInfo(),
S.getLangOpts()))
HandleInvalidLengthModifier(FS, CS, startSpecifier, specifierLen,
diag::warn_format_nonsensical_length);
else if (!FS.hasStandardLengthModifier())

View File

@ -617,6 +617,8 @@ void test_opencl_vector_format(int x) {
printf("%v4d", x); // expected-warning{{invalid conversion specifier 'v'}}
printf("%vd", x); // expected-warning{{invalid conversion specifier 'v'}}
printf("%0vd", x); // expected-warning{{invalid conversion specifier 'v'}}
printf("%hlf", x); // expected-warning{{invalid conversion specifier 'l'}}
printf("%hld", x); // expected-warning{{invalid conversion specifier 'l'}}
}
// Test that we correctly merge the format in both orders.

View File

@ -3,22 +3,72 @@
// RUN: %clang_cc1 -cl-std=CL1.2 -fsyntax-only -pedantic -Wall -Werror %t
// RUN: %clang_cc1 -cl-std=CL1.2 -E -o - %t | FileCheck %s
typedef __attribute__((ext_vector_type(4))) char char4;
typedef __attribute__((ext_vector_type(4))) short short4;
typedef __attribute__((ext_vector_type(4))) int int4;
typedef __attribute__((ext_vector_type(4))) unsigned int uint4;
typedef __attribute__((ext_vector_type(8))) int int8;
typedef __attribute__((ext_vector_type(4))) long long4;
typedef __attribute__((ext_vector_type(4))) float float4;
typedef __attribute__((ext_vector_type(4))) double double4;
int printf(__constant const char* st, ...) __attribute__((format(printf, 1, 2)));
void vector_fixits() {
printf("%v4f", (int4) 123);
// CHECK: printf("%v4d", (int4) 123);
// CHECK: printf("%v4hld", (int4) 123);
printf("%v8d", (int4) 123);
// CHECK: printf("%v4d", (int4) 123);
// CHECK: printf("%v4hld", (int4) 123);
printf("%v4d", (int8) 123);
// CHECK: printf("%v8d", (int8) 123);
// CHECK: printf("%v8hld", (int8) 123);
printf("%v4f", (int8) 123);
// CHECK: printf("%v8d", (int8) 123);
// CHECK: printf("%v8hld", (int8) 123);
printf("%v4ld", (int8) 123);
// CHECK: printf("%v8hld", (int8) 123);
printf("%v4hlf", (int4) 123);
// CHECK: printf("%v4hld", (int4) 123);
printf("%v8hld", (int4) 123);
// CHECK: printf("%v4hld", (int4) 123);
printf("%v4hld", (int8) 123);
// CHECK: printf("%v8hld", (int8) 123);
printf("%v4hlf", (int8) 123);
// CHECK: printf("%v8hld", (int8) 123);
printf("%v4hd", (int4) 123);
// CHECK: printf("%v4hld", (int4) 123);
printf("%v4hld", (short4) 123);
// CHECK: printf("%v4hd", (short4) 123);
printf("%v4ld", (short4) 123);
// CHECK: printf("%v4hd", (short4) 123);
printf("%v4hld", (long4) 123);
// CHECK: printf("%v4ld", (long4) 123);
printf("%v8f", (float4) 2.0f);
// CHECK: printf("%v4hlf", (float4) 2.0f);
printf("%v4f", (float4) 2.0f);
// CHECK: printf("%v4hlf", (float4) 2.0f);
printf("%v4lf", (double4) 2.0);
// CHECK: printf("%v4lf", (double4) 2.0);
/// FIXME: This should be fixed
printf("%v4hhd", (int4) 123);
// CHECK: printf("%v4hhd", (int4) 123);
/// FIXME: This should be fixed
printf("%v4hhd", (int8) 123);
// CHECK: printf("%v4hhd", (int8) 123);
}

View File

@ -1,14 +1,12 @@
// RUN: %clang_cc1 %s -verify -pedantic -fsyntax-only -cl-std=CL2.0 -finclude-default-header
// FIXME: Make sure warnings are produced based on printf format strings.
// expected-no-diagnostics
// Make sure warnings are produced based on printf format strings.
kernel void format_string_warnings(__constant char* arg) {
printf("%d", arg);
printf("%d", arg); // expected-warning {{format specifies type 'int' but the argument has type '__constant char *'}}
printf("not enough arguments %d %d", 4);
printf("not enough arguments %d %d", 4); // expected-warning {{more '%' conversions than data arguments}}
printf("too many arguments", 4);
printf("too many arguments", 4); // expected-warning {{data argument not used by format string}}
}

View File

@ -1,22 +1,90 @@
// RUN: %clang_cc1 -cl-std=CL1.2 -cl-ext=+cl_khr_fp64 -fsyntax-only -verify %s
// RUN: %clang_cc1 -cl-std=CL1.2 -cl-ext=-cl_khr_fp64 -fsyntax-only -verify %s
typedef __attribute__((ext_vector_type(4))) half half4;
typedef __attribute__((ext_vector_type(2))) float float2;
typedef __attribute__((ext_vector_type(4))) float float4;
#ifdef cl_khr_fp64
typedef __attribute__((ext_vector_type(4))) double double4;
#endif
typedef __attribute__((ext_vector_type(4))) char char4;
typedef __attribute__((ext_vector_type(4))) unsigned char uchar4;
typedef __attribute__((ext_vector_type(4))) short short4;
typedef __attribute__((ext_vector_type(4))) unsigned short ushort4;
typedef __attribute__((ext_vector_type(2))) int int2;
typedef __attribute__((ext_vector_type(4))) int int4;
typedef __attribute__((ext_vector_type(16))) int int16;
typedef __attribute__((ext_vector_type(4))) long long4;
typedef __attribute__((ext_vector_type(4))) unsigned int uint4;
typedef __attribute__((ext_vector_type(4))) unsigned long ulong4;
int printf(__constant const char* st, ...) __attribute__((format(printf, 1, 2)));
#ifdef cl_khr_fp64
kernel void format_v4f64(half4 arg_h, float4 arg_f, double4 arg_d)
{
printf("%v4lf", arg_d);
printf("%v4lf", arg_f); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
printf("%v4lf", arg_h); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'half4' (vector of 4 'half' values)}}
printf("%v4lF", arg_d);
printf("%v4lF", arg_f); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
printf("%v4lF", arg_h); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'half4' (vector of 4 'half' values)}}
printf("%v4le", arg_d);
printf("%v4le", arg_f); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
printf("%v4le", arg_h); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'half4' (vector of 4 'half' values)}}
printf("%v4lE", arg_d);
printf("%v4lE", arg_f); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
printf("%v4lE", arg_h); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'half4' (vector of 4 'half' values)}}
printf("%v4lg", arg_d);
printf("%v4lg", arg_f); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
printf("%v4lg", arg_h); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'half4' (vector of 4 'half' values)}}
printf("%v4lG", arg_d);
printf("%v4lG", arg_f); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
printf("%v4lG", arg_h); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'half4' (vector of 4 'half' values)}}
printf("%v4la", arg_d);
printf("%v4la", arg_f); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
printf("%v4la", arg_h); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'half4' (vector of 4 'half' values)}}
printf("%v4lA", arg_d);
printf("%v4lA", arg_f); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
printf("%v4lA", arg_h); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'half4' (vector of 4 'half' values)}}
}
kernel void format_v4f16(half4 arg_h, float4 arg_f, double4 arg_d)
{
printf("%v4hf\n", arg_d); // expected-warning{{format specifies type '__fp16 __attribute__((ext_vector_type(4)))' but the argument has type 'double4' (vector of 4 'double' values)}}
printf("%v4hf\n", arg_f); // expected-warning{{format specifies type '__fp16 __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
printf("%v4hf\n", arg_h);
}
kernel void no_length_modifier_scalar_fp(float f) {
printf("%hf", f); // expected-warning{{length modifier 'h' results in undefined behavior or no effect with 'f' conversion specifier}}
printf("%hlf", f); // expected-warning{{length modifier 'hl' results in undefined behavior or no effect with 'f' conversion specifier}}
printf("%lf", f); // expected-warning{{length modifier 'l' results in undefined behavior or no effect with 'f' conversion specifier}}
}
#endif
kernel void format_v4f32(float4 arg)
{
#ifdef cl_khr_fp64
printf("%v4f\n", arg); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
// Precision modifier
printf("%.2v4f\n", arg); // expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
printf("%.2v4f\n", arg); //expected-warning{{format specifies type 'double __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
#else
// FIXME: These should not warn, and the type should be expected to be float.
printf("%v4f\n", arg); // expected-warning {{double __attribute__((ext_vector_type(4)))' but the argument has type 'float4' (vector of 4 'float' values)}}
@ -92,3 +160,52 @@ kernel void crash_on_s(int4 arg)
{
printf("%v4s\n", arg);
}
kernel void printf_int_length_modifiers(char4 arg_c, short4 arg_s, int4 arg_i, long4 arg_l, uchar4 arg_uc, ushort4 arg_us, uint4 arg_ui, ulong4 arg_ul) {
printf("%v4hhd", arg_c);
printf("%v4hhd", arg_s);
printf("%v4hhd", arg_i);
printf("%v4hhd", arg_l);
printf("%v4hd", arg_c); // expected-warning{{format specifies type 'short __attribute__((ext_vector_type(4)))' but the argument has type 'char4' (vector of 4 'char' values)}}
printf("%v4hd", arg_s);
printf("%v4hd", arg_i); // expected-warning{{format specifies type 'short __attribute__((ext_vector_type(4)))' but the argument has type 'int4' (vector of 4 'int' values)}}
printf("%v4hd", arg_l); // expected-warning{{format specifies type 'short __attribute__((ext_vector_type(4)))' but the argument has type 'long4' (vector of 4 'long' values)}}
printf("%v4hld", arg_c); // expected-warning{{format specifies type 'int __attribute__((ext_vector_type(4)))' but the argument has type 'char4' (vector of 4 'char' values)}}
printf("%v4hld", arg_s); // expected-warning{{format specifies type 'int __attribute__((ext_vector_type(4)))' but the argument has type 'short4' (vector of 4 'short' values)}}
printf("%v4hld", arg_i);
printf("%v4hld", arg_l); // expected-warning{{format specifies type 'int __attribute__((ext_vector_type(4)))' but the argument has type 'long4' (vector of 4 'long' values)}}
printf("%v4ld", arg_c); // expected-warning{{format specifies type 'long __attribute__((ext_vector_type(4)))' but the argument has type 'char4' (vector of 4 'char' values)}}
printf("%v4ld", arg_s); // expected-warning{{format specifies type 'long __attribute__((ext_vector_type(4)))' but the argument has type 'short4' (vector of 4 'short' values)}}
printf("%v4ld", arg_i); // expected-warning{{format specifies type 'long __attribute__((ext_vector_type(4)))' but the argument has type 'int4' (vector of 4 'int' values)}}
printf("%v4ld", arg_l);
printf("%v4hhu", arg_uc);
printf("%v4hhu", arg_us); // expected-warning{{format specifies type 'unsigned char __attribute__((ext_vector_type(4)))' but the argument has type 'ushort4' (vector of 4 'unsigned short' values)}}
printf("%v4hhu", arg_ui); // expected-warning{{format specifies type 'unsigned char __attribute__((ext_vector_type(4)))' but the argument has type 'uint4' (vector of 4 'unsigned int' values)}}
printf("%v4hhu", arg_ul); // expected-warning{{format specifies type 'unsigned char __attribute__((ext_vector_type(4)))' but the argument has type 'ulong4' (vector of 4 'unsigned long' values)}}
printf("%v4hu", arg_uc); // expected-warning{{format specifies type 'unsigned short __attribute__((ext_vector_type(4)))' but the argument has type 'uchar4' (vector of 4 'unsigned char' values)}}
printf("%v4hu", arg_us);
printf("%v4hu", arg_ui); // expected-warning{{format specifies type 'unsigned short __attribute__((ext_vector_type(4)))' but the argument has type 'uint4' (vector of 4 'unsigned int' values)}}
printf("%v4hu", arg_ul); // expected-warning{{format specifies type 'unsigned short __attribute__((ext_vector_type(4)))' but the argument has type 'ulong4' (vector of 4 'unsigned long' values)}}
printf("%v4hlu", arg_uc); // expected-warning{{format specifies type 'unsigned int __attribute__((ext_vector_type(4)))' but the argument has type 'uchar4' (vector of 4 'unsigned char' values)}}
printf("%v4hlu", arg_us); // expected-warning{{format specifies type 'unsigned int __attribute__((ext_vector_type(4)))' but the argument has type 'ushort4' (vector of 4 'unsigned short' values)}}
printf("%v4hlu", arg_ui);
printf("%v4hlu", arg_ul); // expected-warning{{format specifies type 'unsigned int __attribute__((ext_vector_type(4)))' but the argument has type 'ulong4' (vector of 4 'unsigned long' values)}}
printf("%v4lu", arg_uc); // expected-warning{{format specifies type 'unsigned long __attribute__((ext_vector_type(4)))' but the argument has type 'uchar4' (vector of 4 'unsigned char' values)}}
printf("%v4lu", arg_us); // expected-warning{{format specifies type 'unsigned long __attribute__((ext_vector_type(4)))' but the argument has type 'ushort4' (vector of 4 'unsigned short' values)}}
printf("%v4lu", arg_ui); // expected-warning{{format specifies type 'unsigned long __attribute__((ext_vector_type(4)))' but the argument has type 'uint4' (vector of 4 'unsigned int' values)}}
printf("%v4lu", arg_ul);
printf("%v4n", &arg_i); // expected-warning{{invalid conversion specifier 'n'}}
printf("%v4hln", &arg_i); // expected-warning{{invalid conversion specifier 'n'}}
}