mirror of
git://gcc.gnu.org/git/gcc.git
synced 2025-04-18 05:40:23 +08:00
Amend match.pd syntax with force-simplified results
This adds a ! marker to result expressions that should simplify (and if not fail the simplification). This can for example be used like (simplify (plus (vec_cond:s @0 @1 @2) @3) (vec_cond @0 (plus! @1 @3) (plus! @2 @3))) to make the simplification only apply in case both plus operations in the result end up simplified to a simple operand. 2020-07-31 Richard Biener <rguenther@suse.de> * genmatch.c (expr::force_leaf): Add and initialize. (expr::gen_transform): Honor force_leaf by passing NULL as sequence argument to maybe_push_res_to_seq. (parser::parse_expr): Allow ! marker on result expression operations. * doc/match-and-simplify.texi: Amend.
This commit is contained in:
parent
c89366b12f
commit
14c35be3bf
@ -361,6 +361,21 @@ Usually the types of the generated result expressions are
|
||||
determined from the context, but sometimes like in the above case
|
||||
it is required that you specify them explicitely.
|
||||
|
||||
Another modifier for generated expressions is @code{!} which
|
||||
tells the machinery to only consider the simplification in case
|
||||
the marked expression simplified to a simple operand. Consider
|
||||
for example
|
||||
|
||||
@smallexample
|
||||
(simplify
|
||||
(plus (vec_cond:s @@0 @@1 @@2) @@3)
|
||||
(vec_cond @@0 (plus! @@1 @@3) (plus! @@2 @@3)))
|
||||
@end smallexample
|
||||
|
||||
which moves the outer @code{plus} operation to the inner arms
|
||||
of the @code{vec_cond} expression but only if the actual plus
|
||||
operations both simplify.
|
||||
|
||||
As intermediate conversions are often optional there is a way to
|
||||
avoid the need to repeat patterns both with and without such
|
||||
conversions. Namely you can mark a conversion as being optional
|
||||
|
@ -697,12 +697,13 @@ public:
|
||||
expr (id_base *operation_, location_t loc, bool is_commutative_ = false)
|
||||
: operand (OP_EXPR, loc), operation (operation_),
|
||||
ops (vNULL), expr_type (NULL), is_commutative (is_commutative_),
|
||||
is_generic (false), force_single_use (false), opt_grp (0) {}
|
||||
is_generic (false), force_single_use (false), force_leaf (false),
|
||||
opt_grp (0) {}
|
||||
expr (expr *e)
|
||||
: operand (OP_EXPR, e->location), operation (e->operation),
|
||||
ops (vNULL), expr_type (e->expr_type), is_commutative (e->is_commutative),
|
||||
is_generic (e->is_generic), force_single_use (e->force_single_use),
|
||||
opt_grp (e->opt_grp) {}
|
||||
force_leaf (e->force_leaf), opt_grp (e->opt_grp) {}
|
||||
void append_op (operand *op) { ops.safe_push (op); }
|
||||
/* The operator and its operands. */
|
||||
id_base *operation;
|
||||
@ -717,6 +718,9 @@ public:
|
||||
/* Whether pushing any stmt to the sequence should be conditional
|
||||
on this expression having a single-use. */
|
||||
bool force_single_use;
|
||||
/* Whether in the result expression this should be a leaf node
|
||||
with any children simplified down to simple operands. */
|
||||
bool force_leaf;
|
||||
/* If non-zero, the group for optional handling. */
|
||||
unsigned char opt_grp;
|
||||
virtual void gen_transform (FILE *f, int, const char *, bool, int,
|
||||
@ -2520,7 +2524,8 @@ expr::gen_transform (FILE *f, int indent, const char *dest, bool gimple,
|
||||
fprintf (f, ");\n");
|
||||
fprintf_indent (f, indent, "tem_op.resimplify (lseq, valueize);\n");
|
||||
fprintf_indent (f, indent,
|
||||
"_r%d = maybe_push_res_to_seq (&tem_op, lseq);\n", depth);
|
||||
"_r%d = maybe_push_res_to_seq (&tem_op, %s);\n", depth,
|
||||
!force_leaf ? "lseq" : "NULL");
|
||||
fprintf_indent (f, indent,
|
||||
"if (!_r%d) return false;\n",
|
||||
depth);
|
||||
@ -4240,6 +4245,14 @@ parser::parse_expr ()
|
||||
bool force_capture = false;
|
||||
const char *expr_type = NULL;
|
||||
|
||||
if (!parsing_match_operand
|
||||
&& token->type == CPP_NOT
|
||||
&& !(token->flags & PREV_WHITE))
|
||||
{
|
||||
eat_token (CPP_NOT);
|
||||
e->force_leaf = true;
|
||||
}
|
||||
|
||||
if (token->type == CPP_COLON
|
||||
&& !(token->flags & PREV_WHITE))
|
||||
{
|
||||
|
Loading…
x
Reference in New Issue
Block a user