public inbox for binutils@sourceware.org
 help / color / mirror / Atom feed
* [PATCH 2/4] GAS: Make new fake labels when cloning a symbol
@ 2010-07-26 10:47 Maciej W. Rozycki
  2010-07-31  8:59 ` Richard Sandiford
                   ` (2 more replies)
  0 siblings, 3 replies; 18+ messages in thread
From: Maciej W. Rozycki @ 2010-07-26 10:47 UTC (permalink / raw)
  To: binutils; +Cc: Richard Sandiford, Catherine Moore, gnu-mips-sgxx

Hi,

 Equated symbols (defined with .eqv) aka forward references are defined to 
reevaluate the expression they are defined to whenever they are referred 
to.  This does not happen for the special "dot" symbol -- the value 
calculated the first time the equated symbol has been used is then used 
over and over again.

 The reason is each time a reference to the "dot" symbol is made a special 
fake label is created.  This label is then recorded in the chain of 
symbols the equated symbol is defined to and never reevaluated.  The 
solution is to create a new fake label each time the equated symbol is 
used.

 Additionally symbol_clone_if_forward_ref() would only be called 
recursively for internal symbols referring to the special expression 
section.  It should happen for all symbols.

 Overall with symbol definitions like this:

	.data
	.eqv	fnord, .
	.eqv	foobar, fnord + 4
	.eqv	foobaz, foobar - 16
	.word	0
	.word	fnord
	.word	fnord
	.word	foobaz
	.word	foobaz

the "dot" symbol would only be calculated once, with the second .word 
directive, i.e. both the second and the third word emitted would have the 
same value (address of the second word).

 This would also cause "foobaz" to be calculated (as a forward reference) 
with the third .eqv directive and then cloned each time when used with 
.word.  Howeved "foobar" would only be calculated with the second and the 
third .eqv directive, but not with the .word directives, thus fixed at 
the value of the first rather than each use.

 In the end data emitted would be:

0, 0, 0, -12, -12

as if .set was used, rather than:

0, 4, 8, 0, 4

as expected.

2010-07-26  Maciej W. Rozycki  <macro@codesourcery.com>

	gas/
	* symbols.c (symbol_clone_if_forward_ref): Don't limit cloning
	to expr_section symbols.  Make fresh fake labels.
	* write.c (TC_FAKE_LABEL): Move over to...
	* write.h (TC_FAKE_LABEL): ... here.

 OK to apply?

  Maciej

binutils-gas-eqv-dot.diff
Index: binutils-fsf-trunk-quilt/gas/symbols.c
===================================================================
--- binutils-fsf-trunk-quilt.orig/gas/symbols.c	2010-07-24 02:25:04.000000000 +0100
+++ binutils-fsf-trunk-quilt/gas/symbols.c	2010-07-24 02:25:12.000000000 +0100
@@ -645,7 +645,7 @@ symbol_clone_if_forward_ref (symbolS *sy
 
       /* Re-using sy_resolving here, as this routine cannot get called from
 	 symbol resolution code.  */
-      if (symbolP->bsym->section == expr_section && !symbolP->sy_resolving)
+      if (!symbolP->sy_resolving)
 	{
 	  symbolP->sy_resolving = 1;
 	  add_symbol = symbol_clone_if_forward_ref (add_symbol, is_forward);
@@ -656,7 +656,23 @@ symbol_clone_if_forward_ref (symbolS *sy
       if (symbolP->sy_forward_ref
 	  || add_symbol != symbolP->sy_value.X_add_symbol
 	  || op_symbol != symbolP->sy_value.X_op_symbol)
-	symbolP = symbol_clone (symbolP, 0);
+	{
+	  symbolS *temp_symbol;
+	  int is_temp_add;
+	  int is_temp_op;
+
+	  symbolP = symbol_clone (symbolP, 0);
+	  is_temp_add = add_symbol && TC_FAKE_LABEL (S_GET_NAME (add_symbol));
+	  is_temp_op = op_symbol && TC_FAKE_LABEL (S_GET_NAME (op_symbol));
+	  if (is_temp_add || is_temp_op)
+	    {
+	      temp_symbol = symbol_temp_new_now ();
+	      if (is_temp_add)
+		add_symbol = temp_symbol;
+	      if (is_temp_op)
+		op_symbol = temp_symbol;
+	    }
+	}
 
       symbolP->sy_value.X_add_symbol = add_symbol;
       symbolP->sy_value.X_op_symbol = op_symbol;
Index: binutils-fsf-trunk-quilt/gas/write.c
===================================================================
--- binutils-fsf-trunk-quilt.orig/gas/write.c	2010-07-24 02:25:04.000000000 +0100
+++ binutils-fsf-trunk-quilt/gas/write.c	2010-07-24 02:25:12.000000000 +0100
@@ -102,10 +102,6 @@
 #define MD_PCREL_FROM_SECTION(FIX, SEC) md_pcrel_from (FIX)
 #endif
 
-#ifndef TC_FAKE_LABEL
-#define TC_FAKE_LABEL(NAME) (strcmp ((NAME), FAKE_LABEL_NAME) == 0)
-#endif
-
 /* Positive values of TC_FX_SIZE_SLACK allow a target to define
    fixups that far past the end of a frag.  Having such fixups
    is of course most most likely a bug in setting fx_size correctly.
Index: binutils-fsf-trunk-quilt/gas/write.h
===================================================================
--- binutils-fsf-trunk-quilt.orig/gas/write.h	2010-07-24 02:25:04.000000000 +0100
+++ binutils-fsf-trunk-quilt/gas/write.h	2010-07-24 02:25:12.000000000 +0100
@@ -29,6 +29,10 @@
 #define FAKE_LABEL_NAME "L0\001"
 #endif
 
+#ifndef TC_FAKE_LABEL
+#define TC_FAKE_LABEL(NAME) (strcmp ((NAME), FAKE_LABEL_NAME) == 0)
+#endif
+
 #include "bit_fix.h"
 
 /*

^ permalink raw reply	[flat|nested] 18+ messages in thread

end of thread, other threads:[~2010-12-03 16:47 UTC | newest]

Thread overview: 18+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2010-07-26 10:47 [PATCH 2/4] GAS: Make new fake labels when cloning a symbol Maciej W. Rozycki
2010-07-31  8:59 ` Richard Sandiford
2010-08-27 12:11   ` Maciej W. Rozycki
2010-08-30 17:53     ` Richard Sandiford
2010-10-29 14:37 ` [PATCH 2.0/4 v2] GAS: Only clone equated symbols on a final reference Maciej W. Rozycki
2010-10-30  9:56   ` Richard Sandiford
2010-12-01 20:35     ` Maciej W. Rozycki
2010-10-29 14:38 ` [PATCH 2.5/4 v2] GAS: Make new fake labels when cloning a symbol Maciej W. Rozycki
2010-10-30 10:01   ` Richard Sandiford
2010-11-01 12:23     ` Maciej W. Rozycki
2010-11-01 21:32       ` Richard Sandiford
2010-12-01 21:34         ` Maciej W. Rozycki
2010-12-02 10:00           ` Jie Zhang
2010-12-02 17:01           ` Richard Earnshaw
2010-12-02 23:19             ` Maciej W. Rozycki
2010-12-03 10:58               ` Richard Sandiford
2010-12-03 16:20                 ` Maciej W. Rozycki
2010-12-03 16:47                   ` Richard Sandiford

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).