Bug #:
Submitted by:
Reviewed by:
Extended Expr's constant expression predicates to return a source location
if the predicate returns false. This enables us to position the cursor
exactly were the error occurred (simple pleasures:-).

constant.c:9:9: error: enumerator value for 'E2' is not an integer constant
  E2 = (aconst + 1), // illegal
        ^
constant.c:10:8: error: enumerator value for 'E3' is not an integer constant
  E3 = "abc",
       ^
constant.c:12:12: error: enumerator value for 'E5' is not an integer constant
  E5 = 0?7:printf("xx"), // illegal
           ^
constant.c:13:12: error: enumerator value for 'E6' is not an integer constant
  E6 = 1?7:printf("xx"), // legal
           ^
constant.c:16:14: error: enumerator value for 'E9' is not an integer constant
  E9 = E0 || a, // illegal
             ^
constant.c:21:6: error: array has incomplete element type 'void'
void ary[7];
     ^
constant.c:22:28: error: variable length array declared outside of any function
struct { int a; } ary2[1?7:printf("xx")],
                           ^
constant.c:23:34: error: variable length array declared outside of any function
                  aryIllegal[0?7:printf("yy")];
                                 ^
constant.c:25:10: error: variable length array declared outside of any function
int ary3[a]; // illegal
         ^
constant.c:26:17: error: size of array has non-integer type 'float'
typedef int vla[2.0]; // illegal
                ^
constant.c:30:22: error: size of array has non-integer type 'float'
int nonIntegerArray2[1+2.0];
                     ^

llvm-svn: 39454
diff --git a/clang/Sema/SemaDecl.cpp b/clang/Sema/SemaDecl.cpp
index e6bc634..e5fafa2 100644
--- a/clang/Sema/SemaDecl.cpp
+++ b/clang/Sema/SemaDecl.cpp
@@ -31,12 +31,14 @@
 // a constant expression of type int with a value greater than zero.
 bool Sema::isConstantArrayType(ArrayType *ary, SourceLocation loc) { 
   if (Expr *size = ary->getSize()) {
-    if (!size->isConstantExpr()) {
-      Diag(loc, diag::err_typecheck_illegal_vla);
+    SourceLocation expLoc;
+    if (!size->isConstantExpr(expLoc)) {
+      Diag(expLoc, diag::err_typecheck_illegal_vla);
       return false;
     }
     if (!size->getType()->isIntegerType()) {
-      Diag(loc, diag::err_array_size_non_int, size->getType().getAsString());
+      Diag(size->getLocStart(), diag::err_array_size_non_int, 
+           size->getType().getAsString());
       return false;
     }
     // We have a constant expression with an integer type, now make sure 
@@ -778,9 +780,10 @@
       return 0;
     }
   }
+  SourceLocation expLoc;
   // C99 6.7.2.2p2: Make sure we have an integer constant expression.
-  if (Val && !((Expr *)Val)->isIntegerConstantExpr()) {
-    Diag(IdLoc, diag::err_enum_value_not_integer_constant_expr, Id->getName());
+  if (Val && !((Expr *)Val)->isIntegerConstantExpr(expLoc)) {
+    Diag(expLoc, diag::err_enum_value_not_integer_constant_expr, Id->getName());
     return 0;
   }
   QualType Ty = Context.getTagDeclType(TheEnumDecl);
diff --git a/clang/Sema/SemaStmt.cpp b/clang/Sema/SemaStmt.cpp
index 4fd9d99..7796f2c 100644
--- a/clang/Sema/SemaStmt.cpp
+++ b/clang/Sema/SemaStmt.cpp
@@ -37,8 +37,9 @@
                     SourceLocation ColonLoc, StmtTy *SubStmt) {
   assert((LHSVal != 0) && "missing expression in case statement");
     
+  SourceLocation expLoc;
   // C99 6.8.4.2p3: The expression shall be an integer constant.
-  if (!((Expr *)LHSVal)->isIntegerConstantExpr())
+  if (!((Expr *)LHSVal)->isIntegerConstantExpr(expLoc))
     return Diag(CaseLoc, diag::err_case_label_not_integer_constant_expr);
 
   return new CaseStmt((Expr*)LHSVal, (Expr*)RHSVal, (Stmt*)SubStmt);