diff options
-rw-r--r-- | gcc/ChangeLog | 20 | ||||
-rw-r--r-- | gcc/caller-save.c | 22 | ||||
-rw-r--r-- | gcc/df-scan.c | 15 | ||||
-rw-r--r-- | gcc/doc/tm.texi | 2 | ||||
-rw-r--r-- | gcc/flow.c | 3 | ||||
-rw-r--r-- | gcc/postreload.c | 8 | ||||
-rw-r--r-- | gcc/reload.c | 17 | ||||
-rw-r--r-- | gcc/resource.c | 20 | ||||
-rw-r--r-- | gcc/rtl.h | 1 | ||||
-rw-r--r-- | gcc/rtlanal.c | 215 |
10 files changed, 213 insertions, 110 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index f991a4d066d..4f145939528 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,23 @@ +2006-12-20 Joseph Myers <joseph@codesourcery.com> + + * rtlanal.c (struct subreg_info, subreg_get_info, subreg_nregs): + New. + (subreg_regno_offset, subreg_offset_representable_p): Change to + wrappers about subreg_get_info. + (refers_to_regno_p, reg_overlap_mentioned_p): Use subreg_nregs. + * rtl.h (subreg_nregs): Declare. + * doc/tm.texi (HARD_REGNO_NREGS_HAS_PADDING): Update to refer to + subreg_get_info. + * caller-save.c (mark_set_regs, add_stored_regs): Use + subreg_nregs. + * df-scan.c (df_ref_record): Use subreg_nregs. + * flow.c (mark_set_1): Use subreg_nregs. + * postreload.c (move2add_note_store): Use subreg_nregs. + * reload.c (decompose, refers_to_regno_for_reload_p, + reg_overlap_mentioned_for_reload_p): Use subreg_nregs. + * resource.c (update_live_status, mark_referenced_resources, + mark_set_resources): Use subreg_nregs. + 2006-12-20 Zdenek Dvorak <dvorakz@suse.cz> * loop-unswitch.c (unswitch_loop): Update arguments of diff --git a/gcc/caller-save.c b/gcc/caller-save.c index c81c72c49b6..86d74ee1726 100644 --- a/gcc/caller-save.c +++ b/gcc/caller-save.c @@ -508,15 +508,17 @@ mark_set_regs (rtx reg, rtx setter ATTRIBUTE_UNUSED, void *data) if (!REG_P (inner) || REGNO (inner) >= FIRST_PSEUDO_REGISTER) return; regno = subreg_regno (reg); + endregno = regno + subreg_nregs (reg); } else if (REG_P (reg) && REGNO (reg) < FIRST_PSEUDO_REGISTER) - regno = REGNO (reg); + { + regno = REGNO (reg); + endregno = regno + hard_regno_nregs[regno][mode]; + } else return; - endregno = regno + hard_regno_nregs[regno][mode]; - for (i = regno; i < endregno; i++) SET_HARD_REG_BIT (*this_insn_sets, i); } @@ -542,13 +544,17 @@ add_stored_regs (rtx reg, rtx setter, void *data) SUBREG_BYTE (reg), GET_MODE (reg)); reg = SUBREG_REG (reg); + regno = REGNO (reg) + offset; + endregno = regno + subreg_nregs (reg); } + else + { + if (!REG_P (reg) || REGNO (reg) >= FIRST_PSEUDO_REGISTER) + return; - if (!REG_P (reg) || REGNO (reg) >= FIRST_PSEUDO_REGISTER) - return; - - regno = REGNO (reg) + offset; - endregno = regno + hard_regno_nregs[regno][mode]; + regno = REGNO (reg) + offset; + endregno = regno + hard_regno_nregs[regno][mode]; + } for (i = regno; i < endregno; i++) SET_REGNO_REG_SET ((regset) data, i); diff --git a/gcc/df-scan.c b/gcc/df-scan.c index 46dfb072cce..fea786c0196 100644 --- a/gcc/df-scan.c +++ b/gcc/df-scan.c @@ -1083,15 +1083,14 @@ df_ref_record (struct dataflow *dflow, rtx reg, rtx *loc, if (!(dflow->flags & DF_HARD_REGS)) return; - /* GET_MODE (reg) is correct here. We do not want to go into a SUBREG - for the mode, because we only want to add references to regs, which - are really referenced. E.g., a (subreg:SI (reg:DI 0) 0) does _not_ - reference the whole reg 0 in DI mode (which would also include - reg 1, at least, if 0 and 1 are SImode registers). */ - endregno = hard_regno_nregs[regno][GET_MODE (reg)]; if (GET_CODE (reg) == SUBREG) - regno += subreg_regno_offset (regno, GET_MODE (SUBREG_REG (reg)), - SUBREG_BYTE (reg), GET_MODE (reg)); + { + regno += subreg_regno_offset (regno, GET_MODE (SUBREG_REG (reg)), + SUBREG_BYTE (reg), GET_MODE (reg)); + endregno = subreg_nregs (reg); + } + else + endregno = hard_regno_nregs[regno][GET_MODE (reg)]; endregno += regno; /* If this is a multiword hardreg, we create some extra datastructures that diff --git a/gcc/doc/tm.texi b/gcc/doc/tm.texi index f209593f0c9..0896ab8db17 100644 --- a/gcc/doc/tm.texi +++ b/gcc/doc/tm.texi @@ -1991,7 +1991,7 @@ registers but takes up 128 bits in memory, then this would be nonzero. This macros only needs to be defined if there are cases where -@code{subreg_regno_offset} and @code{subreg_offset_representable_p} +@code{subreg_get_info} would otherwise wrongly determine that a @code{subreg} can be represented by an offset to the register number, when in fact such a @code{subreg} would contain some of the padding not stored in diff --git a/gcc/flow.c b/gcc/flow.c index 2b5d3032bf7..1da935bda31 100644 --- a/gcc/flow.c +++ b/gcc/flow.c @@ -2791,8 +2791,7 @@ mark_set_1 (struct propagate_block_info *pbi, enum rtx_code code, rtx reg, rtx c regno_first += subreg_regno_offset (regno_first, inner_mode, SUBREG_BYTE (reg), outer_mode); - regno_last = (regno_first - + hard_regno_nregs[regno_first][outer_mode] - 1); + regno_last = regno_first + subreg_nregs (reg) - 1; /* Since we've just adjusted the register number ranges, make sure REG matches. Otherwise some_was_live will be clear diff --git a/gcc/postreload.c b/gcc/postreload.c index 5f4ae4f5b18..d1e58ab944d 100644 --- a/gcc/postreload.c +++ b/gcc/postreload.c @@ -1429,6 +1429,7 @@ static void move2add_note_store (rtx dst, rtx set, void *data ATTRIBUTE_UNUSED) { unsigned int regno = 0; + unsigned int nregs = 0; unsigned int i; enum machine_mode mode = GET_MODE (dst); @@ -1438,6 +1439,7 @@ move2add_note_store (rtx dst, rtx set, void *data ATTRIBUTE_UNUSED) GET_MODE (SUBREG_REG (dst)), SUBREG_BYTE (dst), GET_MODE (dst)); + nregs = subreg_nregs (dst); dst = SUBREG_REG (dst); } @@ -1455,9 +1457,11 @@ move2add_note_store (rtx dst, rtx set, void *data ATTRIBUTE_UNUSED) return; regno += REGNO (dst); + if (!nregs) + nregs = hard_regno_nregs[regno][mode]; if (SCALAR_INT_MODE_P (GET_MODE (dst)) - && hard_regno_nregs[regno][mode] == 1 && GET_CODE (set) == SET + && nregs == 1 && GET_CODE (set) == SET && GET_CODE (SET_DEST (set)) != ZERO_EXTRACT && GET_CODE (SET_DEST (set)) != STRICT_LOW_PART) { @@ -1557,7 +1561,7 @@ move2add_note_store (rtx dst, rtx set, void *data ATTRIBUTE_UNUSED) } else { - unsigned int endregno = regno + hard_regno_nregs[regno][mode]; + unsigned int endregno = regno + nregs; for (i = regno; i < endregno; i++) /* Reset the information about this register. */ diff --git a/gcc/reload.c b/gcc/reload.c index 1f1bc23020b..50af5d5e366 100644 --- a/gcc/reload.c +++ b/gcc/reload.c @@ -2414,7 +2414,7 @@ decompose (rtx x) return decompose (SUBREG_REG (x)); else /* A hard reg. */ - val.end = val.start + hard_regno_nregs[val.start][GET_MODE (x)]; + val.end = val.start + subreg_nregs (x); break; case SCRATCH: @@ -6381,7 +6381,7 @@ refers_to_regno_for_reload_p (unsigned int regno, unsigned int endregno, unsigned int inner_regno = subreg_regno (x); unsigned int inner_endregno = inner_regno + (inner_regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[inner_regno][GET_MODE (x)] : 1); + ? subreg_nregs (x) : 1); return endregno > inner_regno && regno < inner_endregno; } @@ -6479,6 +6479,10 @@ reg_overlap_mentioned_for_reload_p (rtx x, rtx in) GET_MODE (SUBREG_REG (x)), SUBREG_BYTE (x), GET_MODE (x)); + endregno = regno + (regno < FIRST_PSEUDO_REGISTER + ? subreg_nregs (x) : 1); + + return refers_to_regno_for_reload_p (regno, endregno, in, (rtx*) 0); } else if (REG_P (x)) { @@ -6494,6 +6498,10 @@ reg_overlap_mentioned_for_reload_p (rtx x, rtx in) gcc_assert (reg_equiv_constant[regno]); return 0; } + + endregno = regno + hard_regno_nregs[regno][GET_MODE (x)]; + + return refers_to_regno_for_reload_p (regno, endregno, in, (rtx*) 0); } else if (MEM_P (x)) return refers_to_mem_for_reload_p (in); @@ -6520,10 +6528,7 @@ reg_overlap_mentioned_for_reload_p (rtx x, rtx in) || reg_overlap_mentioned_for_reload_p (XEXP (x, 1), in)); } - endregno = regno + (regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[regno][GET_MODE (x)] : 1); - - return refers_to_regno_for_reload_p (regno, endregno, in, (rtx*) 0); + gcc_unreachable (); } /* Return nonzero if anything in X contains a MEM. Look also for pseudo diff --git a/gcc/resource.c b/gcc/resource.c index cd4eb10628c..398db5c9c40 100644 --- a/gcc/resource.c +++ b/gcc/resource.c @@ -99,11 +99,17 @@ update_live_status (rtx dest, rtx x, void *data ATTRIBUTE_UNUSED) return; if (GET_CODE (dest) == SUBREG) - first_regno = subreg_regno (dest); - else - first_regno = REGNO (dest); + { + first_regno = subreg_regno (dest); + last_regno = first_regno + subreg_nregs (dest); - last_regno = first_regno + hard_regno_nregs[first_regno][GET_MODE (dest)]; + } + else + { + first_regno = REGNO (dest); + last_regno + = first_regno + hard_regno_nregs[first_regno][GET_MODE (dest)]; + } if (GET_CODE (x) == CLOBBER) for (i = first_regno; i < last_regno; i++) @@ -229,8 +235,7 @@ mark_referenced_resources (rtx x, struct resources *res, else { unsigned int regno = subreg_regno (x); - unsigned int last_regno - = regno + hard_regno_nregs[regno][GET_MODE (x)]; + unsigned int last_regno = regno + subreg_nregs (x); gcc_assert (last_regno <= FIRST_PSEUDO_REGISTER); for (r = regno; r < last_regno; r++) @@ -763,8 +768,7 @@ mark_set_resources (rtx x, struct resources *res, int in_dest, else { unsigned int regno = subreg_regno (x); - unsigned int last_regno - = regno + hard_regno_nregs[regno][GET_MODE (x)]; + unsigned int last_regno = regno + subreg_nregs (x); gcc_assert (last_regno <= FIRST_PSEUDO_REGISTER); for (r = regno; r < last_regno; r++) diff --git a/gcc/rtl.h b/gcc/rtl.h index 54dad700087..16de3bbe4b0 100644 --- a/gcc/rtl.h +++ b/gcc/rtl.h @@ -1041,6 +1041,7 @@ extern unsigned int subreg_regno_offset (unsigned int, enum machine_mode, extern bool subreg_offset_representable_p (unsigned int, enum machine_mode, unsigned int, enum machine_mode); extern unsigned int subreg_regno (rtx); +extern unsigned int subreg_nregs (rtx); extern unsigned HOST_WIDE_INT nonzero_bits (rtx, enum machine_mode); extern unsigned int num_sign_bit_copies (rtx, enum machine_mode); extern bool constant_pool_constant_p (rtx); diff --git a/gcc/rtlanal.c b/gcc/rtlanal.c index 4b965f8ca1c..c45a020709f 100644 --- a/gcc/rtlanal.c +++ b/gcc/rtlanal.c @@ -38,6 +38,18 @@ Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA #include "regs.h" #include "function.h" +/* Information about a subreg of a hard register. */ +struct subreg_info +{ + /* Offset of first hard register involved in the subreg. */ + int offset; + /* Number of hard registers involved in the subreg. */ + int nregs; + /* Whether this subreg can be represented as a hard reg with the new + mode. */ + bool representable_p; +}; + /* Forward declarations */ static void set_of_1 (rtx, rtx, void *); static bool covers_regno_p (rtx, unsigned int); @@ -45,6 +57,9 @@ static bool covers_regno_no_parallel_p (rtx, unsigned int); static int rtx_referenced_p_1 (rtx *, void *); static int computed_jump_p_1 (rtx); static void parms_set (rtx, rtx, void *); +static void subreg_get_info (unsigned int, enum machine_mode, + unsigned int, enum machine_mode, + struct subreg_info *); static unsigned HOST_WIDE_INT cached_nonzero_bits (rtx, enum machine_mode, rtx, enum machine_mode, @@ -1176,7 +1191,7 @@ refers_to_regno_p (unsigned int regno, unsigned int endregno, rtx x, unsigned int inner_regno = subreg_regno (x); unsigned int inner_endregno = inner_regno + (inner_regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[inner_regno][GET_MODE (x)] : 1); + ? subreg_nregs (x) : 1); return endregno > inner_regno && regno < inner_endregno; } @@ -1266,13 +1281,15 @@ reg_overlap_mentioned_p (rtx x, rtx in) regno = REGNO (SUBREG_REG (x)); if (regno < FIRST_PSEUDO_REGISTER) regno = subreg_regno (x); + endregno = regno + (regno < FIRST_PSEUDO_REGISTER + ? subreg_nregs (x) : 1); goto do_reg; case REG: regno = REGNO (x); - do_reg: endregno = regno + (regno < FIRST_PSEUDO_REGISTER ? hard_regno_nregs[regno][GET_MODE (x)] : 1); + do_reg: return refers_to_regno_p (regno, endregno, in, (rtx*) 0); case MEM: @@ -2926,69 +2943,27 @@ subreg_lsb (rtx x) SUBREG_BYTE (x)); } -/* This function returns the regno offset of a subreg expression. - xregno - A regno of an inner hard subreg_reg (or what will become one). - xmode - The mode of xregno. - offset - The byte offset. - ymode - The mode of a top level SUBREG (or what may become one). - RETURN - The regno offset which would be used. */ -unsigned int -subreg_regno_offset (unsigned int xregno, enum machine_mode xmode, - unsigned int offset, enum machine_mode ymode) -{ - int nregs_xmode, nregs_ymode; - int mode_multiple, nregs_multiple; - int y_offset; - - gcc_assert (xregno < FIRST_PSEUDO_REGISTER); - - /* Adjust nregs_xmode to allow for 'holes'. */ - if (HARD_REGNO_NREGS_HAS_PADDING (xregno, xmode)) - nregs_xmode = HARD_REGNO_NREGS_WITH_PADDING (xregno, xmode); - else - nregs_xmode = hard_regno_nregs[xregno][xmode]; - - nregs_ymode = hard_regno_nregs[xregno][ymode]; - - /* If this is a big endian paradoxical subreg, which uses more actual - hard registers than the original register, we must return a negative - offset so that we find the proper highpart of the register. */ - if (offset == 0 - && nregs_ymode > nregs_xmode - && (GET_MODE_SIZE (ymode) > UNITS_PER_WORD - ? WORDS_BIG_ENDIAN : BYTES_BIG_ENDIAN)) - return nregs_xmode - nregs_ymode; - - if (offset == 0 || nregs_xmode == nregs_ymode) - return 0; - - /* Size of ymode must not be greater than the size of xmode. */ - mode_multiple = GET_MODE_SIZE (xmode) / GET_MODE_SIZE (ymode); - gcc_assert (mode_multiple != 0); - - y_offset = offset / GET_MODE_SIZE (ymode); - nregs_multiple = nregs_xmode / nregs_ymode; - return (y_offset / (mode_multiple / nregs_multiple)) * nregs_ymode; -} - -/* This function returns true when the offset is representable via - subreg_offset in the given regno. +/* Fill in information about a subreg of a hard register. xregno - A regno of an inner hard subreg_reg (or what will become one). xmode - The mode of xregno. offset - The byte offset. ymode - The mode of a top level SUBREG (or what may become one). - RETURN - Whether the offset is representable. */ -bool -subreg_offset_representable_p (unsigned int xregno, enum machine_mode xmode, - unsigned int offset, enum machine_mode ymode) + info - Pointer to structure to fill in. */ +static void +subreg_get_info (unsigned int xregno, enum machine_mode xmode, + unsigned int offset, enum machine_mode ymode, + struct subreg_info *info) { int nregs_xmode, nregs_ymode; int mode_multiple, nregs_multiple; - int y_offset; + int offset_adj, y_offset, y_offset_adj; int regsize_xmode, regsize_ymode; + bool rknown; gcc_assert (xregno < FIRST_PSEUDO_REGISTER); + rknown = false; + /* If there are holes in a non-scalar mode in registers, we expect that it is made up of its units concatenated together. */ if (HARD_REGNO_NREGS_HAS_PADDING (xregno, xmode)) @@ -3021,7 +2996,10 @@ subreg_offset_representable_p (unsigned int xregno, enum machine_mode xmode, && (offset / GET_MODE_SIZE (xmode_unit) != ((offset + GET_MODE_SIZE (ymode) - 1) / GET_MODE_SIZE (xmode_unit)))) - return false; + { + info->representable_p = false; + rknown = true; + } } else nregs_xmode = hard_regno_nregs[xregno][xmode]; @@ -3029,24 +3007,57 @@ subreg_offset_representable_p (unsigned int xregno, enum machine_mode xmode, nregs_ymode = hard_regno_nregs[xregno][ymode]; /* Paradoxical subregs are otherwise valid. */ - if (offset == 0 - && nregs_ymode > nregs_xmode - && (GET_MODE_SIZE (ymode) > UNITS_PER_WORD - ? WORDS_BIG_ENDIAN : BYTES_BIG_ENDIAN)) - return true; + if (!rknown + && offset == 0 + && GET_MODE_SIZE (ymode) > GET_MODE_SIZE (xmode)) + { + info->representable_p = true; + /* If this is a big endian paradoxical subreg, which uses more + actual hard registers than the original register, we must + return a negative offset so that we find the proper highpart + of the register. */ + if (GET_MODE_SIZE (ymode) > UNITS_PER_WORD + ? WORDS_BIG_ENDIAN : BYTES_BIG_ENDIAN) + info->offset = nregs_xmode - nregs_ymode; + else + info->offset = 0; + info->nregs = nregs_ymode; + return; + } /* If registers store different numbers of bits in the different modes, we cannot generally form this subreg. */ - regsize_xmode = GET_MODE_SIZE (xmode) / nregs_xmode; - regsize_ymode = GET_MODE_SIZE (ymode) / nregs_ymode; - if (regsize_xmode > regsize_ymode && nregs_ymode > 1) - return false; - if (regsize_ymode > regsize_xmode && nregs_xmode > 1) - return false; + if (!HARD_REGNO_NREGS_HAS_PADDING (xregno, xmode) + && !HARD_REGNO_NREGS_HAS_PADDING (xregno, ymode)) + { + regsize_xmode = GET_MODE_SIZE (xmode) / nregs_xmode; + gcc_assert (regsize_xmode * nregs_xmode == GET_MODE_SIZE (xmode)); + regsize_ymode = GET_MODE_SIZE (ymode) / nregs_ymode; + gcc_assert (regsize_ymode * nregs_ymode == GET_MODE_SIZE (ymode)); + if (!rknown && regsize_xmode > regsize_ymode && nregs_ymode > 1) + { + info->representable_p = false; + info->nregs + = (GET_MODE_SIZE (ymode) + regsize_xmode - 1) / regsize_xmode; + info->offset = offset / regsize_xmode; + return; + } + if (!rknown && regsize_ymode > regsize_xmode && nregs_xmode > 1) + { + info->representable_p = false; + info->nregs + = (GET_MODE_SIZE (ymode) + regsize_xmode - 1) / regsize_xmode; + info->offset = offset / regsize_xmode; + return; + } + } /* Lowpart subregs are otherwise valid. */ - if (offset == subreg_lowpart_offset (ymode, xmode)) - return true; + if (!rknown && offset == subreg_lowpart_offset (ymode, xmode)) + { + info->representable_p = true; + rknown = true; + } /* This should always pass, otherwise we don't know how to verify the constraint. These conditions may be relaxed but @@ -3057,22 +3068,61 @@ subreg_offset_representable_p (unsigned int xregno, enum machine_mode xmode, /* The XMODE value can be seen as a vector of NREGS_XMODE values. The subreg must represent a lowpart of given field. Compute what field it is. */ - offset -= subreg_lowpart_offset (ymode, - mode_for_size (GET_MODE_BITSIZE (xmode) - / nregs_xmode, - MODE_INT, 0)); + offset_adj = offset; + offset_adj -= subreg_lowpart_offset (ymode, + mode_for_size (GET_MODE_BITSIZE (xmode) + / nregs_xmode, + MODE_INT, 0)); /* Size of ymode must not be greater than the size of xmode. */ mode_multiple = GET_MODE_SIZE (xmode) / GET_MODE_SIZE (ymode); gcc_assert (mode_multiple != 0); y_offset = offset / GET_MODE_SIZE (ymode); - nregs_multiple = nregs_xmode / nregs_ymode; + y_offset_adj = offset_adj / GET_MODE_SIZE (ymode); + nregs_multiple = nregs_xmode / nregs_ymode; - gcc_assert ((offset % GET_MODE_SIZE (ymode)) == 0); + gcc_assert ((offset_adj % GET_MODE_SIZE (ymode)) == 0); gcc_assert ((mode_multiple % nregs_multiple) == 0); - return (!(y_offset % (mode_multiple / nregs_multiple))); + if (!rknown) + { + info->representable_p = (!(y_offset_adj % (mode_multiple / nregs_multiple))); + rknown = true; + } + info->offset = (y_offset / (mode_multiple / nregs_multiple)) * nregs_ymode; + info->nregs = nregs_ymode; +} + +/* This function returns the regno offset of a subreg expression. + xregno - A regno of an inner hard subreg_reg (or what will become one). + xmode - The mode of xregno. + offset - The byte offset. + ymode - The mode of a top level SUBREG (or what may become one). + RETURN - The regno offset which would be used. */ +unsigned int +subreg_regno_offset (unsigned int xregno, enum machine_mode xmode, + unsigned int offset, enum machine_mode ymode) +{ + struct subreg_info info; + subreg_get_info (xregno, xmode, offset, ymode, &info); + return info.offset; +} + +/* This function returns true when the offset is representable via + subreg_offset in the given regno. + xregno - A regno of an inner hard subreg_reg (or what will become one). + xmode - The mode of xregno. + offset - The byte offset. + ymode - The mode of a top level SUBREG (or what may become one). + RETURN - Whether the offset is representable. */ +bool +subreg_offset_representable_p (unsigned int xregno, enum machine_mode xmode, + unsigned int offset, enum machine_mode ymode) +{ + struct subreg_info info; + subreg_get_info (xregno, xmode, offset, ymode, &info); + return info.representable_p; } /* Return the final regno that a subreg expression refers to. */ @@ -3090,6 +3140,21 @@ subreg_regno (rtx x) return ret; } + +/* Return the number of registers that a subreg expression refers + to. */ +unsigned int +subreg_nregs (rtx x) +{ + struct subreg_info info; + rtx subreg = SUBREG_REG (x); + int regno = REGNO (subreg); + + subreg_get_info (regno, GET_MODE (subreg), SUBREG_BYTE (x), GET_MODE (x), + &info); + return info.nregs; +} + struct parms_set_data { int nregs; |