From 51c3b7c6ec20262f2a4698f42e533c28d2c38a87 Mon Sep 17 00:00:00 2001
From: Ian Lance Taylor <ian@gcc.gnu.org>
Date: Fri, 27 Sep 2019 17:34:58 +0000
Subject: [PATCH] compiler: only check whether struct or array types are big

    Fetching the size of a type typically involves a hash table lookup,
    and is generally non-trivial.  The escape analysis code calls is_big
    more than one might expect.  So only fetch the size if we need it.

    Reviewed-on: https://go-review.googlesource.com/c/gofrontend/+/197699

From-SVN: r276187
---
 gcc/go/gofrontend/MERGE     |  2 +-
 gcc/go/gofrontend/escape.cc | 22 +++++++++++++++++-----
 2 files changed, 18 insertions(+), 6 deletions(-)

diff --git a/gcc/go/gofrontend/MERGE b/gcc/go/gofrontend/MERGE
index 574d33d95bcd..871a3ee5c182 100644
--- a/gcc/go/gofrontend/MERGE
+++ b/gcc/go/gofrontend/MERGE
@@ -1,4 +1,4 @@
-d1fa6c34e56eade6fb5b6291f0a727b1a12bf6f1
+27d1f3031197428b5745d09c167f982d638b8776
 
 The first line of this file holds the git revision number of the last
 merge done from the gofrontend repository.
diff --git a/gcc/go/gofrontend/escape.cc b/gcc/go/gofrontend/escape.cc
index db3afc787d12..91f43a65d3d0 100644
--- a/gcc/go/gofrontend/escape.cc
+++ b/gcc/go/gofrontend/escape.cc
@@ -511,16 +511,28 @@ Node::is_big(Escape_context* context) const
       || t->is_abstract())
     return false;
 
-  int64_t size;
-  bool ok = t->backend_type_size(context->gogo(), &size);
-  bool big = ok && (size < 0 || size > 10 * 1024 * 1024);
+  bool big = false;
+  if (t->struct_type() != NULL
+      || (t->array_type() != NULL && !t->is_slice_type()))
+    {
+      int64_t size;
+      bool ok = t->backend_type_size(context->gogo(), &size);
+      big = ok && (size < 0 || size > 10 * 1024 * 1024);
+    }
 
   if (this->expr() != NULL)
     {
       if (this->expr()->allocation_expression() != NULL)
 	{
-	  ok = t->deref()->backend_type_size(context->gogo(), &size);
-	  big = big || size <= 0 || size >= (1 << 16);
+	  Type* pt = t->deref();
+	  if (pt->struct_type() != NULL
+	      || (pt->array_type() != NULL && !pt->is_slice_type()))
+	    {
+	      int64_t size;
+	      bool ok = pt->backend_type_size(context->gogo(), &size);
+	      if (ok)
+		big = big || size <= 0 || size >= (1 << 16);
+	    }
 	}
       else if (this->expr()->call_expression() != NULL)
 	{
-- 
GitLab