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]

PR1491, FAIL: macros dot


This fixes "FAIL: macros dot" on LABELS_WITHOUT_COLONS targets.  The
test was failing with "unexpected end of file in macro `m' definition"
due to not skipping over multiple labels on the ".endm" line.  We
could legitimately xfail the test since these targets don't properly
support more than one label per line.  At least, not if the labels are
without colons.  However if the first label does have a colon it is
not unreasonable to allow more labels with colons.  The macro.c change
does that.

Once I'd fixed that, the test still failed.  This time the problem was
that the macro expansion listing lacked labels.  Fixed by moving code
around in read_a_source_file to save the line before the label is
eaten.  This change also results in leading whitespace being printed
for the macro expansion, which I think is a good.

gas/
	PR gas/1491
	* macro.c: Delete unnecessary function declarations.
	(buffer_and_nest): Support multiple labels per line for
	LABELS_WITHOUT_COLONS targets if the labels do have colons.
	(free_macro): Move so that we don't need forward declaration.
	* read.c (read_a_source_file): Take a copy of macro expansion line
	before we trim labels.
	* listing.c (listing_newline): Adjust stdin line save for
	input_line_pointer still at start of line.

gas/testsuite/
	PR gas/1491
	* gas/macros/dot.s: Don't start macro invocations is first column.
	* gas/macros/dot.l: Update.
	* gas/macros/macros.exp: Run dot test on more targets.

Index: gas/macro.c
===================================================================
RCS file: /cvs/src/src/gas/macro.c,v
retrieving revision 1.49
diff -u -p -r1.49 macro.c
--- gas/macro.c	11 Sep 2009 15:27:33 -0000	1.49
+++ gas/macro.c	15 Oct 2009 05:32:11 -0000
@@ -30,21 +30,6 @@
 /* The routines in this file handle macro definition and expansion.
    They are called by gas.  */
 
-/* Internal functions.  */
-
-static int get_token (int, sb *, sb *);
-static int getstring (int, sb *, sb *);
-static int get_any_string (int, sb *, sb *);
-static formal_entry *new_formal (void);
-static void del_formal (formal_entry *);
-static int do_formals (macro_entry *, int, sb *);
-static int get_apost_token (int, sb *, sb *, int);
-static int sub_actual (int, sb *, sb *, struct hash_control *, int, sb *, int);
-static const char *macro_expand_body
-  (sb *, sb *, formal_entry *, struct hash_control *, const macro_entry *);
-static const char *macro_expand (int, sb *, macro_entry *, sb *);
-static void free_macro(macro_entry *);
-
 #define ISWHITE(x) ((x) == ' ' || (x) == '\t')
 
 #define ISSEP(x) \
@@ -146,6 +131,7 @@ buffer_and_nest (const char *from, const
     {
       /* Try to find the first pseudo op on the line.  */
       int i = line_start;
+      bfd_boolean had_colon = FALSE;
 
       /* With normal syntax we can suck what we want till we get
 	 to the dot.  With the alternate, labels have to start in
@@ -169,19 +155,24 @@ buffer_and_nest (const char *from, const
 	    i++;
 	  if (i < ptr->len && is_name_ender (ptr->ptr[i]))
 	    i++;
-	  if (LABELS_WITHOUT_COLONS)
-	    break;
 	  /* Skip whitespace.  */
 	  while (i < ptr->len && ISWHITE (ptr->ptr[i]))
 	    i++;
 	  /* Check for the colon.  */
 	  if (i >= ptr->len || ptr->ptr[i] != ':')
 	    {
+	      /* LABELS_WITHOUT_COLONS doesn't mean we cannot have a
+		 colon after a label.  If we do have a colon on the
+		 first label then handle more than one label on the
+		 line, assuming that each label has a colon.  */
+	      if (LABELS_WITHOUT_COLONS && !had_colon)
+		break;
 	      i = line_start;
 	      break;
 	    }
 	  i++;
 	  line_start = i;
+	  had_colon = TRUE;
 	}
 
       /* Skip trailing whitespace.  */
@@ -606,6 +597,26 @@ do_formals (macro_entry *macro, int idx,
   return idx;
 }
 
+/* Free the memory allocated to a macro.  */
+
+static void
+free_macro (macro_entry *macro)
+{
+  formal_entry *formal;
+
+  for (formal = macro->formals; formal; )
+    {
+      formal_entry *f;
+
+      f = formal;
+      formal = formal->next;
+      del_formal (f);
+    }
+  hash_die (macro->formal_hash);
+  sb_kill (&macro->sub);
+  free (macro);
+}
+
 /* Define a new macro.  Returns NULL on success, otherwise returns an
    error message.  If NAMEP is not NULL, *NAMEP is set to the name of
    the macro which was defined.  */
@@ -1235,26 +1246,6 @@ check_macro (const char *line, sb *expan
   return 1;
 }
 
-/* Free the memory allocated to a macro.  */
-
-static void
-free_macro(macro_entry *macro)
-{
-  formal_entry *formal;
-
-  for (formal = macro->formals; formal; )
-    {
-      formal_entry *f;
-
-      f = formal;
-      formal = formal->next;
-      del_formal (f);
-    }
-  hash_die (macro->formal_hash);
-  sb_kill (&macro->sub);
-  free (macro);
-}
-
 /* Delete a macro.  */
 
 void
Index: gas/read.c
===================================================================
RCS file: /cvs/src/src/gas/read.c,v
retrieving revision 1.157
diff -u -p -r1.157 read.c
--- gas/read.c	5 Oct 2009 21:57:12 -0000	1.157
+++ gas/read.c	15 Oct 2009 10:34:00 -0000
@@ -620,19 +620,57 @@ read_a_source_file (char *name)
 #endif
       while (input_line_pointer < buffer_limit)
 	{
+	  bfd_boolean was_new_line;
 	  /* We have more of this buffer to parse.  */
 
 	  /* We now have input_line_pointer->1st char of next line.
 	     If input_line_pointer [-1] == '\n' then we just
 	     scanned another line: so bump line counters.  */
-	  if (is_end_of_line[(unsigned char) input_line_pointer[-1]])
+	  was_new_line = is_end_of_line[(unsigned char) input_line_pointer[-1]];
+	  if (was_new_line)
 	    {
 #ifdef md_start_line_hook
 	      md_start_line_hook ();
 #endif
 	      if (input_line_pointer[-1] == '\n')
 		bump_line_counters ();
+	    }
 
+#ifndef NO_LISTING
+	  /* If listing is on, and we are expanding a macro, then give
+	     the listing code the contents of the expanded line.  */
+	  if (listing)
+	    {
+	      if ((listing & LISTING_MACEXP) && macro_nest > 0)
+		{
+		  /* Find the end of the current expanded macro line.  */
+		  s = find_end_of_line (input_line_pointer, flag_m68k_mri);
+
+		  if (s != last_eol)
+		    {
+		      char *copy;
+		      int len;
+
+		      last_eol = s;
+		      /* Copy it for safe keeping.  Also give an indication of
+			 how much macro nesting is involved at this point.  */
+		      len = s - input_line_pointer;
+		      copy = (char *) xmalloc (len + macro_nest + 2);
+		      memset (copy, '>', macro_nest);
+		      copy[macro_nest] = ' ';
+		      memcpy (copy + macro_nest + 1, input_line_pointer, len);
+		      copy[macro_nest + 1 + len] = '\0';
+
+		      /* Install the line with the listing facility.  */
+		      listing_newline (copy);
+		    }
+		}
+	      else
+		listing_newline (NULL);
+	    }
+#endif
+	  if (was_new_line)
+	    {
 	      line_label = NULL;
 
 	      if (LABELS_WITHOUT_COLONS || flag_m68k_mri)
@@ -645,7 +683,6 @@ read_a_source_file (char *name)
 		      char c;
 		      int mri_line_macro;
 
-		      LISTING_NEWLINE ();
 		      HANDLE_CONDITIONAL_ASSEMBLY ();
 
 		      c = get_symbol_end ();
@@ -712,39 +749,6 @@ read_a_source_file (char *name)
 	    c = *input_line_pointer++;
 	  while (c == '\t' || c == ' ' || c == '\f');
 
-#ifndef NO_LISTING
-	  /* If listing is on, and we are expanding a macro, then give
-	     the listing code the contents of the expanded line.  */
-	  if (listing)
-	    {
-	      if ((listing & LISTING_MACEXP) && macro_nest > 0)
-		{
-		  char *copy;
-		  int len;
-
-		  /* Find the end of the current expanded macro line.  */
-		  s = find_end_of_line (input_line_pointer - 1, flag_m68k_mri);
-
-		  if (s != last_eol)
-		    {
-		      last_eol = s;
-		      /* Copy it for safe keeping.  Also give an indication of
-			 how much macro nesting is involved at this point.  */
-		      len = s - (input_line_pointer - 1);
-		      copy = (char *) xmalloc (len + macro_nest + 2);
-		      memset (copy, '>', macro_nest);
-		      copy[macro_nest] = ' ';
-		      memcpy (copy + macro_nest + 1, input_line_pointer - 1, len);
-		      copy[macro_nest + 1 + len] = '\0';
-
-		      /* Install the line with the listing facility.  */
-		      listing_newline (copy);
-		    }
-		}
-	      else
-		listing_newline (NULL);
-	    }
-#endif
 	  /* C is the 1st significant character.
 	     Input_line_pointer points after that character.  */
 	  if (is_name_beginner (c))
Index: gas/listing.c
===================================================================
RCS file: /cvs/src/src/gas/listing.c,v
retrieving revision 1.42
diff -u -p -r1.42 listing.c
--- gas/listing.c	11 Sep 2009 15:27:33 -0000	1.42
+++ gas/listing.c	15 Oct 2009 10:44:28 -0000
@@ -342,7 +342,7 @@ listing_newline (char *ps)
 	  int seen_quote = 0;
 	  int seen_slash = 0;
 
-	  for (copy = input_line_pointer - 1;
+	  for (copy = input_line_pointer;
 	       *copy && (seen_quote
 			 || is_end_of_line [(unsigned char) *copy] != 1);
 	       copy++)
@@ -353,13 +353,13 @@ listing_newline (char *ps)
 		seen_quote = ! seen_quote;
 	    }
 
-	  len = (copy - input_line_pointer) + 2;
+	  len = copy - input_line_pointer + 1;
 
 	  copy = (char *) xmalloc (len);
 
 	  if (copy != NULL)
 	    {
-	      char *src = input_line_pointer - 1;
+	      char *src = input_line_pointer;
 	      char *dest = copy;
 
 	      while (--len)
Index: gas/testsuite/gas/macros/dot.l
===================================================================
RCS file: /cvs/src/src/gas/testsuite/gas/macros/dot.l,v
retrieving revision 1.2
diff -u -p -r1.2 dot.l
--- gas/testsuite/gas/macros/dot.l	6 May 2005 06:30:33 -0000	1.2
+++ gas/testsuite/gas/macros/dot.l	15 Oct 2009 09:48:27 -0000
@@ -4,16 +4,16 @@
 .*:28: Error: .*
 #...
 [ 	]*[1-9][0-9]*[ 	]+m 4, 2
-[ 	]*[1-9][0-9]*[ 	]+> \.data
+[ 	]*[1-9][0-9]*[ 	]+>  \.data
 [ 	]*[1-9][0-9]*[ 	]+> labelA:labelB:labelC:labelD:x\.y\.z 4\+2
-[ 	]*[1-9][0-9]*[ 	]+>> \.align 4
-[ 	]*[1-9][0-9]*[ 	]+\?+[ 	]+0606[ 	]+>> \.byte 4\+2,4\+2
-[ 	]*[1-9][0-9]*[ 	]+\?+[ 	]+0000[ 	]+> \.skip 2
+[ 	]*[1-9][0-9]*[ 	]+>>  \.align 4
+[ 	]*[1-9][0-9]*[ 	]+\?+[ 	]+06 ?06[ 	]+>>  \.byte 4\+2,4\+2
+[ 	]*[1-9][0-9]*[ 	]+\?+[ 	]+00 ?00[ 	]+>  \.skip 2
 [ 	]*[1-9][0-9]*[ 	]+> labelZ:labelY:labelX:labelW:\.xyz 4-2
-[ 	]*[1-9][0-9]*[ 	]+>> \.align 8
-[ 	]*[1-9][0-9]*[ 	]+\?+[ 	]+0202[ 	]+>> \.byte 4-2,4-2
-[ 	]*[1-9][0-9]*[ 	]+\?+[ 	]+0000 ?0000[ 	]+> \.skip 4\*2
-[ 	]*[1-9][0-9]*[ 	]+0000 ?0000[ 	]*
+[ 	]*[1-9][0-9]*[ 	]+>>  \.align 8
+[ 	]*[1-9][0-9]*[ 	]+\?+[ 	]+02 ?02[ 	]+>>  \.byte 4-2,4-2
+[ 	]*[1-9][0-9]*[ 	]+\?+[ 	]+00 ?00 ?00 ?00[ 	]+>  \.skip 4\*2
+[ 	]*[1-9][0-9]*[ 	]+00 ?00 ?00 ?00[ 	]*
 [ 	]*[1-9][0-9]*[ 	]+> label9:label8:label7:label6:
 [ 	]*[1-9][0-9]*[ 	]+
 [ 	]*[1-9][0-9]*[ 	]+\.purgem \.xyz, x\.y\.z
Index: gas/testsuite/gas/macros/dot.s
===================================================================
RCS file: /cvs/src/src/gas/testsuite/gas/macros/dot.s,v
retrieving revision 1.2
diff -u -p -r1.2 dot.s
--- gas/testsuite/gas/macros/dot.s	6 May 2005 06:30:33 -0000	1.2
+++ gas/testsuite/gas/macros/dot.s	15 Oct 2009 09:48:27 -0000
@@ -21,8 +21,8 @@ labelZ:labelY : labelX :labelW: .xyz arg
  .skip arg.1*arg.2
 label9:label8 : label7 :label6: .endm
 
-m 4, 2
+ m 4, 2
 
  .purgem .xyz, x.y.z
  .xyz 0
-x.y.z 0
+ x.y.z 0
Index: gas/testsuite/gas/macros/macros.exp
===================================================================
RCS file: /cvs/src/src/gas/testsuite/gas/macros/macros.exp,v
retrieving revision 1.30
diff -u -p -r1.30 macros.exp
--- gas/testsuite/gas/macros/macros.exp	29 Sep 2009 14:17:10 -0000	1.30
+++ gas/testsuite/gas/macros/macros.exp	15 Oct 2009 10:01:52 -0000
@@ -61,12 +61,8 @@ run_list_test badarg ""
 case $target_triplet in {
     { *c54x*-*-* } { }
     { *c4x*-*-* } { }
-    { h8500-*-* } { }
-    { m68*-*-* } { }
-    { m88*-*-* } { }
     { mmix-* } { }
     { rx-*-* } { }
-    { z80-* } { }
     default { run_list_test dot "-alm" }
 }
 run_list_test end ""

-- 
Alan Modra
Australia Development Lab, IBM


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