The following adds parsing of clobbers to the GIMPLE FE.  Rather
than parsing { CLOBBER [(bob|bos|eob|eos)] } with the CLOBBER
identifier uglified I've changed this to __CLOBBER [ (bob|bos|eob|eos) ]
which also does not expose the CONSTRUCTOR implementation detail.
The type of the clobber is infered from the LHS.

Parsing of {v} in the assignment is not implemented as part of this
and it should not be necessary as it's infered from the LHS/RHS
by the operand scanner (so it's redundant info).  It's still
printed with -gimple dumping.

I hope to eventually switch non -gimple dumping to the -gimple
dumping syntax for some bits like __MEM dumping and this would
also be a candidate.

Bootstrapped on x86_64-unknown-linux-gnu, testing in progress.

Any comments?

Thanks,
Richard.

gcc/c/
        * gimple-parser.cc (c_parser_gimple_postfix_expression):
        Add ret_type argument, defaulted to error_mark_node.
        Add parsing of __CLOBBER.
        (c_parser_gimple_binary_expression): Pass ret_type down to
        c_parser_gimple_postfix_expression.

gcc/testsuite/
        * gcc.dg/gimplefe-60.c: New testcase.
---
 gcc/c/gimple-parser.cc             | 39 +++++++++++++++++++++++++++---
 gcc/testsuite/gcc.dg/gimplefe-60.c | 16 ++++++++++++
 gcc/tree-pretty-print.cc           | 22 +++++++++++++++++
 3 files changed, 74 insertions(+), 3 deletions(-)
 create mode 100644 gcc/testsuite/gcc.dg/gimplefe-60.c

diff --git a/gcc/c/gimple-parser.cc b/gcc/c/gimple-parser.cc
index 59cb29f420c..7d374dd66b0 100644
--- a/gcc/c/gimple-parser.cc
+++ b/gcc/c/gimple-parser.cc
@@ -110,7 +110,8 @@ static void c_parser_gimple_label (gimple_parser &, 
gimple_seq *);
 static void c_parser_gimple_statement (gimple_parser &, gimple_seq *);
 static struct c_expr c_parser_gimple_binary_expression (gimple_parser &, tree);
 static struct c_expr c_parser_gimple_unary_expression (gimple_parser &);
-static struct c_expr c_parser_gimple_postfix_expression (gimple_parser &);
+static struct c_expr c_parser_gimple_postfix_expression
+                       (gimple_parser &, tree = error_mark_node);
 static struct c_expr c_parser_gimple_postfix_expression_after_primary
                        (gimple_parser &, location_t, struct c_expr);
 static void c_parser_gimple_declaration (gimple_parser &);
@@ -1023,7 +1024,7 @@ c_parser_gimple_binary_expression (gimple_parser &parser, 
tree ret_type)
   struct c_expr ret, lhs, rhs;
   enum tree_code code = ERROR_MARK;
   ret.set_error ();
-  lhs = c_parser_gimple_postfix_expression (parser);
+  lhs = c_parser_gimple_postfix_expression (parser, ret_type);
   if (c_parser_error (parser))
     return ret;
   switch (c_parser_peek_token (parser)->type)
@@ -1488,7 +1489,7 @@ c_parser_gimple_typespec (gimple_parser &parser)
 */
 
 static struct c_expr
-c_parser_gimple_postfix_expression (gimple_parser &parser)
+c_parser_gimple_postfix_expression (gimple_parser &parser, tree ret_type)
 {
   location_t loc = c_parser_peek_token (parser)->location;
   source_range tok_range = c_parser_peek_token (parser)->get_range ();
@@ -1752,6 +1753,38 @@ c_parser_gimple_postfix_expression (gimple_parser 
&parser)
                }
              break;
            }
+         else if (strcmp (IDENTIFIER_POINTER (id), "__CLOBBER") == 0)
+           {
+             /* __CLOBBER [ '(' bob | eob | bos | eos ')' ]  */
+             clobber_kind kind = CLOBBER_UNDEF;
+             c_parser_consume_token (parser);
+             if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
+               {
+                 c_parser_consume_token (parser);
+                 auto tok = c_parser_peek_token (parser);
+                 if (c_parser_require (parser, CPP_NAME,
+                                       "expected clobber kind"))
+                   {
+                     const char *kind_str = IDENTIFIER_POINTER (tok->value);
+                     if (strcmp (kind_str, "bos") == 0)
+                       kind = CLOBBER_STORAGE_BEGIN;
+                     else if (strcmp (kind_str, "bob") == 0)
+                       kind = CLOBBER_OBJECT_BEGIN;
+                     else if (strcmp (kind_str, "eob") == 0)
+                       kind = CLOBBER_OBJECT_END;
+                     else if (strcmp (kind_str, "eos") == 0)
+                       kind = CLOBBER_STORAGE_END;
+                     else
+                       c_parser_error (parser, "expected one of %<bos%>, "
+                                       "%<eos%>, %<bob>, %<eob%>");
+                   }
+                 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
+                                            "expected %<)%>");
+               }
+             /* We infer the (redundant) type from the LHS.  */
+             expr.value = build_clobber (ret_type, kind);
+             break;
+           }
          else if (strcmp (IDENTIFIER_POINTER (id), "_Literal") == 0)
            {
              /* _Literal '(' type-name ')' ( [ '-' ] constant | constructor ) 
*/
diff --git a/gcc/testsuite/gcc.dg/gimplefe-60.c 
b/gcc/testsuite/gcc.dg/gimplefe-60.c
new file mode 100644
index 00000000000..13e9114496e
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/gimplefe-60.c
@@ -0,0 +1,16 @@
+/* { dg-do compile } */
+/* { dg-options "-fgimple" } */
+
+struct X { int i; };
+
+void __GIMPLE
+foo ()
+{
+  struct X x;
+  x = __CLOBBER;
+  x = __CLOBBER(bos);
+  x = __CLOBBER (eos);
+  x = __CLOBBER(bob);
+  x = __CLOBBER(eob);
+  return;
+}
diff --git a/gcc/tree-pretty-print.cc b/gcc/tree-pretty-print.cc
index ed96728cbc4..89fe93a1f6d 100644
--- a/gcc/tree-pretty-print.cc
+++ b/gcc/tree-pretty-print.cc
@@ -3047,6 +3047,28 @@ dump_generic_node (pretty_printer *pp, tree node, int 
spc, dump_flags_t flags,
        widest_int curidx;
        if (flags & TDF_GIMPLE)
          {
+           if (TREE_CLOBBER_P (node))
+             {
+               pp_string (pp, "__CLOBBER");
+               switch (CLOBBER_KIND (node))
+                 {
+                 case CLOBBER_STORAGE_BEGIN:
+                   pp_string (pp, "(bos)");
+                   break;
+                 case CLOBBER_STORAGE_END:
+                   pp_string (pp, "(eos)");
+                   break;
+                 case CLOBBER_OBJECT_BEGIN:
+                   pp_string (pp, "(bob)");
+                   break;
+                 case CLOBBER_OBJECT_END:
+                   pp_string (pp, "(eob)");
+                   break;
+                 default:
+                   break;
+                 }
+               break;
+             }
            pp_string (pp, "_Literal (");
            dump_generic_node (pp, TREE_TYPE (node), spc, flags, false);
            pp_string (pp, ") ");
-- 
2.51.0

Reply via email to