From f90425b2bdc0184a5f7b96e222b9091ad2727b0c Mon Sep 17 00:00:00 2001
From: David Malcolm <dmalcolm@redhat.com>
Date: Tue, 4 Oct 2016 12:51:50 -0400
Subject: [PATCH 11/44] Split class rtx_reader into base_rtx_reader vs
 rtx_reader

This moves read_rtx and friends into rtx_reader, and splits
rtx_reader into two classes:

class base_rtx_reader: has responsibility for reading chars, managing
include files, top-level directives etc.  It is the read-md.o part.

class rtx_reader, a subclass, has the code for reading hierarchical
rtx expressions using the format codes.   It is the read-rtl.o part.

This split is needed by a followup patch, which converts
read_rtx_operand to a virtual function of rtx_reader.  To do this,
instances of rtx_reader (or its subclasses) need a vtable, which
needs to include a ptr to the code in read-rtl.o.  Splitting it up
allows the gen* tools that currently purely use read-md.o to continue
to do so.

gcc/ChangeLog:
	* genpreds.c (write_tm_constrs_h): Update for renaming of
	rtx_reader_ptr to base_rtx_reader_ptr.
	(write_tm_preds_h): Likewise.
	(write_insn_preds_c): Likewise.
	* read-md.c (rtx_reader_ptr): Rename to...
	(base_rtx_reader_ptr): ...this, and convert
	from an rtx_reader * to a base_rtx_reader *.
	(fatal_with_file_and_line): Update for renaming of
	rtx_reader_ptr to base_rtx_reader_ptr.
	(rtx_reader::read_char): Rename to...
	(base_rtx_reader::read_char):... this.
	(rtx_reader::unread_char): Rename to...
	(base_rtx_reader::unread_char):... this.
	(read_escape): Update for renaming of rtx_reader_ptr to
	base_rtx_reader_ptr.
	(read_braced_string): Likewise.
	(read_string): Likewise.
	(rtx_reader::rtx_reader): Rename to...
	(base_rtx_reader::base_rtx_reader): ...this, and update for
	renaming of rtx_reader_ptr to base_rtx_reader_ptr.
	(rtx_reader::~rtx_reader): Rename to...
	(base_rtx_reader::~base_rtx_reader): ...this, and update for
	renaming of rtx_reader_ptr to base_rtx_reader_ptr.
	(rtx_reader::handle_include): Rename to...
	(base_rtx_reader::handle_include): ...this.
	(rtx_reader::handle_file): Rename to...
	(base_rtx_reader::handle_file): ...this.
	(rtx_reader::handle_toplevel_file): Rename to...
	(base_rtx_reader::handle_toplevel_file): ...this.
	(rtx_reader::get_current_location): Rename to...
	(base_rtx_reader::get_current_location): ...this.
	(rtx_reader::add_include_path): Rename to...
	(base_rtx_reader::add_include_path): ...this.
	(rtx_reader::read_md_files): Rename to...
	(base_rtx_reader::read_md_files): ...this.
	* read-md.h (struct enum_type {): Likewise.
	(class rtx_reader): Split into...
	(class base_rtx_reader): ...new class.
	(rtx_reader_ptr): Rename to...
	(base_rtx_reader_ptr): ...this, and convert to a
	base_rtx_reader *.
	(class noop_reader): Update base class to be base_rtx_reader.
	(class rtx_reader): Reintroduce as a subclass of base_rtx_reader.
	(rtx_reader_ptr): Reintroduce as a rtx_reader *.
	(read_char): Update for renaming of rtx_reader_ptr to
	base_rtx_reader_ptr.
	(unread_char): Likewise.
	* read-rtl.c (rtx_reader_ptr): New global.
	(read_rtx): Use rtx_reader_ptr when calling read_rtx_code.
	(read_rtx_code): Convert to...
	(rtx_reader::read_rtx_code): ...this method.
	(read_rtx_operand): Convert to...
	(rtx_reader::read_rtx_operand): ...this method, eliminating use of
	rtx_reader_ptr singleton.  Convert return type from void to rtx,
	and return input.
	(read_nested_rtx): Convert to...
	(rtx_reader::read_nested_rtx): ...this method.
	(read_rtx_variadic): Convert to...
	(rtx_reader::read_rtx_variadic): ...this method.
	(rtx_reader::rtx_reader): New ctor.
	(rtx_reader::~rtx_reader): New dtor.
---
 gcc/genpreds.c |  6 +++---
 gcc/read-md.c  | 54 ++++++++++++++++++++++++++++--------------------------
 gcc/read-md.h  | 53 +++++++++++++++++++++++++++++++++++++++++++----------
 gcc/read-rtl.c | 48 +++++++++++++++++++++++++++++++++---------------
 4 files changed, 107 insertions(+), 54 deletions(-)

diff --git a/gcc/genpreds.c b/gcc/genpreds.c
index 6db1b7b..a9092da 100644
--- a/gcc/genpreds.c
+++ b/gcc/genpreds.c
@@ -1205,7 +1205,7 @@ write_tm_constrs_h (void)
   printf ("\
 /* Generated automatically by the program '%s'\n\
    from the machine description file '%s'.  */\n\n", progname,
-	  rtx_reader_ptr->get_top_level_filename ());
+	  base_rtx_reader_ptr->get_top_level_filename ());
 
   puts ("\
 #ifndef GCC_TM_CONSTRS_H\n\
@@ -1405,7 +1405,7 @@ write_tm_preds_h (void)
   printf ("\
 /* Generated automatically by the program '%s'\n\
    from the machine description file '%s'.  */\n\n", progname,
-	  rtx_reader_ptr->get_top_level_filename ());
+	  base_rtx_reader_ptr->get_top_level_filename ());
 
   puts ("\
 #ifndef GCC_TM_PREDS_H\n\
@@ -1555,7 +1555,7 @@ write_insn_preds_c (void)
   printf ("\
 /* Generated automatically by the program '%s'\n\
    from the machine description file '%s'.  */\n\n", progname,
-	  rtx_reader_ptr->get_top_level_filename ());
+	  base_rtx_reader_ptr->get_top_level_filename ());
 
   puts ("\
 #include \"config.h\"\n\
diff --git a/gcc/read-md.c b/gcc/read-md.c
index 1bbf408..9ffdb8e 100644
--- a/gcc/read-md.c
+++ b/gcc/read-md.c
@@ -56,7 +56,7 @@ void (*include_callback) (const char *);
 
 /* Global singleton.  */
 
-rtx_reader *rtx_reader_ptr;
+base_rtx_reader *base_rtx_reader_ptr;
 
 /* A table of md_constant structures, hashed by name.  Null if no
    constant expansion should occur.  */
@@ -274,8 +274,9 @@ fatal_with_file_and_line (const char *msg, ...)
 
   va_start (ap, msg);
 
-  fprintf (stderr, "%s:%d:%d: error: ", rtx_reader_ptr->get_filename (),
-	   rtx_reader_ptr->get_lineno (), rtx_reader_ptr->get_colno ());
+  fprintf (stderr, "%s:%d:%d: error: ", base_rtx_reader_ptr->get_filename (),
+	   base_rtx_reader_ptr->get_lineno (),
+	   base_rtx_reader_ptr->get_colno ());
   vfprintf (stderr, msg, ap);
   putc ('\n', stderr);
 
@@ -295,8 +296,9 @@ fatal_with_file_and_line (const char *msg, ...)
   context[i] = '\0';
 
   fprintf (stderr, "%s:%d:%d: note: following context is `%s'\n",
-	   rtx_reader_ptr->get_filename (), rtx_reader_ptr->get_lineno (),
-	   rtx_reader_ptr->get_colno (), context);
+	   base_rtx_reader_ptr->get_filename (),
+	   base_rtx_reader_ptr->get_lineno (),
+	   base_rtx_reader_ptr->get_colno (), context);
 
   va_end (ap);
   exit (1);
@@ -399,7 +401,7 @@ void require_word_ws (const char *expected)
 /* Read the next character from the file.  */
 
 int
-rtx_reader::read_char (void)
+base_rtx_reader::read_char (void)
 {
   int ch;
 
@@ -419,7 +421,7 @@ rtx_reader::read_char (void)
 /* Put back CH, which was the last character read from the file.  */
 
 void
-rtx_reader::unread_char (int ch)
+base_rtx_reader::unread_char (int ch)
 {
   if (ch == '\n')
     {
@@ -551,8 +553,8 @@ read_escape (void)
       /* pass anything else through, but issue a warning.  */
     default:
       fprintf (stderr, "%s:%d: warning: unrecognized escape \\%c\n",
-	       rtx_reader_ptr->get_filename (), rtx_reader_ptr->get_lineno (),
-	       c);
+	       base_rtx_reader_ptr->get_filename (),
+	       base_rtx_reader_ptr->get_lineno (), c);
       obstack_1grow (&string_obstack, '\\');
       break;
     }
@@ -595,7 +597,7 @@ read_braced_string (void)
 {
   int c;
   int brace_depth = 1;  /* caller-processed */
-  unsigned long starting_read_md_lineno = rtx_reader_ptr->get_lineno ();
+  unsigned long starting_read_md_lineno = base_rtx_reader_ptr->get_lineno ();
 
   obstack_1grow (&string_obstack, '{');
   while (brace_depth)
@@ -641,7 +643,7 @@ read_string (int star_if_braced)
       c = read_skip_spaces ();
     }
 
-  old_lineno = rtx_reader_ptr->get_lineno ();
+  old_lineno = base_rtx_reader_ptr->get_lineno ();
   if (c == '"')
     stringbuf = read_quoted_string ();
   else if (c == '{')
@@ -656,7 +658,7 @@ read_string (int star_if_braced)
   if (saw_paren)
     require_char_ws (')');
 
-  set_md_ptr_loc (stringbuf, rtx_reader_ptr->get_filename (), old_lineno);
+  set_md_ptr_loc (stringbuf, base_rtx_reader_ptr->get_filename (), old_lineno);
   return stringbuf;
 }
 
@@ -942,9 +944,9 @@ traverse_enum_types (htab_trav callback, void *info)
 }
 
 
-/* Constructor for rtx_reader.  */
+/* Constructor for base_rtx_reader.  */
 
-rtx_reader::rtx_reader ()
+base_rtx_reader::base_rtx_reader ()
 : m_toplevel_fname (NULL),
   m_base_dir (NULL),
   m_read_md_file (NULL),
@@ -955,7 +957,7 @@ rtx_reader::rtx_reader ()
   m_last_dir_md_include_ptr (&m_first_dir_md_include)
 {
   /* Set the global singleton pointer.  */
-  rtx_reader_ptr = this;
+  base_rtx_reader_ptr = this;
 
   /* Initialize global data.  */
   obstack_init (&string_obstack);
@@ -972,9 +974,9 @@ rtx_reader::rtx_reader ()
   unlock_std_streams ();
 }
 
-/* rtx_reader's destructor.  */
+/* base_rtx_reader's destructor.  */
 
-rtx_reader::~rtx_reader ()
+base_rtx_reader::~base_rtx_reader ()
 {
   free (m_base_dir);
 
@@ -998,7 +1000,7 @@ rtx_reader::~rtx_reader ()
   obstack_free (&string_obstack, NULL);
 
   /* Clear the global singleton pointer.  */
-  rtx_reader_ptr = NULL;
+  base_rtx_reader_ptr = NULL;
 }
 
 /* Process an "include" directive, starting with the optional space
@@ -1007,7 +1009,7 @@ rtx_reader::~rtx_reader ()
    which the "include" occurred.  */
 
 void
-rtx_reader::handle_include (file_location loc)
+base_rtx_reader::handle_include (file_location loc)
 {
   const char *filename;
   const char *old_filename;
@@ -1085,7 +1087,7 @@ rtx_reader::handle_include (file_location loc)
    unknown directives.  */
 
 void
-rtx_reader::handle_file ()
+base_rtx_reader::handle_file ()
 {
   struct md_name directive;
   int c;
@@ -1119,7 +1121,7 @@ rtx_reader::handle_file ()
    and m_base_dir accordingly.  */
 
 void
-rtx_reader::handle_toplevel_file ()
+base_rtx_reader::handle_toplevel_file ()
 {
   const char *base;
 
@@ -1134,7 +1136,7 @@ rtx_reader::handle_toplevel_file ()
 }
 
 file_location
-rtx_reader::get_current_location () const
+base_rtx_reader::get_current_location () const
 {
   return file_location (m_read_md_filename, m_read_md_lineno, m_read_md_colno);
 }
@@ -1142,7 +1144,7 @@ rtx_reader::get_current_location () const
 /* Parse a -I option with argument ARG.  */
 
 void
-rtx_reader::add_include_path (const char *arg)
+base_rtx_reader::add_include_path (const char *arg)
 {
   struct file_name_list *dirtmp;
 
@@ -1163,8 +1165,8 @@ rtx_reader::add_include_path (const char *arg)
    generic error should be reported.  */
 
 bool
-rtx_reader::read_md_files (int argc, const char **argv,
-			   bool (*parse_opt) (const char *))
+base_rtx_reader::read_md_files (int argc, const char **argv,
+				bool (*parse_opt) (const char *))
 {
   int i;
   bool no_more_options;
@@ -1259,7 +1261,7 @@ rtx_reader::read_md_files (int argc, const char **argv,
   return !have_error;
 }
 
-/* class noop_reader : public rtx_reader */
+/* class noop_reader : public base_rtx_reader */
 
 /* A dummy implementation which skips unknown directives.  */
 void
diff --git a/gcc/read-md.h b/gcc/read-md.h
index 88d2d4f..0701f35 100644
--- a/gcc/read-md.h
+++ b/gcc/read-md.h
@@ -91,11 +91,23 @@ struct enum_type {
   unsigned int num_values;
 };
 
-class rtx_reader
+/* A class for reading .md files and RTL dump files.
+
+   Implemented in read-md.c.
+
+   This class has responsibility for reading chars from input files, and
+   for certain common top-level directives including the "include"
+   directive.
+
+   It does not handle parsing the hierarchically-nested expressions of
+   rtl.def; for that see the rtx_reader subclass below (implemented in
+   read-rtl.c).  */
+
+class base_rtx_reader
 {
  public:
-  rtx_reader ();
-  virtual ~rtx_reader ();
+  base_rtx_reader ();
+  virtual ~base_rtx_reader ();
 
   bool read_md_files (int, const char **, bool (*) (const char *));
 
@@ -161,20 +173,41 @@ class rtx_reader
   file_name_list **m_last_dir_md_include_ptr;
 };
 
-/* Global singleton.  */
-extern rtx_reader *rtx_reader_ptr;
+/* Global singleton; constrast with rtx_reader_ptr below.  */
+extern base_rtx_reader *base_rtx_reader_ptr;
 
-/* An rtx_reader subclass which skips unknown directives.  */
+/* A base_rtx_reader subclass which skips unknown directives, for
+   the gen* tools that purely use read-md.o.  */
 
-class noop_reader : public rtx_reader
+class noop_reader : public base_rtx_reader
 {
  public:
-  noop_reader () : rtx_reader () {}
+  noop_reader () : base_rtx_reader () {}
 
   /* A dummy implementation which skips unknown directives.  */
   void handle_unknown_directive (file_location, const char *);
 };
 
+/* A base_rtx_reader subclass that actually handles full hierarchical
+   rtx expressions.
+
+   Implemented in read-rtl.c.  */
+
+class rtx_reader : public base_rtx_reader
+{
+ public:
+  rtx_reader ();
+  ~rtx_reader ();
+
+  rtx read_rtx_code (const char *);
+  rtx read_rtx_operand (rtx return_rtx, int idx);
+  rtx read_nested_rtx (void);
+  rtx read_rtx_variadic (rtx);
+};
+
+/* Global singleton; constrast with base_rtx_reader_ptr above.  */
+extern rtx_reader *rtx_reader_ptr;
+
 extern struct obstack string_obstack;
 extern void (*include_callback) (const char *);
 
@@ -183,7 +216,7 @@ extern void (*include_callback) (const char *);
 static inline int
 read_char (void)
 {
-  return rtx_reader_ptr->read_char ();
+  return base_rtx_reader_ptr->read_char ();
 }
 
 /* Put back CH, which was the last character read from the MD file.  */
@@ -191,7 +224,7 @@ read_char (void)
 static inline void
 unread_char (int ch)
 {
-  rtx_reader_ptr->unread_char (ch);
+  base_rtx_reader_ptr->unread_char (ch);
 }
 
 extern int peek_char (void);
diff --git a/gcc/read-rtl.c b/gcc/read-rtl.c
index 925ea45..2622bfe 100644
--- a/gcc/read-rtl.c
+++ b/gcc/read-rtl.c
@@ -106,10 +106,9 @@ htab_t subst_attr_to_iter_map = NULL;
 const char *current_iterator_name;
 
 static void validate_const_int (const char *);
-static rtx read_rtx_code (const char *);
-static void read_rtx_operand (rtx, int);
-static rtx read_nested_rtx (void);
-static rtx read_rtx_variadic (rtx);
+
+/* Global singleton.  */
+rtx_reader *rtx_reader_ptr = NULL;
 
 /* The mode and code iterator structures.  */
 static struct iterator_group modes, codes, ints, substs;
@@ -1076,7 +1075,7 @@ read_rtx (const char *rtx_name, vec<rtx> *rtxen)
       return true;
     }
 
-  apply_iterators (read_rtx_code (rtx_name), rtxen);
+  apply_iterators (rtx_reader_ptr->read_rtx_code (rtx_name), rtxen);
   iterator_uses.truncate (0);
   attribute_uses.truncate (0);
 
@@ -1087,8 +1086,8 @@ read_rtx (const char *rtx_name, vec<rtx> *rtxen)
    either an rtx code or a code iterator.  Parse the rest of the rtx and
    return it.  */
 
-static rtx
-read_rtx_code (const char *code_name)
+rtx
+rtx_reader::read_rtx_code (const char *code_name)
 {
   RTX_CODE code;
   struct mapping *iterator;
@@ -1200,8 +1199,8 @@ read_rtx_code (const char *code_name)
    based on the corresponding format character within GET_RTX_FORMAT
    for the GET_CODE (RETURN_RTX).  */
 
-static void
-read_rtx_operand (rtx return_rtx, int idx)
+rtx
+rtx_reader::read_rtx_operand (rtx return_rtx, int idx)
 {
   RTX_CODE code = GET_CODE (return_rtx);
   const char *format_ptr = GET_RTX_FORMAT (code);
@@ -1304,7 +1303,7 @@ read_rtx_operand (rtx return_rtx, int idx)
 		|| GET_CODE (return_rtx) == DEFINE_INSN_AND_SPLIT))
 	  {
 	    char line_name[20];
-	    const char *read_md_filename = rtx_reader_ptr->get_filename ();
+	    const char *read_md_filename = get_filename ();
 	    const char *fn = (read_md_filename ? read_md_filename : "rtx");
 	    const char *slash;
 	    for (slash = fn; *slash; slash ++)
@@ -1312,7 +1311,7 @@ read_rtx_operand (rtx return_rtx, int idx)
 		fn = slash + 1;
 	    obstack_1grow (&string_obstack, '*');
 	    obstack_grow (&string_obstack, fn, strlen (fn));
-	    sprintf (line_name, ":%d", rtx_reader_ptr->get_lineno ());
+	    sprintf (line_name, ":%d", get_lineno ());
 	    obstack_grow (&string_obstack, line_name, strlen (line_name)+1);
 	    stringbuf = XOBFINISH (&string_obstack, char *);
 	  }
@@ -1398,12 +1397,14 @@ read_rtx_operand (rtx return_rtx, int idx)
     default:
       gcc_unreachable ();
     }
+
+  return return_rtx;
 }
 
 /* Read a nested rtx construct from the MD file and return it.  */
 
-static rtx
-read_nested_rtx (void)
+rtx
+rtx_reader::read_nested_rtx (void)
 {
   struct md_name name;
   rtx return_rtx;
@@ -1427,8 +1428,8 @@ read_nested_rtx (void)
    When called, FORM is (thing x1 x2), and the file position
    is just past the leading parenthesis of x3.  Only works
    for THINGs which are dyadic expressions, e.g. AND, IOR.  */
-static rtx
-read_rtx_variadic (rtx form)
+rtx
+rtx_reader::read_rtx_variadic (rtx form)
 {
   char c = '(';
   rtx p = form, q;
@@ -1451,3 +1452,20 @@ read_rtx_variadic (rtx form)
   unread_char (c);
   return form;
 }
+
+/* Constructor for class rtx_reader.  */
+
+rtx_reader::rtx_reader ()
+: base_rtx_reader ()
+{
+  /* Set the global singleton pointer.  */
+  rtx_reader_ptr = this;
+}
+
+/* Destructor for class rtx_reader.  */
+
+rtx_reader::~rtx_reader ()
+{
+  /* Clear the global singleton pointer.  */
+  rtx_reader_ptr = NULL;
+}
-- 
1.8.5.3

