The define_subst support made it syntactically possible to add
attributes to a define_expand, but until now they had been ignored
by genattrtab.c. This patch allows define_expands to have
"code,alternative" attributes but raises an error for general
"insn" attributes. (Insn attributes would create a chicken-and-egg
problem because you'd need to call the expander to get the insn.)
The point is to allow define_expands to have preferred_for_size
and preferred_for_speed attributes.
Tested as described in the covering note.
gcc/
* genattrtab.c (insn_def): Add max_type field.
(check_defs): Check that the type of a define_expand attribute
is acceptable.
(gen_insn): Handle DEFINE_EXPAND. Initialize the max_type field.
(main): Handle DEFINE_EXPAND.
diff --git a/gcc/genattrtab.c b/gcc/genattrtab.c
index 6f797bf..42f6dc5 100644
--- a/gcc/genattrtab.c
+++ b/gcc/genattrtab.c
@@ -142,6 +142,7 @@ struct insn_def
file_location loc; /* Where in the .md files it occurs. */
int num_alternatives; /* Number of alternatives. */
int vec_idx; /* Index of attribute vector in `def'. */
+ attr_type max_type; /* Maximum allowable type. */
};
/* Once everything has been read in, we store in each attribute value a list
@@ -1167,6 +1168,14 @@ check_defs (void)
XSTR (XEXP (value, 0), 0));
continue;
}
+ if (id->max_type < attr->type)
+ {
+ error_at (id->loc, "`%s's cannot have %s attribute `%s'",
+ GET_RTX_NAME (GET_CODE (id->def)),
+ get_attr_type_name (attr->type),
+ attr->name);
+ continue;
+ }
XVECEXP (id->def, id->vec_idx, i) = value;
XEXP (value, 1) = check_attr_value (id->loc, XEXP (value, 1), attr);
@@ -3283,6 +3292,14 @@ gen_insn (md_rtx_info *info)
switch (GET_CODE (def))
{
+ case DEFINE_EXPAND:
+ id->insn_code = info->index;
+ id->insn_index = insn_index_number;
+ id->num_alternatives = 1;
+ id->vec_idx = 4;
+ id->max_type = AT_CODE_ALT;
+ break;
+
case DEFINE_INSN:
id->insn_code = info->index;
id->insn_index = insn_index_number;
@@ -3290,6 +3307,7 @@ gen_insn (md_rtx_info *info)
if (id->num_alternatives == 0)
id->num_alternatives = 1;
id->vec_idx = 4;
+ id->max_type = AT_INSN;
break;
case DEFINE_PEEPHOLE:
@@ -3299,6 +3317,7 @@ gen_insn (md_rtx_info *info)
if (id->num_alternatives == 0)
id->num_alternatives = 1;
id->vec_idx = 3;
+ id->max_type = AT_INSN;
break;
case DEFINE_ASM_ATTRIBUTES:
@@ -3306,6 +3325,7 @@ gen_insn (md_rtx_info *info)
id->insn_index = -1;
id->num_alternatives = 1;
id->vec_idx = 0;
+ id->max_type = AT_INSN;
got_define_asm_attributes = 1;
break;
@@ -5266,6 +5286,7 @@ main (int argc, char **argv)
{
switch (GET_CODE (info.def))
{
+ case DEFINE_EXPAND:
case DEFINE_INSN:
case DEFINE_PEEPHOLE:
case DEFINE_ASM_ATTRIBUTES: