Commit 94c765ab by J"orn Rennecke Committed by Joern Rennecke

genoutput.c (process_template): Process '*' in '@' alternatives.

	* genoutput.c (process_template): Process '*' in '@' alternatives.
	* doc/md.texi (node Output Statement): Provide example for the above.

From-SVN: r192457
parent c3dc2ac8
2012-10-15 J"orn Rennecke <joern.rennecke@arc.com>
* genoutput.c (process_template): Process '*' in '@' alternatives.
* doc/md.texi (node Output Statement): Provide example for the above.
2012-10-15 Richard Guenther <rguenther@suse.de>
PR tree-optimization/54920
......@@ -665,6 +665,22 @@ as follows, having the output control string start with a @samp{@@}:
@end group
@end smallexample
If you just need a little bit of C code in one (or a few) alternatives,
you can use @samp{*} inside of a @samp{@@} multi-alternative template:
@smallexample
@group
(define_insn ""
[(set (match_operand:SI 0 "general_operand" "=r,<,m")
(const_int 0))]
""
"@@
clrreg %0
* return stack_mem_p (operands[0]) ? \"push 0\" : \"clrmem %0\";
clrmem %0")
@end group
@end smallexample
@node Predicates
@section Predicates
@cindex predicates
......
/* Generate code from to output assembler insns as recognized from rtl.
Copyright (C) 1987, 1988, 1992, 1994, 1995, 1997, 1998, 1999, 2000, 2002,
2003, 2004, 2005, 2007, 2008, 2009, 2010, 2012
2003, 2004, 2005, 2007, 2008, 2009, 2010, 2011, 2012
Free Software Foundation, Inc.
This file is part of GCC.
......@@ -662,19 +662,55 @@ process_template (struct data *d, const char *template_code)
list of assembler code templates, one for each alternative. */
else if (template_code[0] == '@')
{
d->template_code = 0;
d->output_format = INSN_OUTPUT_FORMAT_MULTI;
int found_star = 0;
printf ("\nstatic const char * const output_%d[] = {\n", d->code_number);
for (cp = &template_code[1]; *cp; )
{
while (ISSPACE (*cp))
cp++;
if (*cp == '*')
found_star = 1;
while (!IS_VSPACE (*cp) && *cp != '\0')
++cp;
}
d->template_code = 0;
if (found_star)
{
d->output_format = INSN_OUTPUT_FORMAT_FUNCTION;
puts ("\nstatic const char *");
printf ("output_%d (rtx *operands ATTRIBUTE_UNUSED, "
"rtx insn ATTRIBUTE_UNUSED)\n", d->code_number);
puts ("{");
puts (" switch (which_alternative)\n {");
}
else
{
d->output_format = INSN_OUTPUT_FORMAT_MULTI;
printf ("\nstatic const char * const output_%d[] = {\n",
d->code_number);
}
for (i = 0, cp = &template_code[1]; *cp; )
{
const char *ep, *sp;
const char *ep, *sp, *bp;
while (ISSPACE (*cp))
cp++;
printf (" \"");
bp = cp;
if (found_star)
{
printf (" case %d:", i);
if (*cp == '*')
{
printf ("\n ");
cp++;
}
else
printf (" return \"");
}
else
printf (" \"");
for (ep = sp = cp; !IS_VSPACE (*ep) && *ep != '\0'; ++ep)
if (!ISSPACE (*ep))
......@@ -690,7 +726,18 @@ process_template (struct data *d, const char *template_code)
cp++;
}
printf ("\",\n");
if (!found_star)
puts ("\",");
else if (*bp != '*')
puts ("\";");
else
{
/* The usual action will end with a return.
If there is neither break or return at the end, this is
assumed to be intentional; this allows to have multiple
consecutive alternatives share some code. */
puts ("");
}
i++;
}
if (i == 1)
......@@ -700,7 +747,10 @@ process_template (struct data *d, const char *template_code)
error_with_line (d->lineno,
"wrong number of alternatives in the output template");
printf ("};\n");
if (found_star)
puts (" default: gcc_unreachable ();\n }\n}");
else
printf ("};\n");
}
else
{
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment