[PATCH] Handle undefined extern vars in output_in_order

Alexander Monakov amonakov@ispras.ru
Thu Jun 9 13:13:00 GMT 2016


Hi,

This patch teaches cgraphunit.c:output_in_order to output undefined external
variables via assemble_undefined_decl.  At the moment that is only done for
-ftoplevel-reorder in varpool.c:symbol_table::output_variables.  This patch
makes both behave the same way.  I've also made handling of variables in both
functions look similar to each other.

I'll admit it's rather unclear to me what the '!DECL_EXTERNAL (pv->decl)'
condition is guarding in output_in_order (removed in my patch).  AIUI, it
should be always true for defined variables (or, conversely, if it's false
for a defined variable, why are we skipping it?).

I have plans to reimplement handling of "omp declare target link" in a more
clean manner.  Now it looks quite out of place there.

Bootstrapped and regtested on x86_64, OK for trunk?

Alexander

	* cgraphunit.c (cgraph_order_sort_kind): New entry ORDER_VAR_UNDEF.
	(output_in_order): Loop over undefined variables too.  Output them
	via assemble_undefined_decl.  Skip "omp declare target link" variables
	earlier.
	* varpool.c (symbol_table::output_variables): Handle undefined
	variables together with defined ones.

diff --git a/gcc/cgraphunit.c b/gcc/cgraphunit.c
index 4bfcad7..5a04902 100644
--- a/gcc/cgraphunit.c
+++ b/gcc/cgraphunit.c
@@ -2141,6 +2141,7 @@ enum cgraph_order_sort_kind
   ORDER_UNDEFINED = 0,
   ORDER_FUNCTION,
   ORDER_VAR,
+  ORDER_VAR_UNDEF,
   ORDER_ASM
 };
 
@@ -2187,16 +2188,25 @@ output_in_order (bool no_reorder)
 	}
     }
 
-  FOR_EACH_DEFINED_VARIABLE (pv)
-    if (!DECL_EXTERNAL (pv->decl))
-      {
-	if (no_reorder && !pv->no_reorder)
-	    continue;
-	i = pv->order;
-	gcc_assert (nodes[i].kind == ORDER_UNDEFINED);
-	nodes[i].kind = ORDER_VAR;
-	nodes[i].u.v = pv;
-      }
+  FOR_EACH_VARIABLE (pv)
+    {
+      if (no_reorder && !pv->no_reorder)
+	continue;
+      if (DECL_HARD_REGISTER (pv->decl))
+	continue;
+      if (DECL_HAS_VALUE_EXPR_P (pv->decl))
+	{
+	  gcc_checking_assert (lookup_attribute ("omp declare target link",
+						 DECL_ATTRIBUTES (pv->decl)));
+#ifdef ACCEL_COMPILER
+	  continue;
+#endif
+	}
+      i = pv->order;
+      gcc_assert (nodes[i].kind == ORDER_UNDEFINED);
+      nodes[i].kind = pv->definition ? ORDER_VAR : ORDER_VAR_UNDEF;
+      nodes[i].u.v = pv;
+    }
 
   for (pa = symtab->first_asm_symbol (); pa; pa = pa->next)
     {
@@ -2222,16 +2232,13 @@ output_in_order (bool no_reorder)
 	  break;
 
 	case ORDER_VAR:
-#ifdef ACCEL_COMPILER
-	  /* Do not assemble "omp declare target link" vars.  */
-	  if (DECL_HAS_VALUE_EXPR_P (nodes[i].u.v->decl)
-	      && lookup_attribute ("omp declare target link",
-				   DECL_ATTRIBUTES (nodes[i].u.v->decl)))
-	    break;
-#endif
 	  nodes[i].u.v->assemble_decl ();
 	  break;
 
+	case ORDER_VAR_UNDEF:
+	  assemble_undefined_decl (nodes[i].u.v->decl);
+	  break;
+
 	case ORDER_ASM:
 	  assemble_asm (nodes[i].u.a->asm_str);
 	  break;
diff --git a/gcc/varpool.c b/gcc/varpool.c
index ab615fa..b513026 100644
--- a/gcc/varpool.c
+++ b/gcc/varpool.c
@@ -733,11 +733,6 @@ symbol_table::output_variables (void)
 
   timevar_push (TV_VAROUT);
 
-  FOR_EACH_VARIABLE (node)
-    if (!node->definition
-	&& !DECL_HAS_VALUE_EXPR_P (node->decl)
- 	&& !DECL_HARD_REGISTER (node->decl))
-      assemble_undefined_decl (node->decl);
   FOR_EACH_DEFINED_VARIABLE (node)
     {
       /* Handled in output_in_order.  */
@@ -747,20 +742,24 @@ symbol_table::output_variables (void)
       node->finalize_named_section_flags ();
     }
 
-  FOR_EACH_DEFINED_VARIABLE (node)
+  FOR_EACH_VARIABLE (node)
     {
-      /* Handled in output_in_order.  */
       if (node->no_reorder)
 	continue;
+      if (DECL_HARD_REGISTER (node->decl))
+	continue;
+      if (DECL_HAS_VALUE_EXPR_P (node->decl))
+	{
+	  gcc_checking_assert (lookup_attribute ("omp declare target link",
+						 DECL_ATTRIBUTES (node->decl)));
 #ifdef ACCEL_COMPILER
-      /* Do not assemble "omp declare target link" vars.  */
-      if (DECL_HAS_VALUE_EXPR_P (node->decl)
-	  && lookup_attribute ("omp declare target link",
-			       DECL_ATTRIBUTES (node->decl)))
-	continue;
+	  continue;
 #endif
-      if (node->assemble_decl ())
-        changed = true;
+	}
+      if (node->definition)
+	changed |= node->assemble_decl ();
+      else
+	assemble_undefined_decl (node->decl);
     }
   timevar_pop (TV_VAROUT);
   return changed;



More information about the Gcc-patches mailing list