This is the mail archive of the binutils@sourceware.org mailing list for the binutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[PATCH][GAS][AARCH64]Fix "align directive causes MAP_DATA symbol to be lost"


Hi all,

This is a similar patch to the one for ARM: https://sourceware.org/ml/binutils/2015-03/msg00042.html

A MAP_DATA symbol is postponed until the code is in MAP_INSN state.
When we have the following similar asm,

.text
.long 123  --> (1)
.align 4 --> (2)
    ret

(1) MAP_DATA is ignored because the code is initially in MAP_UNDEFINED mode.

a (2).align directive will triggle a frag initialization to setup the MAP_INSN state and mapping symbol, and start a new frag. And the MAP_DATA symbol for (1) is left forgotten silently.

This patch change the structure a little bit to correctly emit MAP_DATA mapping symbol.
Two test cases are also adjusted. Gas regression tests Okay.
Okay to commit?

Regards,
Renlin Li

gas/ChangeLog:

2015-03-24  Renlin Li  <renlin.li@arm.com>

* config/tc-aarch64.c (mapping_state): Remove first MAP_DATA emitting code.
    (mapping_state_2): Emit first MAP_DATA symbol here.
diff --git a/gas/config/tc-aarch64.c b/gas/config/tc-aarch64.c
index 9179fc6..9e8a40b 100644
--- a/gas/config/tc-aarch64.c
+++ b/gas/config/tc-aarch64.c
@@ -1467,13 +1467,12 @@ static void mapping_state_2 (enum mstate state, int max_chars);
 /* Set the mapping state to STATE.  Only call this when about to
    emit some STATE bytes to the file.  */
 
+#define TRANSITION(from, to) (mapstate == (from) && state == (to))
 void
 mapping_state (enum mstate state)
 {
   enum mstate mapstate = seg_info (now_seg)->tc_segment_info_data.mapstate;
 
-#define TRANSITION(from, to) (mapstate == (from) && state == (to))
-
   if (mapstate == state)
     /* The mapping symbol has already been emitted.
        There is nothing else to do.  */
@@ -1481,22 +1480,8 @@ mapping_state (enum mstate state)
   else if (TRANSITION (MAP_UNDEFINED, MAP_DATA))
     /* This case will be evaluated later in the next else.  */
     return;
-  else if (TRANSITION (MAP_UNDEFINED, MAP_INSN))
-    {
-      /* Only add the symbol if the offset is > 0:
-         if we're at the first frag, check it's size > 0;
-         if we're not at the first frag, then for sure
-         the offset is > 0.  */
-      struct frag *const frag_first = seg_info (now_seg)->frchainP->frch_root;
-      const int add_symbol = (frag_now != frag_first)
-	|| (frag_now_fix () > 0);
-
-      if (add_symbol)
-	make_mapping_symbol (MAP_DATA, (valueT) 0, frag_first);
-    }
 
   mapping_state_2 (state, 0);
-#undef TRANSITION
 }
 
 /* Same as mapping_state, but MAX_CHARS bytes have already been
@@ -1515,9 +1500,24 @@ mapping_state_2 (enum mstate state, int max_chars)
        There is nothing else to do.  */
     return;
 
+  if (TRANSITION (MAP_UNDEFINED, MAP_INSN))
+    {
+      /* Only add the symbol if the offset is > 0:
+	 if we're at the first frag, check it's size > 0;
+	 if we're not at the first frag, then for sure
+	 the offset is > 0.  */
+      struct frag *const frag_first = seg_info (now_seg)->frchainP->frch_root;
+      const int add_symbol = (frag_now != frag_first)
+	|| (frag_now_fix () > 0);
+
+      if (add_symbol)
+	make_mapping_symbol (MAP_DATA, (valueT) 0, frag_first);
+    }
+
   seg_info (now_seg)->tc_segment_info_data.mapstate = state;
   make_mapping_symbol (state, (valueT) frag_now_fix () - max_chars, frag_now);
 }
+#undef TRANSITION
 #else
 #define mapping_state(x)	/* nothing */
 #define mapping_state_2(x, y)	/* nothing */

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]