From e9fc6c21007f3530d73cc4ba4983dc9f118af219 Mon Sep 17 00:00:00 2001
From: Alexandre Oliva <aoliva@redhat.com>
Date: Fri, 9 Mar 2007 23:25:59 +0000
Subject: [PATCH] * app.c (do_scrub_chars): Recognize comments after # line
 "file". * read.c (get_linefile_number): New. (s_app_line): Accept ill-formed
 .linefile lines as comments.

---
 gas/ChangeLog |  6 ++++++
 gas/app.c     | 14 ++------------
 gas/read.c    | 49 +++++++++++++++++++++++++++++++++++++++++--------
 3 files changed, 49 insertions(+), 20 deletions(-)

diff --git a/gas/ChangeLog b/gas/ChangeLog
index 2c3acbf7273..bd41e3a18bf 100644
--- a/gas/ChangeLog
+++ b/gas/ChangeLog
@@ -1,3 +1,9 @@
+2007-03-09  Alexandre Oliva  <aoliva@redhat.com>
+
+	* app.c (do_scrub_chars): Recognize comments after # line "file".
+	* read.c (get_linefile_number): New.
+	(s_app_line): Accept ill-formed .linefile lines as comments.
+
 2007-03-09  Alan Modra  <amodra@bigpond.net.au>
 
 	* config/tc-i386.h (WORKING_DOT_WORD): Define.
diff --git a/gas/app.c b/gas/app.c
index e6b39d61213..dc08f835235 100644
--- a/gas/app.c
+++ b/gas/app.c
@@ -355,7 +355,7 @@ do_scrub_chars (int (*get) (char *, int), char *tostart, int tolen)
 	  5: parsing a string, then go to old-state
 	  6: putting out \ escape in a "d string.
 	  7: no longer used
-	  8: After putting out a .appfile string, flush until newline.
+	  8: no longer used
 	  9: After seeing symbol char in state 3 (keep 1white after symchar)
 	 10: After seeing whitespace in state 9 (keep white before symchar)
 	 11: After seeing a symbol character in state 0 (eg a label definition)
@@ -514,7 +514,7 @@ do_scrub_chars (int (*get) (char *, int), char *tostart, int tolen)
 		  PUT (ch);
 		  quotechar = ch;
 		  state = 5;
-		  old_state = 8;
+		  old_state = 3;
 		}
 	      else
 		{
@@ -635,16 +635,6 @@ do_scrub_chars (int (*get) (char *, int), char *tostart, int tolen)
 	  PUT (ch);
 	  continue;
 
-	case 8:
-	  do
-	    if ((ch = GET ()) == EOF)
-	      goto fromeof;
-	    else
-	      PUT (ch);
-	  while (ch != '\n');
-	  state = 0;
-	  continue;
-
 #ifdef DOUBLEBAR_PARALLEL
 	case 13:
 	  ch = GET ();
diff --git a/gas/read.c b/gas/read.c
index 97a2ab26ec8..c622eb26068 100644
--- a/gas/read.c
+++ b/gas/read.c
@@ -1698,6 +1698,19 @@ s_app_file (int appfile)
     }
 }
 
+static int
+get_linefile_number (int *flag)
+{
+  SKIP_WHITESPACE ();
+
+  if (*input_line_pointer < '0' || *input_line_pointer > '9')
+    return 0;
+
+  *flag = get_absolute_expression ();
+
+  return 1;
+}
+
 /* Handle the .appline pseudo-op.  This is automatically generated by
    do_scrub_chars when a preprocessor # line comment is seen.  This
    default definition may be overridden by the object or CPU specific
@@ -1706,10 +1719,19 @@ s_app_file (int appfile)
 void
 s_app_line (int appline)
 {
+  char *file = NULL;
   int l;
 
   /* The given number is that of the next line.  */
-  l = get_absolute_expression () - 1;
+  if (appline)
+    l = get_absolute_expression ();
+  else if (!get_linefile_number (&l))
+    {
+      ignore_rest_of_line ();
+      return;
+    }
+
+  l--;
 
   if (l < -1)
     /* Some of the back ends can't deal with non-positive line numbers.
@@ -1726,18 +1748,20 @@ s_app_line (int appline)
   else
     {
       int flags = 0;
-      char *file = NULL;
       int length = 0;
 
       if (!appline)
 	{
-	  file = demand_copy_string (&length);
+	  SKIP_WHITESPACE ();
+
+	  if (*input_line_pointer == '"')
+	    file = demand_copy_string (&length);
 
 	  if (file)
 	    {
 	      int this_flag;
 
-	      while ((this_flag = get_absolute_expression ()))
+	      while (get_linefile_number (&this_flag))
 		switch (this_flag)
 		  {
 		    /* From GCC's cpp documentation:
@@ -1772,16 +1796,25 @@ s_app_line (int appline)
 			     this_flag);
 		    break;
 		  }
+
+	      if (!is_end_of_line[(unsigned char)*input_line_pointer])
+		file = 0;
 	    }
 	}
 
-      new_logical_line_flags (file, l, flags);
+      if (appline || file)
+	{
+	  new_logical_line_flags (file, l, flags);
 #ifdef LISTING
-      if (listing)
-	listing_source_line (l);
+	  if (listing)
+	    listing_source_line (l);
 #endif
+	}
     }
-  demand_empty_rest_of_line ();
+  if (appline || file)
+    demand_empty_rest_of_line ();
+  else
+    ignore_rest_of_line ();
 }
 
 /* Handle the .end pseudo-op.  Actually, the real work is done in