diff options
-rw-r--r-- | gdb/ChangeLog | 19 | ||||
-rw-r--r-- | gdb/Makefile.in | 14 | ||||
-rw-r--r-- | gdb/gdbarch.c | 30 | ||||
-rw-r--r-- | gdb/gdbarch.h | 7 | ||||
-rwxr-xr-x | gdb/gdbarch.sh | 4 | ||||
-rw-r--r-- | gdb/regcache.c | 83 | ||||
-rw-r--r-- | gdb/reggroups.c | 268 | ||||
-rw-r--r-- | gdb/reggroups.h | 61 |
8 files changed, 459 insertions, 27 deletions
diff --git a/gdb/ChangeLog b/gdb/ChangeLog index effdb1f..61f6723 100644 --- a/gdb/ChangeLog +++ b/gdb/ChangeLog @@ -1,5 +1,24 @@ 2002-11-02 Andrew Cagney <cagney@redhat.com> + * reggroups.h, reggroups.c: New files. + * regcache.c: Include "reggroups.h". + (enum regcache_dump_what): Add `regcache_dump_groups'. + (regcache_dump): Contract size of the "Type" column. When + specified, dump the register's groups. + (maintenance_print_register_groups): New function. + (_initialize_regcache): Add command `maint print register-groups'. + * Makefile.in (COMMON_OBS): Add reggroups.o + (SFILES): Add reggroups.c. + (reggroups_h): Define. + (regcache.o, gdbarch.o): Update dependencies. + (reggroups.o): Specify dependencies. + * gdbarch.sh (register_reggroup_p): Add pure multi-arch method. + Add opaque declaration for `struct reggroup' in generated .h file. + Include "reggroups.h" in generated .c file. + gdbarch.h, gdbarch.c: Re-generate. + +2002-11-02 Andrew Cagney <cagney@redhat.com> + * regcache.h (deprecated_read_register_gen): Rename read_register_gen. (deprecated_write_register_gen): Rename write_register_gen. diff --git a/gdb/Makefile.in b/gdb/Makefile.in index a057202..ab9a33b 100644 --- a/gdb/Makefile.in +++ b/gdb/Makefile.in @@ -550,7 +550,7 @@ SFILES = ada-exp.y ada-lang.c ada-typeprint.c ada-valprint.c ada-tasks.c \ nlmread.c \ objfiles.c osabi.c \ p-exp.y p-lang.c p-typeprint.c p-valprint.c parse.c printcmd.c \ - regcache.c remote.c \ + regcache.c reggroups.c remote.c \ scm-exp.c scm-lang.c scm-valprint.c serial.c ser-unix.c source.c \ stabsread.c stack.c std-regs.c symfile.c symmisc.c symtab.c \ target.c thread.c top.c tracepoint.c typeprint.c \ @@ -698,6 +698,7 @@ ppc_tdep_h = ppc-tdep.h $(osabi_h) ppcnbsd_tdep_h = ppcnbsd-tdep.h proc_utils_h = proc-utils.h regcache_h = regcache.h +reggroups_h = reggroups.h remote_utils_h = remote-utils.h $(target_h) remote_h = remote.h scm_lang_h = scm-lang.h $(scm_tags_h) @@ -854,7 +855,8 @@ COMMON_OBS = version.o blockframe.o breakpoint.o findvar.o regcache.o \ nlmread.o serial.o mdebugread.o top.o utils.o \ ui-file.o \ frame.o doublest.o \ - gnu-v2-abi.o gnu-v3-abi.o hpacc-abi.o cp-abi.o cp-support.o + gnu-v2-abi.o gnu-v3-abi.o hpacc-abi.o cp-abi.o cp-support.o \ + reggroups.o OBS = $(COMMON_OBS) $(ANNOTATE_OBS) @@ -1685,7 +1687,7 @@ gdbarch.o: gdbarch.c $(defs_h) $(arch_utils_h) $(gdbcmd_h) $(inferior_h) \ $(gdb_string_h) $(symtab_h) $(frame_h) $(inferior_h) $(breakpoint_h) \ $(gdb_wait_h) $(gdbcore_h) $(gdbcmd_h) $(target_h) $(gdbthread_h) \ $(annotate_h) $(symfile_h) $(value_h) $(symcat_h) $(floatformat_h) \ - $(gdb_assert_h) $(gdb_string_h) $(gdb_events_h) + $(gdb_assert_h) $(gdb_string_h) $(gdb_events_h) $(reggroups_h) gdbtypes.o: gdbtypes.c $(defs_h) $(gdb_string_h) $(bfd_h) $(symtab_h) \ $(symfile_h) $(objfiles_h) $(gdbtypes_h) $(expression_h) \ $(language_h) $(target_h) $(value_h) $(demangle_h) $(complaints_h) \ @@ -2003,8 +2005,10 @@ procfs.o: procfs.c $(defs_h) $(inferior_h) $(target_h) $(gdbcore_h) \ ptx4-nat.o: ptx4-nat.c $(defs_h) $(inferior_h) $(gdbcore_h) $(regcache_h) \ $(gregset_h) regcache.o: regcache.c $(defs_h) $(inferior_h) $(target_h) $(gdbarch_h) \ - $(gdbcmd_h) $(regcache_h) $(gdb_assert_h) $(gdb_string_h) \ - $(gdbcmd_h) + $(gdbcmd_h) $(regcache_h) $(reggroups_h) $(gdb_assert_h) \ + $(gdb_string_h) $(gdbcmd_h) +reggroups.o: reggroups.c $(defs_h) $(reggroups_h) $(gdbtypes_h) \ + $(gdb_assert_h) $(regcache_h) $(command_h) $(gdbcmd_h) remote-array.o: remote-array.c $(defs_h) $(gdbcore_h) $(target_h) \ $(gdb_string_h) $(command_h) $(serial_h) $(monitor_h) \ $(remote_utils_h) $(inferior_h) $(version_h) $(regcache_h) diff --git a/gdb/gdbarch.c b/gdb/gdbarch.c index b34e565..0e438f3 100644 --- a/gdb/gdbarch.c +++ b/gdb/gdbarch.c @@ -64,6 +64,7 @@ #include "gdb_assert.h" #include "gdb_string.h" #include "gdb-events.h" +#include "reggroups.h" /* Static function declarations */ @@ -274,6 +275,7 @@ struct gdbarch gdbarch_address_class_type_flags_ftype *address_class_type_flags; gdbarch_address_class_type_flags_to_name_ftype *address_class_type_flags_to_name; gdbarch_address_class_name_to_type_flags_ftype *address_class_name_to_type_flags; + gdbarch_register_reggroup_p_ftype *register_reggroup_p; }; @@ -437,6 +439,7 @@ struct gdbarch startup_gdbarch = 0, 0, 0, + default_register_reggroup_p, /* startup_gdbarch() */ }; @@ -568,6 +571,7 @@ gdbarch_alloc (const struct gdbarch_info *info, current_gdbarch->elf_make_msymbol_special = default_elf_make_msymbol_special; current_gdbarch->coff_make_msymbol_special = default_coff_make_msymbol_special; current_gdbarch->name_of_malloc = "malloc"; + current_gdbarch->register_reggroup_p = default_register_reggroup_p; /* gdbarch_alloc() */ return current_gdbarch; @@ -819,6 +823,9 @@ verify_gdbarch (struct gdbarch *gdbarch) /* Skip verify of address_class_type_flags, has predicate */ /* Skip verify of address_class_type_flags_to_name, has predicate */ /* Skip verify of address_class_name_to_type_flags, has predicate */ + if ((GDB_MULTI_ARCH > GDB_MULTI_ARCH_PARTIAL) + && (gdbarch->register_reggroup_p == default_register_reggroup_p)) + fprintf_unfiltered (log, "\n\tregister_reggroup_p"); buf = ui_file_xstrdup (log, &dummy); make_cleanup (xfree, buf); if (strlen (buf) > 0) @@ -853,6 +860,10 @@ gdbarch_dump (struct gdbarch *gdbarch, struct ui_file *file) (long) current_gdbarch->in_function_epilogue_p); if (GDB_MULTI_ARCH) fprintf_unfiltered (file, + "gdbarch_dump: register_reggroup_p = 0x%08lx\n", + (long) current_gdbarch->register_reggroup_p); + if (GDB_MULTI_ARCH) + fprintf_unfiltered (file, "gdbarch_dump: pseudo_register_read = 0x%08lx\n", (long) current_gdbarch->pseudo_register_read); if (GDB_MULTI_ARCH) @@ -5186,6 +5197,25 @@ set_gdbarch_address_class_name_to_type_flags (struct gdbarch *gdbarch, gdbarch->address_class_name_to_type_flags = address_class_name_to_type_flags; } +int +gdbarch_register_reggroup_p (struct gdbarch *gdbarch, int regnum, struct reggroup *reggroup) +{ + gdb_assert (gdbarch != NULL); + if (gdbarch->register_reggroup_p == 0) + internal_error (__FILE__, __LINE__, + "gdbarch: gdbarch_register_reggroup_p invalid"); + if (gdbarch_debug >= 2) + fprintf_unfiltered (gdb_stdlog, "gdbarch_register_reggroup_p called\n"); + return gdbarch->register_reggroup_p (gdbarch, regnum, reggroup); +} + +void +set_gdbarch_register_reggroup_p (struct gdbarch *gdbarch, + gdbarch_register_reggroup_p_ftype register_reggroup_p) +{ + gdbarch->register_reggroup_p = register_reggroup_p; +} + /* Keep a registry of per-architecture data-pointers required by GDB modules. */ diff --git a/gdb/gdbarch.h b/gdb/gdbarch.h index 524071a..3add874 100644 --- a/gdb/gdbarch.h +++ b/gdb/gdbarch.h @@ -47,6 +47,7 @@ struct value; struct objfile; struct minimal_symbol; struct regcache; +struct reggroup; extern struct gdbarch *current_gdbarch; @@ -2660,6 +2661,12 @@ typedef int (gdbarch_address_class_name_to_type_flags_ftype) (struct gdbarch *gd extern int gdbarch_address_class_name_to_type_flags (struct gdbarch *gdbarch, char *name, int *type_flags_ptr); extern void set_gdbarch_address_class_name_to_type_flags (struct gdbarch *gdbarch, gdbarch_address_class_name_to_type_flags_ftype *address_class_name_to_type_flags); +/* Is a register in a group */ + +typedef int (gdbarch_register_reggroup_p_ftype) (struct gdbarch *gdbarch, int regnum, struct reggroup *reggroup); +extern int gdbarch_register_reggroup_p (struct gdbarch *gdbarch, int regnum, struct reggroup *reggroup); +extern void set_gdbarch_register_reggroup_p (struct gdbarch *gdbarch, gdbarch_register_reggroup_p_ftype *register_reggroup_p); + extern struct gdbarch_tdep *gdbarch_tdep (struct gdbarch *gdbarch); diff --git a/gdb/gdbarch.sh b/gdb/gdbarch.sh index da0e760..1dd29f2 100755 --- a/gdb/gdbarch.sh +++ b/gdb/gdbarch.sh @@ -667,6 +667,8 @@ v::HAVE_NONSTEPPABLE_WATCHPOINT:int:have_nonsteppable_watchpoint::::0:0::0 F:2:ADDRESS_CLASS_TYPE_FLAGS:int:address_class_type_flags:int byte_size, int dwarf2_addr_class:byte_size, dwarf2_addr_class M:2:ADDRESS_CLASS_TYPE_FLAGS_TO_NAME:char *:address_class_type_flags_to_name:int type_flags:type_flags: M:2:ADDRESS_CLASS_NAME_TO_TYPE_FLAGS:int:address_class_name_to_type_flags:char *name, int *type_flags_ptr:name, type_flags_ptr +# Is a register in a group +m:::int:register_reggroup_p:int regnum, struct reggroup *reggroup:regnum, reggroup:::default_register_reggroup_p EOF } @@ -778,6 +780,7 @@ struct value; struct objfile; struct minimal_symbol; struct regcache; +struct reggroup; extern struct gdbarch *current_gdbarch; @@ -1253,6 +1256,7 @@ cat <<EOF #include "gdb_assert.h" #include "gdb_string.h" #include "gdb-events.h" +#include "reggroups.h" /* Static function declarations */ diff --git a/gdb/regcache.c b/gdb/regcache.c index 070651e..16a520c 100644 --- a/gdb/regcache.c +++ b/gdb/regcache.c @@ -26,6 +26,7 @@ #include "gdbarch.h" #include "gdbcmd.h" #include "regcache.h" +#include "reggroups.h" #include "gdb_assert.h" #include "gdb_string.h" #include "gdbcmd.h" /* For maintenanceprintlist. */ @@ -1479,7 +1480,7 @@ dump_endian_bytes (struct ui_file *file, enum bfd_endian endian, enum regcache_dump_what { - regcache_dump_none, regcache_dump_raw, regcache_dump_cooked + regcache_dump_none, regcache_dump_raw, regcache_dump_cooked, regcache_dump_groups }; static void @@ -1487,6 +1488,8 @@ regcache_dump (struct regcache *regcache, struct ui_file *file, enum regcache_dump_what what_to_dump) { struct cleanup *cleanups = make_cleanup (null_cleanup, NULL); + struct gdbarch *gdbarch = regcache->descr->gdbarch; + struct reggroup *const *groups = reggroups (gdbarch); int regnum; int footnote_nr = 0; int footnote_register_size = 0; @@ -1593,27 +1596,32 @@ regcache_dump (struct regcache *regcache, struct ui_file *file, } /* Type. */ - if (regnum < 0) - fprintf_unfiltered (file, " %-20s", "Type"); - else - { - static const char blt[] = "builtin_type"; - const char *t = TYPE_NAME (register_type (regcache->descr->gdbarch, - regnum)); - if (t == NULL) - { - char *n; - if (!footnote_register_type_name_null) - footnote_register_type_name_null = ++footnote_nr; - xasprintf (&n, "*%d", footnote_register_type_name_null); - make_cleanup (xfree, n); - t = n; - } - /* Chop a leading builtin_type. */ - if (strncmp (t, blt, strlen (blt)) == 0) - t += strlen (blt); - fprintf_unfiltered (file, " %-20s", t); - } + { + const char *t; + if (regnum < 0) + t = "Type"; + else + { + static const char blt[] = "builtin_type"; + t = TYPE_NAME (register_type (regcache->descr->gdbarch, regnum)); + if (t == NULL) + { + char *n; + if (!footnote_register_type_name_null) + footnote_register_type_name_null = ++footnote_nr; + xasprintf (&n, "*%d", footnote_register_type_name_null); + make_cleanup (xfree, n); + t = n; + } + /* Chop a leading builtin_type. */ + if (strncmp (t, blt, strlen (blt)) == 0) + t += strlen (blt); + } + fprintf_unfiltered (file, " %-15s", t); + } + + /* Leading space always present. */ + fprintf_unfiltered (file, " "); /* Value, raw. */ if (what_to_dump == regcache_dump_raw) @@ -1647,6 +1655,26 @@ regcache_dump (struct regcache *regcache, struct ui_file *file, } } + /* Group members. */ + if (what_to_dump == regcache_dump_groups) + { + if (regnum < 0) + fprintf_unfiltered (file, "Groups"); + else + { + int i; + const char *sep = ""; + for (i = 0; groups[i] != NULL; i++) + { + if (gdbarch_register_reggroup_p (gdbarch, regnum, groups[i])) + { + fprintf_unfiltered (file, "%s%s", sep, reggroup_name (groups[i])); + sep = ","; + } + } + } + } + fprintf_unfiltered (file, "\n"); } @@ -1696,6 +1724,12 @@ maintenance_print_cooked_registers (char *args, int from_tty) regcache_print (args, regcache_dump_cooked); } +static void +maintenance_print_register_groups (char *args, int from_tty) +{ + regcache_print (args, regcache_dump_groups); +} + void _initialize_regcache (void) { @@ -1728,5 +1762,10 @@ Takes an optional file parameter.", "Print the internal register configuration including cooked values.\ Takes an optional file parameter.", &maintenanceprintlist); + add_cmd ("register-groups", class_maintenance, + maintenance_print_register_groups, + "Print the internal register configuration including each register's group.\ +Takes an optional file parameter.", + &maintenanceprintlist); } diff --git a/gdb/reggroups.c b/gdb/reggroups.c new file mode 100644 index 0000000..8c3cbb7 --- /dev/null +++ b/gdb/reggroups.c @@ -0,0 +1,268 @@ +/* Register groupings for GDB, the GNU debugger. + + Copyright 2002 Free Software Foundation, Inc. + + Contributed by Red Hat. + + This file is part of GDB. + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. */ + +#include "defs.h" +#include "reggroups.h" +#include "gdbtypes.h" +#include "gdb_assert.h" +#include "regcache.h" +#include "command.h" +#include "gdbcmd.h" /* For maintenanceprintlist. */ + +/* Individual register groups. */ + +struct reggroup +{ + const char *name; + enum reggroup_type type; +}; + +struct reggroup * +reggroup_new (const char *name, enum reggroup_type type) +{ + struct reggroup *group = XMALLOC (struct reggroup); + group->name = name; + group->type = type; + return group; +} + +/* Register group attributes. */ + +const char * +reggroup_name (struct reggroup *group) +{ + return group->name; +} + +enum reggroup_type +reggroup_type (struct reggroup *group) +{ + return group->type; +} + +/* All the groups for a given architecture. */ + +struct reggroups +{ + int nr_group; + struct reggroup **group; +}; + +static struct gdbarch_data *reggroups_data; + +static void * +reggroups_init (struct gdbarch *gdbarch) +{ + struct reggroups *groups = XMALLOC (struct reggroups); + groups->nr_group = 0; + groups->group = NULL; + return groups; +} + +static void +reggroups_free (struct gdbarch *gdbarch, void *data) +{ + struct reggroups *groups = data; + xfree (groups->group); + xfree (groups); +} + +/* Add a register group (with attribute values) to the pre-defined + list. This function can be called during architecture + initialization and hence needs to handle NULL architecture groups. */ + +static void +add_group (struct reggroups *groups, struct reggroup *group) +{ + gdb_assert (group != NULL); + groups->nr_group++; + groups->group = xrealloc (groups->group, (sizeof (struct reggroup *) + * (groups->nr_group + 1))); + groups->group[groups->nr_group - 1] = group; + groups->group[groups->nr_group] = NULL; +} + +void +reggroup_add (struct gdbarch *gdbarch, struct reggroup *group) +{ + struct reggroups *groups = gdbarch_data (gdbarch, reggroups_data); + if (groups == NULL) + { + /* ULGH, called during architecture initialization. Patch + things up. */ + groups = reggroups_init (gdbarch); + set_gdbarch_data (gdbarch, reggroups_data, groups); + } + add_group (groups, group); +} + +/* The register groups for the current architecture. Mumble something + about the lifetime of the buffer.... */ + +static struct reggroups *default_groups; + +struct reggroup * const* +reggroups (struct gdbarch *gdbarch) +{ + struct reggroups *groups = gdbarch_data (gdbarch, reggroups_data); + /* Don't allow this function to be called during architecture + creation. */ + gdb_assert (groups != NULL); + if (groups->group == NULL) + return default_groups->group; + else + return groups->group; +} + +/* Is REGNUM a member of REGGROUP? */ +int +default_register_reggroup_p (struct gdbarch *gdbarch, int regnum, + struct reggroup *group) +{ + int vector_p; + int float_p; + int raw_p; + if (REGISTER_NAME (regnum) == NULL + || *REGISTER_NAME (regnum) == '\0') + return 0; + if (group == all_reggroup) + return 1; + vector_p = TYPE_VECTOR (register_type (gdbarch, regnum)); + float_p = TYPE_CODE (register_type (gdbarch, regnum)) == TYPE_CODE_FLT; + raw_p = regnum < gdbarch_num_regs (gdbarch); + if (group == float_reggroup) + return float_p; + if (group == vector_reggroup) + return vector_p; + if (group == general_reggroup) + return (!vector_p && !float_p); + if (group == save_reggroup || group == restore_reggroup) + return raw_p; + return 0; +} + +/* Dump out a table of register groups for the current architecture. */ + +static void +reggroups_dump (struct gdbarch *gdbarch, struct ui_file *file) +{ + struct reggroup *const *groups = reggroups (gdbarch); + int i = -1; + do + { + /* Group name. */ + { + const char *name; + if (i < 0) + name = "Group"; + else + name = reggroup_name (groups[i]); + fprintf_unfiltered (file, " %-10s", name); + } + + /* Group type. */ + { + const char *type; + if (i < 0) + type = "Type"; + else + { + switch (reggroup_type (groups[i])) + { + case USER_REGGROUP: + type = "user"; + break; + case INTERNAL_REGGROUP: + type = "internal"; + break; + default: + internal_error (__FILE__, __LINE__, "bad switch"); + } + } + fprintf_unfiltered (file, " %-10s", type); + } + + /* Note: If you change this, be sure to also update the + documentation. */ + + fprintf_unfiltered (file, "\n"); + i++; + } + while (groups[i] != NULL); +} + +static void +maintenance_print_reggroups (char *args, int from_tty) +{ + if (args == NULL) + reggroups_dump (current_gdbarch, gdb_stdout); + else + { + struct ui_file *file = gdb_fopen (args, "w"); + if (file == NULL) + perror_with_name ("maintenance print reggroups"); + reggroups_dump (current_gdbarch, file); + ui_file_delete (file); + } +} + +/* Pre-defined register groups. */ +static struct reggroup general_group = { "general", USER_REGGROUP }; +static struct reggroup float_group = { "float", USER_REGGROUP }; +static struct reggroup system_group = { "system", USER_REGGROUP }; +static struct reggroup vector_group = { "vector", USER_REGGROUP }; +static struct reggroup all_group = { "all", USER_REGGROUP }; +static struct reggroup save_group = { "save", INTERNAL_REGGROUP }; +static struct reggroup restore_group = { "restore", INTERNAL_REGGROUP }; + +struct reggroup *const general_reggroup = &general_group; +struct reggroup *const float_reggroup = &float_group; +struct reggroup *const system_reggroup = &system_group; +struct reggroup *const vector_reggroup = &vector_group; +struct reggroup *const all_reggroup = &all_group; +struct reggroup *const save_reggroup = &save_group; +struct reggroup *const restore_reggroup = &restore_group; + +void +_initialize_reggroup (void) +{ + reggroups_data = register_gdbarch_data (reggroups_init, reggroups_free); + + /* The pre-defined list of groups. */ + default_groups = reggroups_init (NULL); + add_group (default_groups, general_reggroup); + add_group (default_groups, float_reggroup); + add_group (default_groups, system_reggroup); + add_group (default_groups, vector_reggroup); + add_group (default_groups, all_reggroup); + add_group (default_groups, save_reggroup); + add_group (default_groups, restore_reggroup); + + + add_cmd ("reggroups", class_maintenance, + maintenance_print_reggroups, "\ +Print the internal register group names.\n\ +Takes an optional file parameter.", + &maintenanceprintlist); + +} diff --git a/gdb/reggroups.h b/gdb/reggroups.h new file mode 100644 index 0000000..0088a85 --- /dev/null +++ b/gdb/reggroups.h @@ -0,0 +1,61 @@ +/* Register groupings for GDB, the GNU debugger. + + Copyright 2002 Free Software Foundation, Inc. + + Contributed by Red Hat. + + This file is part of GDB. + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. */ + +#ifndef REGGROUPS_H +#define REGGROUPS_H + +struct gdbarch; +struct reggroup; + +enum reggroup_type { USER_REGGROUP, INTERNAL_REGGROUP }; + +/* Pre-defined, user visible, register groups. */ +extern struct reggroup *const general_reggroup; +extern struct reggroup *const float_reggroup; +extern struct reggroup *const system_reggroup; +extern struct reggroup *const vector_reggroup; +extern struct reggroup *const all_reggroup; + +/* Pre-defined, internal, register groups. */ +extern struct reggroup *const save_reggroup; +extern struct reggroup *const restore_reggroup; + +/* Create a new local register group. */ +extern struct reggroup *reggroup_new (const char *name, + enum reggroup_type type); + +/* Add a register group (with attribute values) to the pre-defined list. */ +extern void reggroup_add (struct gdbarch *gdbarch, struct reggroup *group); + +/* Register group attributes. */ +extern const char *reggroup_name (struct reggroup *reggroup); +extern enum reggroup_type reggroup_type (struct reggroup *reggroup); + +/* The register groups for the current architecture. */ +extern struct reggroup *const *reggroups (struct gdbarch *gdbarch); + +/* Is REGNUM a member of REGGROUP? */ +extern int default_register_reggroup_p (struct gdbarch *gdbarch, int regnum, + struct reggroup *reggroup); + +#endif |