Fix PR/18564 - regression in showing __thread so extern variable
Ensure tls variable address is not relocated, as the msym addr is an offset in the thread local storage of the shared library/object.
This commit is contained in:
parent
e68fa6f076
commit
5382cfab61
@ -1,3 +1,10 @@
|
||||
2015-09-15 Philippe Waroquiers <philippe.waroquiers@skynet.be>
|
||||
|
||||
* symtab.h (address_class): Document that TLS variables
|
||||
are handled by LOC_UNRESOLVED.
|
||||
* findvar.c (default_read_var_value): Don't relocate TLS variables.
|
||||
* printcmd.c (address_info): Don't relocate TLS variables.
|
||||
|
||||
2015-09-15 Pierre Langlois <pierre.langlois@arm.com>
|
||||
|
||||
* aarch64-tdep.c (decode_add_sub_imm): Use debug_printf.
|
||||
|
@ -739,14 +739,17 @@ default_read_var_value (struct symbol *var, const struct block *var_block,
|
||||
|
||||
if (msym == NULL)
|
||||
error (_("No global symbol \"%s\"."), SYMBOL_LINKAGE_NAME (var));
|
||||
if (overlay_debugging)
|
||||
addr = symbol_overlayed_address (BMSYMBOL_VALUE_ADDRESS (lookup_data.result),
|
||||
MSYMBOL_OBJ_SECTION (lookup_data.result.objfile,
|
||||
msym));
|
||||
else
|
||||
addr = BMSYMBOL_VALUE_ADDRESS (lookup_data.result);
|
||||
|
||||
obj_section = MSYMBOL_OBJ_SECTION (lookup_data.result.objfile, msym);
|
||||
/* Relocate address, unless there is no section or the variable is
|
||||
a TLS variable. */
|
||||
if (obj_section == NULL
|
||||
|| (obj_section->the_bfd_section->flags & SEC_THREAD_LOCAL) != 0)
|
||||
addr = MSYMBOL_VALUE_RAW_ADDRESS (msym);
|
||||
else
|
||||
addr = BMSYMBOL_VALUE_ADDRESS (lookup_data.result);
|
||||
if (overlay_debugging)
|
||||
addr = symbol_overlayed_address (addr, obj_section);
|
||||
/* Determine address of TLS variable. */
|
||||
if (obj_section
|
||||
&& (obj_section->the_bfd_section->flags & SEC_THREAD_LOCAL) != 0)
|
||||
addr = target_translate_tls_address (obj_section->objfile, addr);
|
||||
|
@ -1376,16 +1376,19 @@ address_info (char *exp, int from_tty)
|
||||
else
|
||||
{
|
||||
section = MSYMBOL_OBJ_SECTION (msym.objfile, msym.minsym);
|
||||
load_addr = BMSYMBOL_VALUE_ADDRESS (msym);
|
||||
|
||||
if (section
|
||||
&& (section->the_bfd_section->flags & SEC_THREAD_LOCAL) != 0)
|
||||
printf_filtered (_("a thread-local variable at offset %s "
|
||||
"in the thread-local storage for `%s'"),
|
||||
paddress (gdbarch, load_addr),
|
||||
objfile_name (section->objfile));
|
||||
{
|
||||
load_addr = MSYMBOL_VALUE_RAW_ADDRESS (msym.minsym);
|
||||
printf_filtered (_("a thread-local variable at offset %s "
|
||||
"in the thread-local storage for `%s'"),
|
||||
paddress (gdbarch, load_addr),
|
||||
objfile_name (section->objfile));
|
||||
}
|
||||
else
|
||||
{
|
||||
load_addr = BMSYMBOL_VALUE_ADDRESS (msym);
|
||||
printf_filtered (_("static storage at address "));
|
||||
fputs_filtered (paddress (gdbarch, load_addr), gdb_stdout);
|
||||
if (section_is_overlay (section))
|
||||
|
@ -584,7 +584,13 @@ enum address_class
|
||||
not find it in the full symbol table. But a reference to an external
|
||||
symbol in a local block shadowing other definition requires full symbol
|
||||
without possibly having its address available for LOC_STATIC. Testcase
|
||||
is provided as `gdb.dwarf2/dw2-unresolved.exp'. */
|
||||
is provided as `gdb.dwarf2/dw2-unresolved.exp'.
|
||||
|
||||
This is also used for thread local storage (TLS) variables. In this case,
|
||||
the address of the TLS variable must be determined when the variable is
|
||||
referenced, from the MSYMBOL_VALUE_RAW_ADDRESS, which is the offset
|
||||
of the TLS variable in the thread local storage of the shared
|
||||
library/object. */
|
||||
|
||||
LOC_UNRESOLVED,
|
||||
|
||||
|
@ -1,3 +1,9 @@
|
||||
2015-09-15 Philippe Waroquiers <philippe.waroquiers@skynet.be>
|
||||
|
||||
* gdb.threads/tls-so_extern.exp: New test file.
|
||||
* gdb.threads/tls-so_extern.c: New test file.
|
||||
* gdb.threads/tls-so_extern_main.c: New test file.
|
||||
|
||||
2015-09-15 Jan Kratochvil <jan.kratochvil@redhat.com>
|
||||
|
||||
* gdb.opt/solib-intra-step-lib.c: New file.
|
||||
|
19
gdb/testsuite/gdb.threads/tls-so_extern.c
Normal file
19
gdb/testsuite/gdb.threads/tls-so_extern.c
Normal file
@ -0,0 +1,19 @@
|
||||
/* This testcase is part of GDB, the GNU debugger.
|
||||
|
||||
Copyright 2015 Free Software Foundation, Inc.
|
||||
|
||||
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 3 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, see <http://www.gnu.org/licenses/>. */
|
||||
|
||||
__thread void *so_extern;
|
||||
__thread void *so_extern2;
|
81
gdb/testsuite/gdb.threads/tls-so_extern.exp
Normal file
81
gdb/testsuite/gdb.threads/tls-so_extern.exp
Normal file
@ -0,0 +1,81 @@
|
||||
# Copyright 2003-2015 Free Software Foundation, Inc.
|
||||
|
||||
# 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 3 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, see <http://www.gnu.org/licenses/>. */
|
||||
|
||||
# tls-so_extern.exp -- Expect script to test thread local storage in gdb, with
|
||||
# a variable defined in a shared library.
|
||||
|
||||
standard_testfile tls-so_extern_main.c
|
||||
set libfile tls-so_extern
|
||||
set srcfile_lib ${libfile}.c
|
||||
set binfile_lib [standard_output_file ${libfile}.so]
|
||||
|
||||
|
||||
# get the value of gcc_compiled
|
||||
if [get_compiler_info] {
|
||||
return -1
|
||||
}
|
||||
|
||||
|
||||
if { [gdb_compile_shlib_pthreads ${srcdir}/${subdir}/${srcfile_lib} ${binfile_lib} {debug}] != ""
|
||||
|| [gdb_compile_pthreads ${srcdir}/${subdir}/${srcfile} ${binfile} executable [list debug shlib=${binfile_lib}]] != ""} {
|
||||
return -1
|
||||
}
|
||||
|
||||
|
||||
clean_restart ${binfile}
|
||||
gdb_load_shlibs ${binfile_lib}
|
||||
|
||||
if ![runto_main] then {
|
||||
fail "Can't run to main"
|
||||
return 0
|
||||
}
|
||||
|
||||
gdb_test "print so_extern" "0x0" "print thread local storage variable"
|
||||
|
||||
gdb_test "ptype so_extern" "void \\*" "ptype of thread local storage variable"
|
||||
|
||||
gdb_test "info address so_extern" \
|
||||
"Symbol \\\"so_extern\\\" is a thread-local variable at offset 0x0 in the thread-local storage for .*tls-so_extern.*" \
|
||||
"print storage info for thread local storage variable"
|
||||
|
||||
set line_number [gdb_get_line_number "break here to check result"]
|
||||
|
||||
gdb_test "break $line_number" \
|
||||
"Breakpoint.*at.*file.*tls-so_extern_main.c.*line ${line_number}." \
|
||||
"break in thread function"
|
||||
gdb_test "continue" \
|
||||
"tls_ptr .* at .*:.*break here to check result.*" \
|
||||
"continue to break in tls_ptr called by main"
|
||||
gdb_test "print so_extern == &so_extern" \
|
||||
" = 1" \
|
||||
"check so_extern address in main"
|
||||
gdb_test "continue" \
|
||||
"tls_ptr .* at .*:.*break here to check result.*" \
|
||||
"continue to break in a thread"
|
||||
gdb_test "print so_extern == &so_extern" \
|
||||
" = 1" \
|
||||
"check so_extern address"
|
||||
gdb_test "continue" \
|
||||
"tls_ptr .* at .*:.*break here to check result.*" \
|
||||
"continue to break in the other thread"
|
||||
gdb_test "print so_extern == &so_extern" \
|
||||
" = 1" \
|
||||
"check so_extern address in other thread"
|
||||
gdb_test "continue" \
|
||||
"tls_ptr .* at .*:.*break here to check result.*" \
|
||||
"continue to break in tls_ptr called at end of main"
|
||||
gdb_test "print so_extern == &so_extern" \
|
||||
" = 1" \
|
||||
"check so_extern address at end of main"
|
47
gdb/testsuite/gdb.threads/tls-so_extern_main.c
Normal file
47
gdb/testsuite/gdb.threads/tls-so_extern_main.c
Normal file
@ -0,0 +1,47 @@
|
||||
/* This testcase is part of GDB, the GNU debugger.
|
||||
|
||||
Copyright 2015 Free Software Foundation, Inc.
|
||||
|
||||
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 3 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, see <http://www.gnu.org/licenses/>. */
|
||||
|
||||
#include <pthread.h>
|
||||
|
||||
extern __thread void *so_extern;
|
||||
extern __thread void *so_extern2;
|
||||
|
||||
static void *
|
||||
tls_ptr (void *p)
|
||||
{
|
||||
so_extern = &so_extern;
|
||||
so_extern2 = &so_extern2; /* break here to check result */
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
pthread_t threads[2];
|
||||
|
||||
tls_ptr (NULL);
|
||||
|
||||
pthread_create (&threads[0], NULL, tls_ptr, NULL);
|
||||
pthread_create (&threads[1], NULL, tls_ptr, NULL);
|
||||
|
||||
pthread_join (threads[0], NULL);
|
||||
pthread_join (threads[1], NULL);
|
||||
|
||||
tls_ptr (NULL);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user