<div dir="ltr">Hello Douglas,<div><br></div><div>Thanks for the report. I don't think it is intentional, it is certainly a regression (I'm surprised the patch would lead to such behavior), I will take a look tomorrow.</div></div><br><div class="gmail_quote"><div dir="ltr" class="gmail_attr">On Wed, Apr 1, 2020 at 8:28 PM Yung, Douglas via cfe-commits <<a href="mailto:cfe-commits@lists.llvm.org">cfe-commits@lists.llvm.org</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">Hi Haojian,<br>
<br>
I noticed that after your change, the compiler is now giving an error when trying to create a vector of >= 1024 elements when previously it worked, and gcc has no problem with the same code. Is that intentional? I have put the details in PR45387, can you take a look?<br>
<br>
Douglas Yung<br>
<br>
-----Original Message-----<br>
From: cfe-commits <<a href="mailto:cfe-commits-bounces@lists.llvm.org" target="_blank">cfe-commits-bounces@lists.llvm.org</a>> On Behalf Of Haojian Wu via cfe-commits<br>
Sent: Monday, March 30, 2020 5:57<br>
To: <a href="mailto:cfe-commits@lists.llvm.org" target="_blank">cfe-commits@lists.llvm.org</a><br>
Subject: [clang] 6f428e0 - [AST] Fix crashes on decltype(recovery-expr).<br>
<br>
<br>
Author: Haojian Wu<br>
Date: 2020-03-30T14:56:33+02:00<br>
New Revision: 6f428e09fbe8ce7e3510ae024031a5fc19653483<br>
<br>
URL: <a href="https://github.com/llvm/llvm-project/commit/6f428e09fbe8ce7e3510ae024031a5fc19653483" rel="noreferrer" target="_blank">https://github.com/llvm/llvm-project/commit/6f428e09fbe8ce7e3510ae024031a5fc19653483</a><br>
DIFF: <a href="https://github.com/llvm/llvm-project/commit/6f428e09fbe8ce7e3510ae024031a5fc19653483.diff" rel="noreferrer" target="_blank">https://github.com/llvm/llvm-project/commit/6f428e09fbe8ce7e3510ae024031a5fc19653483.diff</a><br>
<br>
LOG: [AST] Fix crashes on decltype(recovery-expr).<br>
<br>
Summary: We mark these decls as invalid.<br>
<br>
Reviewers: sammccall<br>
<br>
Subscribers: cfe-commits<br>
<br>
Tags: #clang<br>
<br>
Differential Revision: <a href="https://reviews.llvm.org/D77037" rel="noreferrer" target="_blank">https://reviews.llvm.org/D77037</a><br>
<br>
Added: <br>
<br>
<br>
Modified: <br>
    clang/include/clang/AST/DependenceFlags.h<br>
    clang/include/clang/AST/Type.h<br>
    clang/lib/Parse/ParseExprCXX.cpp<br>
    clang/lib/Sema/SemaType.cpp<br>
    clang/test/AST/ast-dump-expr-errors.cpp<br>
    clang/test/Sema/invalid-member.cpp<br>
    clang/unittests/Sema/CodeCompleteTest.cpp<br>
<br>
Removed: <br>
<br>
<br>
<br>
################################################################################<br>
diff  --git a/clang/include/clang/AST/DependenceFlags.h b/clang/include/clang/AST/DependenceFlags.h<br>
index 75c9aa1656b8..0b24bae6df9b 100644<br>
--- a/clang/include/clang/AST/DependenceFlags.h<br>
+++ b/clang/include/clang/AST/DependenceFlags.h<br>
@@ -50,14 +50,16 @@ struct TypeDependenceScope {<br>
     /// Whether this type is a variably-modified type (C99 6.7.5).<br>
     VariablyModified = 8,<br>
<br>
-    // FIXME: add Error bit.<br>
+    /// Whether this type references an error, e.g. decltype(err-expression)<br>
+    /// yields an error type.<br>
+    Error = 16,<br>
<br>
     None = 0,<br>
-    All = 15,<br>
+    All = 31,<br>
<br>
     DependentInstantiation = Dependent | Instantiation,<br>
<br>
-    LLVM_MARK_AS_BITMASK_ENUM(/*LargestValue=*/VariablyModified)<br>
+    LLVM_MARK_AS_BITMASK_ENUM(/*LargestValue=*/Error)<br>
   };<br>
 };<br>
 using TypeDependence = TypeDependenceScope::TypeDependence;<br>
@@ -147,6 +149,7 @@ class Dependence {<br>
     return translate(V, UnexpandedPack, TypeDependence::UnexpandedPack) |<br>
            translate(V, Instantiation, TypeDependence::Instantiation) |<br>
            translate(V, Dependent, TypeDependence::Dependent) |<br>
+           translate(V, Error, TypeDependence::Error) |<br>
            translate(V, VariablyModified, TypeDependence::VariablyModified);<br>
   }<br>
<br>
<br>
diff  --git a/clang/include/clang/AST/Type.h b/clang/include/clang/AST/Type.h index 248fbcfba98e..5d2c035ea0fe 100644<br>
--- a/clang/include/clang/AST/Type.h<br>
+++ b/clang/include/clang/AST/Type.h<br>
@@ -2139,6 +2139,11 @@ class alignas(8) Type : public ExtQualsTypeCommonBase {<br>
     return static_cast<TypeDependence>(TypeBits.Dependence);<br>
   }<br>
<br>
+  /// Whether this type is an error type.<br>
+  bool containsErrors() const {<br>
+    return getDependence() & TypeDependence::Error;  }<br>
+<br>
   /// Whether this type is a dependent type, meaning that its definition<br>
   /// somehow depends on a template parameter (C++ [temp.dep.type]).<br>
   bool isDependentType() const {<br>
<br>
diff  --git a/clang/lib/Parse/ParseExprCXX.cpp b/clang/lib/Parse/ParseExprCXX.cpp<br>
index 761fad9456be..4389c8777c6d 100644<br>
--- a/clang/lib/Parse/ParseExprCXX.cpp<br>
+++ b/clang/lib/Parse/ParseExprCXX.cpp<br>
@@ -3105,10 +3105,14 @@ Parser::ParseCXXNewExpression(bool UseGlobal, SourceLocation Start) {<br>
       auto RunSignatureHelp = [&]() {<br>
         ParsedType TypeRep =<br>
             Actions.ActOnTypeName(getCurScope(), DeclaratorInfo).get();<br>
-        assert(TypeRep && "invalid types should be handled before");<br>
-        QualType PreferredType = Actions.ProduceConstructorSignatureHelp(<br>
-            getCurScope(), TypeRep.get()->getCanonicalTypeInternal(),<br>
-            DeclaratorInfo.getEndLoc(), ConstructorArgs, ConstructorLParen);<br>
+        QualType PreferredType;<br>
+        // ActOnTypeName might adjust DeclaratorInfo and return a null type even<br>
+        // the passing DeclaratorInfo is valid, e.g. running SignatureHelp on<br>
+        // `new decltype(invalid) (^)`.<br>
+        if (TypeRep)<br>
+          PreferredType = Actions.ProduceConstructorSignatureHelp(<br>
+              getCurScope(), TypeRep.get()->getCanonicalTypeInternal(),<br>
+              DeclaratorInfo.getEndLoc(), ConstructorArgs, <br>
+ ConstructorLParen);<br>
         CalledSignatureHelp = true;<br>
         return PreferredType;<br>
       };<br>
<br>
diff  --git a/clang/lib/Sema/SemaType.cpp b/clang/lib/Sema/SemaType.cpp index 55ce028fb8c2..e128ebf31270 100644<br>
--- a/clang/lib/Sema/SemaType.cpp<br>
+++ b/clang/lib/Sema/SemaType.cpp<br>
@@ -1678,6 +1678,12 @@ static QualType ConvertDeclSpecToType(TypeProcessingState &state) {<br>
     break;<br>
   }<br>
<br>
+  // FIXME: we want resulting declarations to be marked invalid, but <br>
+ claiming  // the type is invalid is too strong - e.g. it causes <br>
+ ActOnTypeName to return  // a null type.<br>
+  if (Result->containsErrors())<br>
+    declarator.setInvalidType();<br>
+<br>
   if (S.getLangOpts().OpenCL &&<br>
       S.checkOpenCLDisabledTypeDeclSpec(DS, Result))<br>
     declarator.setInvalidType(true);<br>
<br>
diff  --git a/clang/test/AST/ast-dump-expr-errors.cpp b/clang/test/AST/ast-dump-expr-errors.cpp<br>
index e623fad04f4c..9334b73a4354 100644<br>
--- a/clang/test/AST/ast-dump-expr-errors.cpp<br>
+++ b/clang/test/AST/ast-dump-expr-errors.cpp<br>
@@ -42,5 +42,9 @@ int d = static_cast<int>(bar() + 1);<br>
<br>
 // FIXME: store initializer even when 'auto' could not be deduced.<br>
 // Expressions with errors currently do not keep initializers around.<br>
-// CHECK:     `-VarDecl {{.*}} invalid e 'auto'<br>
+// CHECK: -VarDecl {{.*}} invalid e 'auto'<br>
 auto e = bar();<br>
+<br>
+// Error type should result in an invalid decl.<br>
+// CHECK: -VarDecl {{.*}} invalid f 'decltype(<recovery-expr>(bar))'<br>
+decltype(bar()) f;<br>
<br>
diff  --git a/clang/test/Sema/invalid-member.cpp b/clang/test/Sema/invalid-member.cpp<br>
index 5475157e936e..544979980fc9 100644<br>
--- a/clang/test/Sema/invalid-member.cpp<br>
+++ b/clang/test/Sema/invalid-member.cpp<br>
@@ -1,7 +1,15 @@<br>
-// RUN: %clang_cc1 -verify -fsyntax-only %s -void foo(); // expected-note {{requires 0 arguments}}<br>
+// RUN: %clang_cc1 -verify -fsyntax-only -fno-recovery-ast %s // RUN: <br>
+%clang_cc1 -verify -fsyntax-only -frecovery-ast %s<br>
+<br>
+void foo(); // expected-note 2{{requires 0 arguments}}<br>
 class X {<br>
   decltype(foo(42)) invalid; // expected-error {{no matching function}}  };  // Should be able to evaluate sizeof without crashing.<br>
 static_assert(sizeof(X) == 1, "No valid members");<br>
+<br>
+class Y {<br>
+  typeof(foo(42)) invalid; // expected-error {{no matching function}} <br>
+}; // Should be able to evaluate sizeof without crashing.<br>
+static_assert(sizeof(Y) == 1, "No valid members");<br>
<br>
diff  --git a/clang/unittests/Sema/CodeCompleteTest.cpp b/clang/unittests/Sema/CodeCompleteTest.cpp<br>
index a9441a679cac..d8b303d77bb9 100644<br>
--- a/clang/unittests/Sema/CodeCompleteTest.cpp<br>
+++ b/clang/unittests/Sema/CodeCompleteTest.cpp<br>
@@ -486,7 +486,10 @@ TEST(PreferredTypeTest, NoCrashOnInvalidTypes) {<br>
   StringRef Code = R"cpp(<br>
     auto x = decltype(&1)(^);<br>
     auto y = new decltype(&1)(^);<br>
+    // GNU decimal type extension is not supported in clang.<br>
+    auto z = new _Decimal128(^);<br>
   )cpp";<br>
   EXPECT_THAT(collectPreferredTypes(Code), Each("NULL TYPE"));  }<br>
+<br>
 } // namespace<br>
<br>
<br>
<br>
_______________________________________________<br>
cfe-commits mailing list<br>
<a href="mailto:cfe-commits@lists.llvm.org" target="_blank">cfe-commits@lists.llvm.org</a><br>
<a href="https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits" rel="noreferrer" target="_blank">https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits</a><br>
_______________________________________________<br>
cfe-commits mailing list<br>
<a href="mailto:cfe-commits@lists.llvm.org" target="_blank">cfe-commits@lists.llvm.org</a><br>
<a href="https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits" rel="noreferrer" target="_blank">https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits</a><br>
</blockquote></div>