From: Kevin Buettner Date: Thu, 31 Mar 2005 20:39:14 +0000 (+0000) Subject: Add TLS load module support for FRV. X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=186993b45845f14288bdb57ea581914decd9b024;p=binutils-gdb.git Add TLS load module support for FRV. --- diff --git a/gdb/ChangeLog b/gdb/ChangeLog index 7b94a88ff98..ac21981c11b 100644 --- a/gdb/ChangeLog +++ b/gdb/ChangeLog @@ -1,3 +1,13 @@ +2005-03-31 Kevin Buettner + + * solib-frv.c (struct lm_info): Add new field ``lm_addr''. + (main_lm_addr): New static global. + (frv_current_sos): Retain the link map address for each entry. + (frv_clear_solib): Clear main_lm_addr. + (frv_fetch_objfile_link_map): New function. + * frv-tdep.c (frv_gdbarch_init): Register TLS load module fetcher. + * frv-tdep.h (frv_fetch_objfile_link_map): Declare. + 2005-03-31 Kevin Buettner * gdbarch.sh (fetch_tls_load_module_address): New architecture method. diff --git a/gdb/frv-tdep.c b/gdb/frv-tdep.c index 32eb92e4018..20b4427c9c3 100644 --- a/gdb/frv-tdep.c +++ b/gdb/frv-tdep.c @@ -1564,6 +1564,10 @@ frv_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches) /* Set the fallback (prologue based) frame sniffer. */ frame_unwind_append_sniffer (gdbarch, frv_frame_sniffer); + /* Enable TLS support. */ + set_gdbarch_fetch_tls_load_module_address (gdbarch, + frv_fetch_objfile_link_map); + return gdbarch; } diff --git a/gdb/frv-tdep.h b/gdb/frv-tdep.h index 73122a6240b..e4665dfe912 100644 --- a/gdb/frv-tdep.h +++ b/gdb/frv-tdep.h @@ -111,3 +111,8 @@ CORE_ADDR frv_fdpic_find_global_pointer (CORE_ADDR addr); for that function, if one exists. If no canonical descriptor could be found, return 0. */ CORE_ADDR frv_fdpic_find_canonical_descriptor (CORE_ADDR entry_point); + + +/* Given an objfile, return the address of its link map. This value is + needed for TLS support. */ +CORE_ADDR frv_fetch_objfile_link_map (struct objfile *objfile); diff --git a/gdb/solib-frv.c b/gdb/solib-frv.c index 3fb542445fb..ecc791a3379 100644 --- a/gdb/solib-frv.c +++ b/gdb/solib-frv.c @@ -201,6 +201,8 @@ struct lm_info struct int_elf32_fdpic_loadmap *map; /* The GOT address for this link map entry. */ CORE_ADDR got_value; + /* The link map address, needed for frv_fetch_objfile_link_map(). */ + CORE_ADDR lm_addr; /* Cached dynamic symbol table and dynamic relocs initialized and used only by find_canonical_descriptor_in_load_object(). @@ -341,6 +343,9 @@ open_symbol_file_object (void *from_ttyp) /* Cached value for lm_base(), below. */ static CORE_ADDR lm_base_cache = 0; +/* Link map address for main module. */ +static CORE_ADDR main_lm_addr = 0; + /* Return the address from which the link map chain may be found. On the FR-V, this may be found in a number of ways. Assuming that the main executable has already been relocated, the easiest way to find @@ -467,6 +472,7 @@ frv_current_sos (void) sop->lm_info = xcalloc (1, sizeof (struct lm_info)); sop->lm_info->map = loadmap; sop->lm_info->got_value = got_addr; + sop->lm_info->lm_addr = lm_addr; /* Fetch the name. */ addr = extract_unsigned_integer (&lm_buf.l_name, sizeof (lm_buf.l_name)); @@ -491,6 +497,10 @@ frv_current_sos (void) *sos_next_ptr = sop; sos_next_ptr = &sop->next; } + else + { + main_lm_addr = lm_addr; + } lm_addr = extract_unsigned_integer (&lm_buf.l_next, sizeof (lm_buf.l_next)); } @@ -949,6 +959,7 @@ frv_clear_solib (void) lm_base_cache = 0; enable_break1_done = 0; enable_break2_done = 0; + main_lm_addr = 0; } static void @@ -1200,6 +1211,33 @@ find_canonical_descriptor_in_load_object return addr; } +/* Given an objfile, return the address of its link map. This value is + needed for TLS support. */ +CORE_ADDR +frv_fetch_objfile_link_map (struct objfile *objfile) +{ + struct so_list *so; + + /* Cause frv_current_sos() to be run if it hasn't been already. */ + if (main_lm_addr == 0) + solib_add (0, 0, 0, 1); + + /* frv_current_sos() will set main_lm_addr for the main executable. */ + if (objfile == symfile_objfile) + return main_lm_addr; + + /* The other link map addresses may be found by examining the list + of shared libraries. */ + for (so = master_so_list (); so; so = so->next) + { + if (so->objfile == objfile) + return so->lm_info->lm_addr; + } + + /* Not found! */ + return 0; +} + static struct target_so_ops frv_so_ops; void