diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h --- a/clang/include/clang/Sema/Sema.h +++ b/clang/include/clang/Sema/Sema.h @@ -13571,6 +13571,7 @@ bool CheckRISCVLMUL(CallExpr *TheCall, unsigned ArgNum); bool CheckRISCVBuiltinFunctionCall(const TargetInfo &TI, unsigned BuiltinID, CallExpr *TheCall); + void checkRVVTypeSupport(QualType Ty, SourceLocation Loc, ValueDecl *D); bool CheckLoongArchBuiltinFunctionCall(const TargetInfo &TI, unsigned BuiltinID, CallExpr *TheCall); bool CheckWebAssemblyBuiltinFunctionCall(const TargetInfo &TI, diff --git a/clang/lib/Sema/Sema.cpp b/clang/lib/Sema/Sema.cpp --- a/clang/lib/Sema/Sema.cpp +++ b/clang/lib/Sema/Sema.cpp @@ -2048,20 +2048,8 @@ targetDiag(D->getLocation(), diag::note_defined_here, FD) << D; } - // RISC-V vector builtin types (RISCVVTypes.def) - if (Ty->isRVVType(/* Bitwidth */ 64, /* IsFloat */ false) && - !TI.hasFeature("zve64x")) - Diag(Loc, diag::err_riscv_type_requires_extension, FD) << Ty << "zve64x"; - if (Ty->isRVVType(/* Bitwidth */ 16, /* IsFloat */ true) && - !TI.hasFeature("experimental-zvfh")) - Diag(Loc, diag::err_riscv_type_requires_extension, FD) - << Ty << "zvfh"; - if (Ty->isRVVType(/* Bitwidth */ 32, /* IsFloat */ true) && - !TI.hasFeature("zve32f")) - Diag(Loc, diag::err_riscv_type_requires_extension, FD) << Ty << "zve32f"; - if (Ty->isRVVType(/* Bitwidth */ 64, /* IsFloat */ true) && - !TI.hasFeature("zve64d")) - Diag(Loc, diag::err_riscv_type_requires_extension, FD) << Ty << "zve64d"; + if (Ty->isRVVType()) + checkRVVTypeSupport(Ty, Loc, D); // Don't allow SVE types in functions without a SVE target. if (Ty->isSVESizelessBuiltinType() && FD && FD->hasBody()) { diff --git a/clang/lib/Sema/SemaChecking.cpp b/clang/lib/Sema/SemaChecking.cpp --- a/clang/lib/Sema/SemaChecking.cpp +++ b/clang/lib/Sema/SemaChecking.cpp @@ -4967,6 +4967,26 @@ return false; } +void Sema::checkRVVTypeSupport(QualType Ty, SourceLocation Loc, ValueDecl *D) { + const TargetInfo &TI = Context.getTargetInfo(); + if (Ty->isRVVType(/* Bitwidth */ 64, /* IsFloat */ false) && + !TI.hasFeature("zve64x")) + Diag(Loc, diag::err_riscv_type_requires_extension, D) << Ty << "zve64x"; + if (Ty->isRVVType(/* Bitwidth */ 16, /* IsFloat */ true) && + !TI.hasFeature("experimental-zvfh")) + Diag(Loc, diag::err_riscv_type_requires_extension, D) << Ty << "zvfh"; + if (Ty->isRVVType(/* Bitwidth */ 32, /* IsFloat */ true) && + !TI.hasFeature("zve32f")) + Diag(Loc, diag::err_riscv_type_requires_extension, D) << Ty << "zve32f"; + if (Ty->isRVVType(/* Bitwidth */ 64, /* IsFloat */ true) && + !TI.hasFeature("zve64d")) + Diag(Loc, diag::err_riscv_type_requires_extension, D) << Ty << "zve64d"; + // Given that caller already checked isRVVType() before calling this function, + // if we don't have at least zve32x supported, then we need to emit error. + if (!TI.hasFeature("zve32x")) + Diag(Loc, diag::err_riscv_type_requires_extension, D) << Ty << "zve32x"; +} + bool Sema::CheckNVPTXBuiltinFunctionCall(const TargetInfo &TI, unsigned BuiltinID, CallExpr *TheCall) { diff --git a/clang/lib/Sema/SemaDecl.cpp b/clang/lib/Sema/SemaDecl.cpp --- a/clang/lib/Sema/SemaDecl.cpp +++ b/clang/lib/Sema/SemaDecl.cpp @@ -8782,6 +8782,9 @@ return; } } + + if (T->isRVVType()) + checkRVVTypeSupport(T, NewVD->getLocation(), cast(CurContext)); } /// Perform semantic checking on a newly-created variable diff --git a/clang/test/CodeGen/RISCV/rvv-intrinsics-handcrafted/rvv-intrinsic-datatypes.cpp b/clang/test/CodeGen/RISCV/rvv-intrinsics-handcrafted/rvv-intrinsic-datatypes.cpp --- a/clang/test/CodeGen/RISCV/rvv-intrinsics-handcrafted/rvv-intrinsic-datatypes.cpp +++ b/clang/test/CodeGen/RISCV/rvv-intrinsics-handcrafted/rvv-intrinsic-datatypes.cpp @@ -1,6 +1,7 @@ // NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --version 2 // REQUIRES: riscv-registered-target -// RUN: %clang_cc1 -triple riscv64 -target-feature +zve32x -O0 -emit-llvm %s -o - | FileCheck %s +// RUN: %clang_cc1 -triple riscv64 -target-feature +v -target-feature +experimental-zvfh \ +// RUN: -O0 -emit-llvm %s -o - | FileCheck %s #include diff --git a/clang/test/Sema/riscv-types.c b/clang/test/Sema/riscv-types.c --- a/clang/test/Sema/riscv-types.c +++ b/clang/test/Sema/riscv-types.c @@ -1,5 +1,5 @@ -// RUN: %clang_cc1 -triple riscv64 -target-feature +v -ast-print %s \ -// RUN: | FileCheck %s +// RUN: %clang_cc1 -triple riscv64 -target-feature +v \ +// RUN: -target-feature +experimental-zvfh -ast-print %s | FileCheck %s void bar(void) { // CHECK: __rvv_int64m1_t x0; diff --git a/clang/test/Sema/riscv-vector-float16-check.c b/clang/test/Sema/riscv-vector-float16-check.c --- a/clang/test/Sema/riscv-vector-float16-check.c +++ b/clang/test/Sema/riscv-vector-float16-check.c @@ -5,4 +5,17 @@ #include vfloat16m1_t foo() { /* expected-error {{RISC-V type 'vfloat16m1_t' (aka '__rvv_float16m1_t') requires the 'zvfh' extension}} */ -} /* expected-warning {{non-void function does not return a value}}*/ + vfloat16m1_t f16m1; /* expected-error {{RISC-V type 'vfloat16m1_t' (aka '__rvv_float16m1_t') requires the 'zvfh' extension}} */ + + (void)f16m1; /* expected-error {{RISC-V type 'vfloat16m1_t' (aka '__rvv_float16m1_t') requires the 'zvfh' extension}} */ + + return f16m1; /* expected-error {{RISC-V type 'vfloat16m1_t' (aka '__rvv_float16m1_t') requires the 'zvfh' extension}} */ +} + +vfloat16m1x2_t bar() { /* expected-error {{RISC-V type 'vfloat16m1x2_t' (aka '__rvv_float16m1x2_t') requires the 'zvfh' extension}} */ + vfloat16m1x2_t f16m1x2; /* expected-error {{RISC-V type 'vfloat16m1x2_t' (aka '__rvv_float16m1x2_t') requires the 'zvfh' extension}} */ + + (void)f16m1x2; /* expected-error {{RISC-V type 'vfloat16m1x2_t' (aka '__rvv_float16m1x2_t') requires the 'zvfh' extension}} */ + + return f16m1x2; /* expected-error {{RISC-V type 'vfloat16m1x2_t' (aka '__rvv_float16m1x2_t') requires the 'zvfh' extension}} */ +} diff --git a/clang/test/Sema/riscv-vector-float32-check.c b/clang/test/Sema/riscv-vector-float32-check.c --- a/clang/test/Sema/riscv-vector-float32-check.c +++ b/clang/test/Sema/riscv-vector-float32-check.c @@ -5,4 +5,17 @@ #include vfloat32m1_t foo() { /* expected-error {{RISC-V type 'vfloat32m1_t' (aka '__rvv_float32m1_t') requires the 'zve32f' extension}} */ -} /* expected-warning {{non-void function does not return a value}}*/ + vfloat32m1_t f32m1; /* expected-error {{RISC-V type 'vfloat32m1_t' (aka '__rvv_float32m1_t') requires the 'zve32f' extension}} */ + + (void)f32m1; /* expected-error {{RISC-V type 'vfloat32m1_t' (aka '__rvv_float32m1_t') requires the 'zve32f' extension}} */ + + return f32m1; /* expected-error {{RISC-V type 'vfloat32m1_t' (aka '__rvv_float32m1_t') requires the 'zve32f' extension}} */ +} + +vfloat32m1x2_t bar() { /* expected-error {{RISC-V type 'vfloat32m1x2_t' (aka '__rvv_float32m1x2_t') requires the 'zve32f' extension}} */ + vfloat32m1x2_t f32m1x2; /* expected-error {{RISC-V type 'vfloat32m1x2_t' (aka '__rvv_float32m1x2_t') requires the 'zve32f' extension}} */ + + (void)f32m1x2; /* expected-error {{RISC-V type 'vfloat32m1x2_t' (aka '__rvv_float32m1x2_t') requires the 'zve32f' extension}} */ + + return f32m1x2; /* expected-error {{RISC-V type 'vfloat32m1x2_t' (aka '__rvv_float32m1x2_t') requires the 'zve32f' extension}} */ +} diff --git a/clang/test/Sema/riscv-vector-float64-check.c b/clang/test/Sema/riscv-vector-float64-check.c --- a/clang/test/Sema/riscv-vector-float64-check.c +++ b/clang/test/Sema/riscv-vector-float64-check.c @@ -5,4 +5,17 @@ #include vfloat64m1_t foo() { /* expected-error {{RISC-V type 'vfloat64m1_t' (aka '__rvv_float64m1_t') requires the 'zve64d' extension}} */ -} /* expected-warning {{non-void function does not return a value}}*/ + vfloat64m1_t f64m1; /* expected-error {{RISC-V type 'vfloat64m1_t' (aka '__rvv_float64m1_t') requires the 'zve64d' extension}} */ + + (void)f64m1; /* expected-error {{RISC-V type 'vfloat64m1_t' (aka '__rvv_float64m1_t') requires the 'zve64d' extension}} */ + + return f64m1; /* expected-error {{RISC-V type 'vfloat64m1_t' (aka '__rvv_float64m1_t') requires the 'zve64d' extension}} */ +} + +vfloat64m1x2_t bar() { /* expected-error {{RISC-V type 'vfloat64m1x2_t' (aka '__rvv_float64m1x2_t') requires the 'zve64d' extension}} */ + vfloat64m1x2_t f64m1x2; /* expected-error {{RISC-V type 'vfloat64m1x2_t' (aka '__rvv_float64m1x2_t') requires the 'zve64d' extension}} */ + + (void)f64m1x2; /* expected-error {{RISC-V type 'vfloat64m1x2_t' (aka '__rvv_float64m1x2_t') requires the 'zve64d' extension}} */ + + return f64m1x2; /* expected-error {{RISC-V type 'vfloat64m1x2_t' (aka '__rvv_float64m1x2_t') requires the 'zve64d' extension}} */ +} diff --git a/clang/test/Sema/riscv-vector-int64-check.c b/clang/test/Sema/riscv-vector-int64-check.c --- a/clang/test/Sema/riscv-vector-int64-check.c +++ b/clang/test/Sema/riscv-vector-int64-check.c @@ -5,4 +5,17 @@ #include vint64m1_t foo() { /* expected-error {{RISC-V type 'vint64m1_t' (aka '__rvv_int64m1_t') requires the 'zve64x' extension}} */ -} /* expected-warning {{non-void function does not return a value}}*/ + vint64m1_t i64m1; /* expected-error {{RISC-V type 'vint64m1_t' (aka '__rvv_int64m1_t') requires the 'zve64x' extension}} */ + + (void)i64m1; /* expected-error {{RISC-V type 'vint64m1_t' (aka '__rvv_int64m1_t') requires the 'zve64x' extension}} */ + + return i64m1; /* expected-error {{RISC-V type 'vint64m1_t' (aka '__rvv_int64m1_t') requires the 'zve64x' extension}} */ +} + +vint64m1x2_t bar() { /* expected-error {{RISC-V type 'vint64m1x2_t' (aka '__rvv_int64m1x2_t') requires the 'zve64x' extension}} */ + vint64m1x2_t i64m1x2; /* expected-error {{RISC-V type 'vint64m1x2_t' (aka '__rvv_int64m1x2_t') requires the 'zve64x' extension}} */ + + (void)i64m1x2; /* expected-error {{RISC-V type 'vint64m1x2_t' (aka '__rvv_int64m1x2_t') requires the 'zve64x' extension}} */ + + return i64m1x2; /* expected-error {{RISC-V type 'vint64m1x2_t' (aka '__rvv_int64m1x2_t') requires the 'zve64x' extension}} */ +} diff --git a/clang/test/Sema/riscv-vector-zve32x-check.c b/clang/test/Sema/riscv-vector-zve32x-check.c new file mode 100644 --- /dev/null +++ b/clang/test/Sema/riscv-vector-zve32x-check.c @@ -0,0 +1,107 @@ +// RUN: %clang_cc1 -triple riscv64 \ +// RUN: -disable-O0-optnone -o - -fsyntax-only %s -verify +// REQUIRES: riscv-registered-target + +__rvv_int8m1_t foo8() { /* expected-error {{RISC-V type '__rvv_int8m1_t' requires the 'zve32x' extension}} */ + __rvv_int8m1_t i8m1; /* expected-error {{RISC-V type '__rvv_int8m1_t' requires the 'zve32x' extension}} */ + + (void)i8m1; /* expected-error {{RISC-V type '__rvv_int8m1_t' requires the 'zve32x' extension}} */ + + return i8m1; /* expected-error {{RISC-V type '__rvv_int8m1_t' requires the 'zve32x' extension}} */ +} + +__rvv_int16m1_t foo16() { /* expected-error {{RISC-V type '__rvv_int16m1_t' requires the 'zve32x' extension}} */ + __rvv_int16m1_t i16m1; /* expected-error {{RISC-V type '__rvv_int16m1_t' requires the 'zve32x' extension}} */ + + (void)i16m1; /* expected-error {{RISC-V type '__rvv_int16m1_t' requires the 'zve32x' extension}} */ + + return i16m1; /* expected-error {{RISC-V type '__rvv_int16m1_t' requires the 'zve32x' extension}} */ +} + +__rvv_int32m1_t foo32() { /* expected-error {{RISC-V type '__rvv_int32m1_t' requires the 'zve32x' extension}} */ + __rvv_int32m1_t i32m1; /* expected-error {{RISC-V type '__rvv_int32m1_t' requires the 'zve32x' extension}} */ + + (void)i32m1; /* expected-error {{RISC-V type '__rvv_int32m1_t' requires the 'zve32x' extension}} */ + + return i32m1; /* expected-error {{RISC-V type '__rvv_int32m1_t' requires the 'zve32x' extension}} */ +} + +__rvv_int8m1x2_t bar8() { /* expected-error {{RISC-V type '__rvv_int8m1x2_t' requires the 'zve32x' extension}} */ + __rvv_int8m1x2_t i8m1x2; /* expected-error {{RISC-V type '__rvv_int8m1x2_t' requires the 'zve32x' extension}} */ + + (void)i8m1x2; /* expected-error {{RISC-V type '__rvv_int8m1x2_t' requires the 'zve32x' extension}} */ + + return i8m1x2; /* expected-error {{RISC-V type '__rvv_int8m1x2_t' requires the 'zve32x' extension}} */ +} + +__rvv_int16m1x2_t bar16() { /* expected-error {{RISC-V type '__rvv_int16m1x2_t' requires the 'zve32x' extension}} */ + __rvv_int16m1x2_t i16m1x2; /* expected-error {{RISC-V type '__rvv_int16m1x2_t' requires the 'zve32x' extension}} */ + + (void)i16m1x2; /* expected-error {{RISC-V type '__rvv_int16m1x2_t' requires the 'zve32x' extension}} */ + + return i16m1x2; /* expected-error {{RISC-V type '__rvv_int16m1x2_t' requires the 'zve32x' extension}} */ +} + +__rvv_int32m1x2_t bar32() { /* expected-error {{RISC-V type '__rvv_int32m1x2_t' requires the 'zve32x' extension}} */ + __rvv_int32m1x2_t i32m1x2; /* expected-error {{RISC-V type '__rvv_int32m1x2_t' requires the 'zve32x' extension}} */ + + (void)i32m1x2; /* expected-error {{RISC-V type '__rvv_int32m1x2_t' requires the 'zve32x' extension}} */ + + return i32m1x2; /* expected-error {{RISC-V type '__rvv_int32m1x2_t' requires the 'zve32x' extension}} */ +} + +__rvv_bool1_t vbool1 () { /* expected-error {{RISC-V type '__rvv_bool1_t' requires the 'zve32x' extension}} */ + __rvv_bool1_t b1; /* expected-error {{RISC-V type '__rvv_bool1_t' requires the 'zve32x' extension}} */ + + (void)b1; /* expected-error {{RISC-V type '__rvv_bool1_t' requires the 'zve32x' extension}} */ + + return b1; /* expected-error {{RISC-V type '__rvv_bool1_t' requires the 'zve32x' extension}} */ +} + +__rvv_bool2_t vbool2 () { /* expected-error {{RISC-V type '__rvv_bool2_t' requires the 'zve32x' extension}} */ + __rvv_bool2_t b2; /* expected-error {{RISC-V type '__rvv_bool2_t' requires the 'zve32x' extension}} */ + + (void)b2; /* expected-error {{RISC-V type '__rvv_bool2_t' requires the 'zve32x' extension}} */ + + return b2; /* expected-error {{RISC-V type '__rvv_bool2_t' requires the 'zve32x' extension}} */ +} + +__rvv_bool4_t vbool4 () { /* expected-error {{RISC-V type '__rvv_bool4_t' requires the 'zve32x' extension}} */ + __rvv_bool4_t b4; /* expected-error {{RISC-V type '__rvv_bool4_t' requires the 'zve32x' extension}} */ + + (void)b4; /* expected-error {{RISC-V type '__rvv_bool4_t' requires the 'zve32x' extension}} */ + + return b4; /* expected-error {{RISC-V type '__rvv_bool4_t' requires the 'zve32x' extension}} */ +} + +__rvv_bool8_t vbool8 () { /* expected-error {{RISC-V type '__rvv_bool8_t' requires the 'zve32x' extension}} */ + __rvv_bool8_t b8; /* expected-error {{RISC-V type '__rvv_bool8_t' requires the 'zve32x' extension}} */ + + (void)b8; /* expected-error {{RISC-V type '__rvv_bool8_t' requires the 'zve32x' extension}} */ + + return b8; /* expected-error {{RISC-V type '__rvv_bool8_t' requires the 'zve32x' extension}} */ +} + +__rvv_bool16_t vbool16 () { /* expected-error {{RISC-V type '__rvv_bool16_t' requires the 'zve32x' extension}} */ + __rvv_bool16_t b16; /* expected-error {{RISC-V type '__rvv_bool16_t' requires the 'zve32x' extension}} */ + + (void)b16; /* expected-error {{RISC-V type '__rvv_bool16_t' requires the 'zve32x' extension}} */ + + return b16; /* expected-error {{RISC-V type '__rvv_bool16_t' requires the 'zve32x' extension}} */ +} + +__rvv_bool32_t vbool32 () { /* expected-error {{RISC-V type '__rvv_bool32_t' requires the 'zve32x' extension}} */ + __rvv_bool32_t b32; /* expected-error {{RISC-V type '__rvv_bool32_t' requires the 'zve32x' extension}} */ + + (void)b32; /* expected-error {{RISC-V type '__rvv_bool32_t' requires the 'zve32x' extension}} */ + + return b32; /* expected-error {{RISC-V type '__rvv_bool32_t' requires the 'zve32x' extension}} */ +} + +__rvv_bool64_t vbool64 () { /* expected-error {{RISC-V type '__rvv_bool64_t' requires the 'zve32x' extension}} */ + __rvv_bool64_t b64; /* expected-error {{RISC-V type '__rvv_bool64_t' requires the 'zve32x' extension}} */ + + (void)b64; /* expected-error {{RISC-V type '__rvv_bool64_t' requires the 'zve32x' extension}} */ + + return b64; /* expected-error {{RISC-V type '__rvv_bool64_t' requires the 'zve32x' extension}} */ +}