Index: include/clang/Basic/DiagnosticSemaKinds.td
===================================================================
--- include/clang/Basic/DiagnosticSemaKinds.td	(revision 282063)
+++ include/clang/Basic/DiagnosticSemaKinds.td	(working copy)
@@ -5932,6 +5932,8 @@
   "only the first dimension of an allocated array may have dynamic size">;
 def err_new_array_init_args : Error<
   "array 'new' cannot have initialization arguments">;
+def err_new_array_excess_initializers : Error<
+  "excess elements in array 'new' initializer">;
 def ext_new_paren_array_nonconst : ExtWarn<
   "when type is in parentheses, array cannot have dynamic size">;
 def err_placement_new_non_placement_delete : Error<
Index: lib/Sema/SemaExprCXX.cpp
===================================================================
--- lib/Sema/SemaExprCXX.cpp	(revision 282063)
+++ lib/Sema/SemaExprCXX.cpp	(working copy)
@@ -1589,6 +1589,13 @@
     if (result.isInvalid()) return ExprError();
     ArraySize = result.get();
   }
+
+  // this variable will store size of array, specified in new[] expression.
+  llvm::APSInt ArraySizeValue;
+  // this value becomes true if size of array is not value dependent and
+  // is integer constant expression.
+  bool ArraySizeValueIsValid = false;
+
   // C++98 5.3.4p6: "The expression in a direct-new-declarator shall have
   //   integral or enumeration type with a non-negative value."
   // C++11 [expr.new]p6: The expression [...] shall be of integral or unscoped
@@ -1687,13 +1694,13 @@
     // Note: such a construct has well-defined semantics in C++11: it throws
     // std::bad_array_new_length.
     if (!ArraySize->isValueDependent()) {
-      llvm::APSInt Value;
       // We've already performed any required implicit conversion to integer or
       // unscoped enumeration type.
-      if (ArraySize->isIntegerConstantExpr(Value, Context)) {
-        if (Value < llvm::APSInt(
-                        llvm::APInt::getNullValue(Value.getBitWidth()),
-                                 Value.isUnsigned())) {
+      if (ArraySize->isIntegerConstantExpr(ArraySizeValue, Context)) {
+        ArraySizeValueIsValid = true;
+        if (ArraySizeValue < llvm::APSInt(
+                        llvm::APInt::getNullValue(ArraySizeValue.getBitWidth()),
+                        ArraySizeValue.isUnsigned())) {
           if (getLangOpts().CPlusPlus11)
             Diag(ArraySize->getLocStart(),
                  diag::warn_typecheck_negative_array_new_size)
@@ -1704,17 +1711,18 @@
                              << ArraySize->getSourceRange());
         } else if (!AllocType->isDependentType()) {
           unsigned ActiveSizeBits =
-            ConstantArrayType::getNumAddressingBits(Context, AllocType, Value);
+            ConstantArrayType::getNumAddressingBits(Context, AllocType,
+                                                    ArraySizeValue);
           if (ActiveSizeBits > ConstantArrayType::getMaxSizeBits(Context)) {
             if (getLangOpts().CPlusPlus11)
               Diag(ArraySize->getLocStart(),
                    diag::warn_array_new_too_large)
-                << Value.toString(10)
+                << ArraySizeValue.toString(10)
                 << ArraySize->getSourceRange();
             else
               return ExprError(Diag(ArraySize->getLocStart(),
                                     diag::err_array_too_large)
-                               << Value.toString(10)
+                               << ArraySizeValue.toString(10)
                                << ArraySize->getSourceRange());
           }
         }
@@ -1802,10 +1810,58 @@
       return ExprError();
     }
     if (InitListExpr *ILE = dyn_cast_or_null<InitListExpr>(Initializer)) {
-      // We do the initialization typechecking against the array type
-      // corresponding to the number of initializers + 1 (to also check
-      // default-initialization).
-      unsigned NumElements = ILE->getNumInits() + 1;
+
+      unsigned NumElements = ILE->getNumInits();
+
+      if (ArraySizeValueIsValid) {
+        llvm::APSInt InitListSizeValue(
+                       llvm::APInt(ArraySizeValue.getBitWidth(),
+                                   static_cast<uint64_t>(NumElements)),
+                       ArraySizeValue.isUnsigned());
+
+        unsigned NumAdjustedElements =
+          static_cast<unsigned>(ArraySizeValue.getZExtValue());
+
+        if (ArraySizeValue < InitListSizeValue) {
+          // if ArraySizeValue store value less than 0,
+          // then NumAdjustedElements can't be used in getInit().
+          if (!ArraySizeValue.isUnsigned() &&
+              ArraySizeValue.isNegative())
+            NumAdjustedElements = 0;
+
+          if (NumElements > 0) {
+            Expr *FirstExcessElement = ILE->getInit(NumAdjustedElements);
+            Expr *LastExcessElement = ILE->getInit(NumElements - 1);
+
+            SourceRange ExcessElementsRange(
+                        FirstExcessElement->getSourceRange().getBegin(),
+                        LastExcessElement->getSourceRange().getEnd());
+
+            Diag(StartLoc, diag::err_new_array_excess_initializers)
+                << ExcessElementsRange;
+
+            return ExprError();
+          }
+
+          // This block covers such cases like: new T[-1] {}
+          // CodeGen will emit operator new (-1), which will
+          // throw exception in runtime. The caveat is that
+          // default constructor for T is still required as array
+          // filler.
+          NumAdjustedElements = 1;
+        }
+
+        // make sure, that InitType array has exactly the same number
+        // of elements as declared in new[]
+        NumElements = NumAdjustedElements;
+      } else {
+        // If size is not constant expression, then
+        // we do the initialization typechecking against the array type
+        // corresponding to the number of initializers + 1 (to also check
+        // default-initialization).
+        ++NumElements;
+      }
+
       InitType = Context.getConstantArrayType(AllocType,
           llvm::APInt(Context.getTypeSize(Context.getSizeType()), NumElements),
                                               ArrayType::Normal, 0);
