This is the mail archive of the
gdb-patches@sources.redhat.com
mailing list for the GDB project.
[patch/rfc,rfa:ppc64] Add osabi wildcard support
- From: Andrew Cagney <ac131313 at redhat dot com>
- To: gdb-patches at sources dot redhat dot com
- Date: Thu, 23 Oct 2003 19:25:37 -0400
- Subject: [patch/rfc,rfa:ppc64] Add osabi wildcard support
Hello,
The attached patch adds the ability to specify a wildcard machine when
registering an OSABI / arch / machine. It then updates PPC64 GNU/Linux
to specify that wild card (-1) instead of zero as the default machine.
Looking at the PPC64 GNU/Linux code:
gdbarch_register_osabi (bfd_arch_powerpc, 0, GDB_OSABI_LINUX,
ppc_linux_init_abi);
I believe that the call is attempting to register ppc_linux_init_abi as
the OSABI handler for all arch/machine conbinations. The problem is
that machine "0" gets turned into bfd_mach_ppc or bfd_mach_ppc64
dependant on how GDB is built, and they are both incompatible with each
other and incompatible . And that in turn restricts the support to just
one half of the ISA family making it impossible for GDB to debug both 32
and 64 bit :-(
I know of two ways to fix this. First is the attached patch which
modifies osabi.[hc] so that a wildcard machine (-1) can be specified vis:
gdbarch_register_osabi (bfd_arch_powerpc, -1, GDB_OSABI_LINUX,
ppc_linux_init_abi);
and the second is to explicitly register both of these architecture
variants vis:
gdbarch_register_osabi (bfd_arch_powerpc, bfd_mach_ppc, ...
gdbarch_register_osabi (bfd_arch_powerpc, bfd_mach_ppc64, ...
(possibly also splitting ppc_linux_init_abi into ppc_linux_init_abi_32
and ppc_linux_init_abi_32).
There are pros and cons to both.
The former will always match, making the code somewhat future proof, the
later is far simplier.
preferences?
Andrew
PS: I'm also wondering if the existing ppc arch/machine table is
complete. I think it will indicate that e500 is "compatible" with "ppc"
when it is not.
2003-10-23 Andrew Cagney <cagney@redhat.com>
* ppc-linux-tdep.c (_initialize_ppc_linux_tdep): Pass a -ve wild
card machine to gdbarch_register_osabi.
* osabi.c (struct gdb_osabi_handler): Add the filed "arch",
mention that a NULL arch_info is a wild card.
(gdbarch_register_osabi): Change type of "machine" to long. Add a
-ve machine to the list as a wild card.
(gdbarch_init_osabi): Check for a wild card. Use the
bfd_arch_mach in "info".
* osabi.h (gdbarch_register_osabi): Add parameter names. Change
type of "machine" to long. Mention that -1 is a machine wild
card.
Index: doc/ChangeLog
2003-10-23 Andrew Cagney <cagney@redhat.com>
* gdbint.texinfo (Target Architecture Definition): Update
gdbarch_register_osabi removing "gdbarch" parameter and making
"machine" a long. Recommend -1 and not zero as a machine.
Index: osabi.c
===================================================================
RCS file: /cvs/src/src/gdb/osabi.c,v
retrieving revision 1.17
diff -u -r1.17 osabi.c
--- osabi.c 24 Aug 2003 11:47:18 -0000 1.17
+++ osabi.c 23 Oct 2003 22:45:04 -0000
@@ -89,10 +89,13 @@
}
/* Handler for a given architecture/OS ABI pair. There should be only
- one handler for a given OS ABI each architecture family. */
-struct gdb_osabi_handler
+ one handler for a given OS ABI each architecture family. When
+ "arch_info" is NULL, indicating a machine wild card, the "arch"
+ should be used. */
+struct gdb_osabi_handler
{
struct gdb_osabi_handler *next;
+ enum bfd_architecture arch;
const struct bfd_arch_info *arch_info;
enum gdb_osabi osabi;
void (*init_osabi)(struct gdbarch_info, struct gdbarch *);
@@ -101,35 +104,42 @@
static struct gdb_osabi_handler *gdb_osabi_handler_list;
void
-gdbarch_register_osabi (enum bfd_architecture arch, unsigned long machine,
+gdbarch_register_osabi (enum bfd_architecture arch, long machine,
enum gdb_osabi osabi,
void (*init_osabi)(struct gdbarch_info,
struct gdbarch *))
{
struct gdb_osabi_handler **handler_p;
- const struct bfd_arch_info *arch_info = bfd_lookup_arch (arch, machine);
+ const struct bfd_arch_info *arch_info;
const char **name_ptr;
/* Registering an OS ABI handler for "unknown" is not allowed. */
- if (osabi == GDB_OSABI_UNKNOWN)
+ gdb_assert (osabi != GDB_OSABI_UNKNOWN);
+
+ /* Look up the machine, or use NULL to indicate a wildcard match. */
+ if (machine >= 0)
{
- internal_error
- (__FILE__, __LINE__,
- "gdbarch_register_osabi: An attempt to register a handler for "
- "OS ABI \"%s\" for architecture %s was made. The handler will "
- "not be registered",
- gdbarch_osabi_name (osabi),
- bfd_printable_arch_mach (arch, machine));
- return;
+ /* NOTE: cagney/2003-10-23: The machine 0 returns the
+ architecture's default machine as specified by the current
+ target configuration. For instance, for PPC, the machine 0
+ returns either bfd_mach_ppc (GDB/BFD configured as
+ powerpc-*-*) or bfd_mach_ppc64 (GDB/BFD configured as
+ powerpc64-*-*). This may not be as you expect. */
+ arch_info = bfd_lookup_arch (arch, machine);
+ gdb_assert (arch_info != NULL);
}
+ else
+ arch_info = NULL;
- gdb_assert (arch_info);
-
- for (handler_p = &gdb_osabi_handler_list; *handler_p != NULL;
+ /* Search the hander list for the first wild-card entry (.arch_info
+ == NULL), or the end of the list. At the same time, when not
+ adding a wild card, check that the new entry isn't already in the
+ list. */
+ for (handler_p = &gdb_osabi_handler_list;
+ (*handler_p) != NULL && (*handler_p)->arch_info != NULL;
handler_p = &(*handler_p)->next)
{
- if ((*handler_p)->arch_info == arch_info
- && (*handler_p)->osabi == osabi)
+ if (arch_info != NULL && (*handler_p)->arch_info == arch_info)
{
internal_error
(__FILE__, __LINE__,
@@ -137,18 +147,31 @@
"has already been registered for architecture %s",
gdbarch_osabi_name (osabi),
arch_info->printable_name);
- /* If user wants to continue, override previous definition. */
- (*handler_p)->init_osabi = init_osabi;
- return;
}
}
- (*handler_p)
- = (struct gdb_osabi_handler *) xmalloc (sizeof (struct gdb_osabi_handler));
- (*handler_p)->next = NULL;
- (*handler_p)->arch_info = arch_info;
- (*handler_p)->osabi = osabi;
- (*handler_p)->init_osabi = init_osabi;
+ /* For wild card entries, walk the rest of the list checking that
+ there isn't a wild card duplicate. */
+ if (arch_info == NULL)
+ {
+ struct gdb_osabi_handler *p;
+ for (p = (*handler_p); p != NULL; p = p->next)
+ {
+ gdb_assert (p->arch_info == NULL);
+ gdb_assert (p->arch != arch);
+ }
+ }
+
+ /* Link the new entry in. */
+ {
+ struct gdb_osabi_handler *new_handler = XMALLOC (struct gdb_osabi_handler);
+ new_handler->next = (*handler_p);
+ (*handler_p) = new_handler;
+ new_handler->arch_info = arch_info;
+ new_handler->osabi = osabi;
+ new_handler->init_osabi = init_osabi;
+ new_handler->arch = arch;
+ }
/* Add this OS ABI to the list of enum values for "set osabi", if it isn't
already there. */
@@ -286,7 +309,6 @@
void
gdbarch_init_osabi (struct gdbarch_info info, struct gdbarch *gdbarch)
{
- const struct bfd_arch_info *arch_info = gdbarch_bfd_arch_info (gdbarch);
const struct bfd_arch_info *compatible;
struct gdb_osabi_handler *handler;
@@ -303,6 +325,17 @@
if (handler->osabi != info.osabi)
continue;
+ /* Wild card match. */
+ if (handler->arch_info == NULL)
+ {
+ if (handler->arch == info.bfd_arch_info->arch)
+ {
+ handler->init_osabi (info, gdbarch);
+ return;
+ }
+ continue;
+ }
+
/* Check whether the machine type and architecture of the
handler are compatible with the desired machine type and
architecture.
@@ -311,7 +344,8 @@
type that is compatible with the desired machine type. Right
now we simply return the first match, which is fine for now.
However, we might want to do something smarter in the future. */
- compatible = arch_info->compatible (arch_info, handler->arch_info);
+ compatible = info.bfd_arch_info->compatible (info.bfd_arch_info,
+ handler->arch_info);
if (compatible == handler->arch_info)
{
(*handler->init_osabi) (info, gdbarch);
@@ -319,13 +353,12 @@
}
}
- fprintf_filtered
- (gdb_stderr,
- "A handler for the OS ABI \"%s\" is not built into this "
- "configuration of GDB. "
- "Attempting to continue with the default %s settings",
- gdbarch_osabi_name (info.osabi),
- bfd_printable_arch_mach (arch_info->arch, arch_info->mach));
+ warning ("A handler for the OS ABI \"%s\" is not built into this "
+ "configuration of GDB, "
+ "Attempting to continue with the default %s settings\n",
+ gdbarch_osabi_name (info.osabi),
+ bfd_printable_arch_mach (info.bfd_arch_info->arch,
+ info.bfd_arch_info->mach));
}
Index: osabi.h
===================================================================
RCS file: /cvs/src/src/gdb/osabi.h,v
retrieving revision 1.8
diff -u -r1.8 osabi.h
--- osabi.h 4 Jan 2003 23:38:45 -0000 1.8
+++ osabi.h 23 Oct 2003 22:45:04 -0000
@@ -32,11 +32,14 @@
/* Register a handler for an OS ABI variant for a given architecture
and machine type. There should be only one handler for a given OS
- ABI for each architecture and machine type combination. */
-void gdbarch_register_osabi (enum bfd_architecture, unsigned long,
- enum gdb_osabi,
- void (*)(struct gdbarch_info,
- struct gdbarch *));
+ ABI for each architecture and machine type combination. The
+ machine -1 can be specified as a wild card and will match any
+ machine of the specified architecture (if there is no better
+ match). */
+void gdbarch_register_osabi (enum bfd_architecture arch, long machine,
+ enum gdb_osabi osabi,
+ void (*init_osabi)(struct gdbarch_info,
+ struct gdbarch *));
/* Lookup the OS ABI corresponding to the specified BFD. */
enum gdb_osabi gdbarch_lookup_osabi (bfd *);
Index: ppc-linux-tdep.c
===================================================================
RCS file: /cvs/src/src/gdb/ppc-linux-tdep.c,v
retrieving revision 1.44
diff -u -r1.44 ppc-linux-tdep.c
--- ppc-linux-tdep.c 22 Oct 2003 23:54:11 -0000 1.44
+++ ppc-linux-tdep.c 23 Oct 2003 22:45:05 -0000
@@ -1085,7 +1085,8 @@
void
_initialize_ppc_linux_tdep (void)
{
- gdbarch_register_osabi (bfd_arch_powerpc, 0, GDB_OSABI_LINUX,
+ /* Accept any machine type, 32-bit or 64-bit. */
+ gdbarch_register_osabi (bfd_arch_powerpc, -1, GDB_OSABI_LINUX,
ppc_linux_init_abi);
add_core_fns (&ppc_linux_regset_core_fns);
}
Index: doc/gdbint.texinfo
===================================================================
RCS file: /cvs/src/src/gdb/doc/gdbint.texinfo,v
retrieving revision 1.177
diff -u -r1.177 gdbint.texinfo
--- doc/gdbint.texinfo 20 Oct 2003 15:38:02 -0000 1.177
+++ doc/gdbint.texinfo 23 Oct 2003 22:45:09 -0000
@@ -2442,12 +2442,11 @@
Return the name of the OS ABI corresponding to @var{osabi}.
@end deftypefun
-@deftypefun void gdbarch_register_osabi (enum bfd_architecture @var{arch}, unsigned long @var{machine}, enum gdb_osabi @var{osabi}, void (*@var{init_osabi})(struct gdbarch_info @var{info}, struct gdbarch *@var{gdbarch}))
+@deftypefun void gdbarch_register_osabi (enum bfd_architecture @var{arch}, long @var{machine}, enum gdb_osabi @var{osabi}, void (*@var{init_osabi})(struct gdbarch_info @var{info}))
Register the OS ABI handler specified by @var{init_osabi} for the
architecture, machine type and OS ABI specified by @var{arch},
-@var{machine} and @var{osabi}. In most cases, a value of zero for the
-machine type, which implies the architecture's default machine type,
-will suffice.
+@var{machine} and @var{osabi}. In most cases, a value of -1 for the
+machine type, which implies a wild card match, will suffice.
@end deftypefun
@deftypefun void gdbarch_register_osabi_sniffer (enum bfd_architecture @var{arch}, enum bfd_flavour @var{flavour}, enum gdb_osabi (*@var{sniffer})(bfd *@var{abfd}))