From 835d684f69ec156d52acd654463203ff299e273f Mon Sep 17 00:00:00 2001
From: David Malcolm <dmalcolm@redhat.com>
Date: Thu, 9 Jan 2014 09:37:59 -0500
Subject: [PATCH 109/159] FIXME: add rtx_expr_list

---
 gcc/coretypes.h |  6 ++++++
 gcc/emit-rtl.c  |  7 +++++++
 gcc/gengenrtl.c |  3 ++-
 gcc/rtl.h       | 44 ++++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 59 insertions(+), 1 deletion(-)

diff --git a/gcc/coretypes.h b/gcc/coretypes.h
index 477d9f5..c60c452 100644
--- a/gcc/coretypes.h
+++ b/gcc/coretypes.h
@@ -57,6 +57,8 @@ typedef const struct simple_bitmap_def *const_sbitmap;
 
    The underlying class hierarchy looks like this:
       -+-rtx (any kind of expression)
+	  |-rtx_expr_list (a node within an externally singly-linked list of
+	  |                rtx)
 	  |-rtx_insn_list (a node within an externally singly-linked list of
 	  |                rtx_base_insn)
 	  |-rtx_sequence (a vector of rtx, used in the late passes)
@@ -84,6 +86,10 @@ struct rtvec_def;
 typedef struct rtvec_def *rtvec;
 typedef const struct rtvec_def *const_rtvec;
 
+struct rtx_expr_list_def;
+typedef struct rtx_expr_list_def *rtx_expr_list;
+typedef const struct rtx_expr_list_def *const_rtx_expr_list;
+
 struct rtx_insn_list_def;
 typedef struct rtx_insn_list_def *rtx_insn_list;
 typedef const struct rtx_insn_list_def *const_rtx_insn_list;
diff --git a/gcc/emit-rtl.c b/gcc/emit-rtl.c
index 6124355..d487aaf 100644
--- a/gcc/emit-rtl.c
+++ b/gcc/emit-rtl.c
@@ -394,6 +394,13 @@ gen_raw_REG (enum machine_mode mode, int regno)
    functions do the raw handling.  If you add to this list, modify
    special_rtx in gengenrtl.c as well.  */
 
+rtx_expr_list
+gen_rtx_EXPR_LIST (enum machine_mode mode, rtx expr, rtx expr_list)
+{
+  return gen_rtx_fmt_ee (EXPR_LIST, mode, expr,
+			 expr_list)->as_an_rtx_expr_list ();
+}
+
 rtx_insn_list
 gen_rtx_INSN_LIST (enum machine_mode mode, rtx insn, rtx insn_list)
 {
diff --git a/gcc/gengenrtl.c b/gcc/gengenrtl.c
index caca702..a9d149d 100644
--- a/gcc/gengenrtl.c
+++ b/gcc/gengenrtl.c
@@ -123,7 +123,8 @@ special_format (const char *fmt)
 static int
 special_rtx (int idx)
 {
-  return (strcmp (defs[idx].enumname, "INSN_LIST") == 0
+  return (strcmp (defs[idx].enumname, "EXPR_LIST") == 0
+	  || strcmp (defs[idx].enumname, "INSN_LIST") == 0
 	  || strcmp (defs[idx].enumname, "CONST_INT") == 0
 	  || strcmp (defs[idx].enumname, "REG") == 0
 	  || strcmp (defs[idx].enumname, "SUBREG") == 0
diff --git a/gcc/rtl.h b/gcc/rtl.h
index cd37539..2cf4c2c 100644
--- a/gcc/rtl.h
+++ b/gcc/rtl.h
@@ -371,6 +371,12 @@ public:
      Keep these in the same order as the corresponding DEF_RTL_EXPR within
      rtl.def.  */
 
+  inline rtx_expr_list
+  as_an_rtx_expr_list ()
+  {
+    return as_a <rtx_expr_list_def> (this);
+  }
+
   inline rtx_insn_list
   as_an_rtx_insn_list ()
   {
@@ -459,6 +465,29 @@ public:
   inline void set_next_insn (rtx new_next);
 };
 
+/* A node for constructing singly-linked lists of rtx.  */
+
+struct GTY(()) rtx_expr_list_def : public rtx_def
+{
+  /* No extra fields, but adds invariant: (GET_CODE (X) == EXPR_LIST).  */
+
+public:
+  /* Get next in list.  */
+  rtx_expr_list next () const;
+
+  /* Get at the underlying rtx.  */
+  rtx element () const;
+
+};
+
+template <>
+template <>
+inline bool
+is_a_helper <rtx_expr_list_def>::test (rtx rt)
+{
+  return rt->code == EXPR_LIST;
+}
+
 /* A node for constructing singly-linked lists of rtx_base_insn,
    where the list is "external" to the insn (as opposed to the
    doubly-linked list embedded within rtx_base_insn itself).  */
@@ -1166,6 +1195,20 @@ extern void rtl_check_failed_flag (const char *, const_rtx, const char *,
 #define XC2EXP(RTX, N, C1, C2)      (RTL_CHECKC2 (RTX, N, C1, C2).rt_rtx)
 
 
+inline rtx_expr_list rtx_expr_list_def::next () const
+{
+  rtx tmp = XEXP (this, 1);
+  if (tmp)
+    return tmp->as_an_rtx_expr_list ();
+  else
+    return NULL;
+}
+
+inline rtx rtx_expr_list_def::element () const
+{
+  return XEXP (this, 0);
+}
+
 inline rtx_insn_list rtx_insn_list_def::next () const
 {
   rtx tmp = XEXP (this, 1);
@@ -2777,6 +2820,7 @@ get_mem_attrs (const_rtx x)
    generation functions included above do the raw handling.  If you
    add to this list, modify special_rtx in gengenrtl.c as well.  */
 
+extern rtx_expr_list gen_rtx_EXPR_LIST (enum machine_mode, rtx, rtx);
 extern rtx_insn_list gen_rtx_INSN_LIST (enum machine_mode, rtx, rtx);
 extern rtx gen_rtx_CONST_INT (enum machine_mode, HOST_WIDE_INT);
 extern rtx gen_rtx_CONST_VECTOR (enum machine_mode, rtvec);
-- 
1.7.11.7

