summaryrefslogtreecommitdiffstats
path: root/clang
diff options
context:
space:
mode:
Diffstat (limited to 'clang')
-rw-r--r--clang/include/clang/Basic/DiagnosticSemaKinds.td6
-rw-r--r--clang/lib/AST/Expr.cpp5
-rw-r--r--clang/lib/Sema/SemaExprCXX.cpp32
-rw-r--r--clang/lib/Sema/SemaType.cpp6
-rw-r--r--clang/test/SemaCXX/c99.cpp8
5 files changed, 41 insertions, 16 deletions
diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td
index c9bfaaf55bc..f9f2f15af06 100644
--- a/clang/include/clang/Basic/DiagnosticSemaKinds.td
+++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td
@@ -67,6 +67,9 @@ def ext_flexible_array_init : Extension<
// Declarations.
def ext_vla : Extension<
"variable length arrays are a C99 feature, accepted as an extension">;
+def err_vla_cxx : Error<
+ "variable length arrays are not permitted in C++">;
+
def ext_anon_param_requires_type_specifier : Extension<
"type specifier required for unnamed parameter, defaults to int">;
def err_bad_variable_name : Error<
@@ -2135,6 +2138,9 @@ def err_objc_array_of_interfaces : Error<
"array of interface %0 is invalid (probably should be an array of pointers)">;
def ext_c99_array_usage : Extension<
"use of C99-specific array features, accepted as an extension">;
+def err_c99_array_usage_cxx : Error<
+ "C99-specific array features are not permitted in C++">;
+
def err_invalid_protocol_qualifiers : Error<
"invalid protocol qualifiers on non-ObjC type">;
def warn_ivar_use_hidden : Warning<
diff --git a/clang/lib/AST/Expr.cpp b/clang/lib/AST/Expr.cpp
index 969098c2346..fb79f4d0f24 100644
--- a/clang/lib/AST/Expr.cpp
+++ b/clang/lib/AST/Expr.cpp
@@ -1331,7 +1331,6 @@ static ICEDiag CheckICE(const Expr* E, ASTContext &Ctx) {
case Expr::VAArgExprClass:
case Expr::AddrLabelExprClass:
case Expr::StmtExprClass:
- case Expr::GNUNullExprClass:
case Expr::CXXMemberCallExprClass:
case Expr::CXXDynamicCastExprClass:
case Expr::CXXTypeidExprClass:
@@ -1368,6 +1367,10 @@ static ICEDiag CheckICE(const Expr* E, ASTContext &Ctx) {
case Expr::ExprClass:
return ICEDiag(2, E->getLocStart());
+ case Expr::GNUNullExprClass:
+ // GCC considers the GNU __null value to be an integral constant expression.
+ return NoDiag();
+
case Expr::ParenExprClass:
return CheckICE(cast<ParenExpr>(E)->getSubExpr(), Ctx);
case Expr::IntegerLiteralClass:
diff --git a/clang/lib/Sema/SemaExprCXX.cpp b/clang/lib/Sema/SemaExprCXX.cpp
index d08d445911f..edf51cac6e7 100644
--- a/clang/lib/Sema/SemaExprCXX.cpp
+++ b/clang/lib/Sema/SemaExprCXX.cpp
@@ -326,25 +326,31 @@ Sema::ActOnCXXNew(SourceLocation StartLoc, bool UseGlobal,
Skip = 1;
}
+ // Every dimension shall be of constant size.
+ if (D.getNumTypeObjects() > 0 &&
+ D.getTypeObject(0).Kind == DeclaratorChunk::Array) {
+ for (unsigned I = 1, N = D.getNumTypeObjects(); I < N; ++I) {
+ if (D.getTypeObject(I).Kind != DeclaratorChunk::Array)
+ break;
+
+ DeclaratorChunk::ArrayTypeInfo &Array = D.getTypeObject(I).Arr;
+ if (Expr *NumElts = (Expr *)Array.NumElts) {
+ if (!NumElts->isTypeDependent() && !NumElts->isValueDependent() &&
+ !NumElts->isIntegerConstantExpr(Context)) {
+ Diag(D.getTypeObject(I).Loc, diag::err_new_array_nonconst)
+ << NumElts->getSourceRange();
+ return ExprError();
+ }
+ }
+ }
+ }
+
//FIXME: Store DeclaratorInfo in CXXNew expression.
DeclaratorInfo *DInfo = 0;
QualType AllocType = GetTypeForDeclarator(D, /*Scope=*/0, &DInfo, Skip);
if (D.isInvalidType())
return ExprError();
- // Every dimension shall be of constant size.
- unsigned i = 1;
- QualType ElementType = AllocType;
- while (const ArrayType *Array = Context.getAsArrayType(ElementType)) {
- if (!Array->isConstantArrayType()) {
- Diag(D.getTypeObject(i).Loc, diag::err_new_array_nonconst)
- << static_cast<Expr*>(D.getTypeObject(i).Arr.NumElts)->getSourceRange();
- return ExprError();
- }
- ElementType = Array->getElementType();
- ++i;
- }
-
return BuildCXXNew(StartLoc, UseGlobal,
PlacementLParen,
move(PlacementArgs),
diff --git a/clang/lib/Sema/SemaType.cpp b/clang/lib/Sema/SemaType.cpp
index c4064e135eb..9f951989a73 100644
--- a/clang/lib/Sema/SemaType.cpp
+++ b/clang/lib/Sema/SemaType.cpp
@@ -593,9 +593,11 @@ QualType Sema::BuildArrayType(QualType T, ArrayType::ArraySizeModifier ASM,
if (ArraySize && !ArraySize->isTypeDependent() &&
!ArraySize->isValueDependent() &&
!ArraySize->isIntegerConstantExpr(Context))
- Diag(Loc, diag::ext_vla);
+ Diag(Loc, getLangOptions().CPlusPlus? diag::err_vla_cxx : diag::ext_vla);
else if (ASM != ArrayType::Normal || Quals != 0)
- Diag(Loc, diag::ext_c99_array_usage);
+ Diag(Loc,
+ getLangOptions().CPlusPlus? diag::err_c99_array_usage_cxx
+ : diag::ext_c99_array_usage);
}
return T;
diff --git a/clang/test/SemaCXX/c99.cpp b/clang/test/SemaCXX/c99.cpp
new file mode 100644
index 00000000000..b0ee056ef37
--- /dev/null
+++ b/clang/test/SemaCXX/c99.cpp
@@ -0,0 +1,8 @@
+// RUN: clang-cc -fsyntax-only -verify %s
+
+void f0(int i) {
+ char array[i]; // expected-error{{variable length arrays}}
+}
+
+void f1(int i[static 5]) { // expected-error{{C99}}
+}
OpenPOWER on IntegriCloud