From 94489f35a7f8e16d7fd553ddf96023cb78a2afbb Mon Sep 17 00:00:00 2001 From: Richard Sandiford Date: Thu, 27 Feb 2020 10:41:42 +0000 Subject: [PATCH] [Sema][SVE] Reject arithmetic on pointers to sizeless types This patch completes a trio of changes related to arrays of sizeless types. It rejects various forms of arithmetic on pointers to sizeless types, in the same way as for other incomplete types. Differential Revision: https://reviews.llvm.org/D76086 --- clang/include/clang/Basic/DiagnosticSemaKinds.td | 4 ++-- clang/lib/Sema/SemaExpr.cpp | 7 ++++--- clang/test/Sema/sizeless-1.c | 12 ++++++++++++ clang/test/SemaCXX/sizeless-1.cpp | 12 ++++++++++++ 4 files changed, 30 insertions(+), 5 deletions(-) diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td index 4c057ba..1d32bc5 100644 --- a/clang/include/clang/Basic/DiagnosticSemaKinds.td +++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td @@ -6237,8 +6237,8 @@ def err_typecheck_illegal_increment_decrement : Error< "cannot %select{decrement|increment}1 value of type %0">; def err_typecheck_expect_int : Error< "used type %0 where integer is required">; -def err_typecheck_arithmetic_incomplete_type : Error< - "arithmetic on a pointer to an incomplete type %0">; +def err_typecheck_arithmetic_incomplete_or_sizeless_type : Error< + "arithmetic on a pointer to %select{an incomplete|sizeless}0 type %1">; def err_typecheck_pointer_arith_function_type : Error< "arithmetic on%select{ a|}0 pointer%select{|s}0 to%select{ the|}2 " "function type%select{|s}2 %1%select{| and %3}2">; diff --git a/clang/lib/Sema/SemaExpr.cpp b/clang/lib/Sema/SemaExpr.cpp index a3ac743..c1bfb96 100644 --- a/clang/lib/Sema/SemaExpr.cpp +++ b/clang/lib/Sema/SemaExpr.cpp @@ -9534,9 +9534,10 @@ static bool checkArithmeticIncompletePointerType(Sema &S, SourceLocation Loc, assert(ResType->isAnyPointerType() && !ResType->isDependentType()); QualType PointeeTy = ResType->getPointeeType(); - return S.RequireCompleteType(Loc, PointeeTy, - diag::err_typecheck_arithmetic_incomplete_type, - PointeeTy, Operand->getSourceRange()); + return S.RequireCompleteSizedType( + Loc, PointeeTy, + diag::err_typecheck_arithmetic_incomplete_or_sizeless_type, + Operand->getSourceRange()); } /// Check the validity of an arithmetic pointer operand. diff --git a/clang/test/Sema/sizeless-1.c b/clang/test/Sema/sizeless-1.c index 70f9fb7..c823823 100644 --- a/clang/test/Sema/sizeless-1.c +++ b/clang/test/Sema/sizeless-1.c @@ -137,6 +137,8 @@ void func(int sel) { dump(&volatile_int8); dump(&const_volatile_int8); + dump(&local_int8 + 1); // expected-error {{arithmetic on a pointer to sizeless type}} + *&local_int8 = local_int8; *&const_int8 = local_int8; // expected-error {{read-only variable is not assignable}} *&volatile_int8 = local_int8; @@ -158,6 +160,16 @@ void func(int sel) { noproto(local_int8); varargs(1, local_int8, local_int16); + global_int8_ptr++; // expected-error {{arithmetic on a pointer to sizeless type}} + global_int8_ptr--; // expected-error {{arithmetic on a pointer to sizeless type}} + ++global_int8_ptr; // expected-error {{arithmetic on a pointer to sizeless type}} + --global_int8_ptr; // expected-error {{arithmetic on a pointer to sizeless type}} + global_int8_ptr + 1; // expected-error {{arithmetic on a pointer to sizeless type}} + global_int8_ptr - 1; // expected-error {{arithmetic on a pointer to sizeless type}} + global_int8_ptr += 1; // expected-error {{arithmetic on a pointer to sizeless type}} + global_int8_ptr -= 1; // expected-error {{arithmetic on a pointer to sizeless type}} + global_int8_ptr - global_int8_ptr; // expected-error {{arithmetic on a pointer to sizeless type}} + +init_int8; // expected-error {{invalid argument type 'svint8_t'}} ++init_int8; // expected-error {{cannot increment value of type 'svint8_t'}} init_int8++; // expected-error {{cannot increment value of type 'svint8_t'}} diff --git a/clang/test/SemaCXX/sizeless-1.cpp b/clang/test/SemaCXX/sizeless-1.cpp index 4c56784..b13b862 100644 --- a/clang/test/SemaCXX/sizeless-1.cpp +++ b/clang/test/SemaCXX/sizeless-1.cpp @@ -158,6 +158,8 @@ void func(int sel) { dump(&volatile_int8); dump(&const_volatile_int8); + dump(&local_int8 + 1); // expected-error {{arithmetic on a pointer to sizeless type}} + *&local_int8 = local_int8; *&const_int8 = local_int8; // expected-error {{read-only variable is not assignable}} *&volatile_int8 = local_int8; @@ -178,6 +180,16 @@ void func(int sel) { varargs(1, local_int8, local_int16); + global_int8_ptr++; // expected-error {{arithmetic on a pointer to sizeless type}} + global_int8_ptr--; // expected-error {{arithmetic on a pointer to sizeless type}} + ++global_int8_ptr; // expected-error {{arithmetic on a pointer to sizeless type}} + --global_int8_ptr; // expected-error {{arithmetic on a pointer to sizeless type}} + global_int8_ptr + 1; // expected-error {{arithmetic on a pointer to sizeless type}} + global_int8_ptr - 1; // expected-error {{arithmetic on a pointer to sizeless type}} + global_int8_ptr += 1; // expected-error {{arithmetic on a pointer to sizeless type}} + global_int8_ptr -= 1; // expected-error {{arithmetic on a pointer to sizeless type}} + global_int8_ptr - global_int8_ptr; // expected-error {{arithmetic on a pointer to sizeless type}} + +init_int8; // expected-error {{invalid argument type 'svint8_t'}} ++init_int8; // expected-error {{cannot increment value of type 'svint8_t'}} init_int8++; // expected-error {{cannot increment value of type 'svint8_t'}} -- 2.7.4