summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCarmelo Amoroso <carmelo.amoroso@st.com>2011-01-21 15:04:47 +0100
committerCarmelo Amoroso <carmelo.amoroso@st.com>2011-01-21 15:04:47 +0100
commit2aee0efdec50321ffbe6891c593611461cc7b16e (patch)
treef6b3c17d1e3fddf14360317f4f18b86b0c83c045
parent8100a075b7dd7471562decb1860571a335d68b0d (diff)
parentb5dd2e706c1a098b2e8cd8df10500a3dde350efc (diff)
Merge remote branch 'origin/master' into prelink
* origin/master: bump version to 0.9.32-rc2-git release 0.9.32-rc2 nptl: Fix __USER_LABEL_PREFIX__ concatenatio nptl: fix start_thread() for _STACK_GROWS_UP ldso: get rid of _dl_lookup_hash Add protected symbols support for all architectures Revert "ldso/arm: Correct protected symbol resolution" Revert "ldso_sh: add support for protected symbols to SH" Revert "ldso/i386: support protected symbols" cris: Fix build issues syslog: fix 'everyone logs with user facility' __psfs_parse_spec: always use long int for %p buildsys: headers target should not depend on sysnum.h buildsys: fix make release target nptl: get rid of the last preprocessor warning when __ASSUME_TGKILL is not defined remove uClibc_ctype.h if !LOCALE Revert "Makefile.in: Add header to 'all' target" nptl: get rid of preprocessor warning when __ASSUME_TGKILL is not defined Conflicts: ldso/include/dl-hash.h ldso/ldso/arm/elfinterp.c ldso/ldso/avr32/elfinterp.c ldso/ldso/bfin/elfinterp.c ldso/ldso/cris/elfinterp.c ldso/ldso/dl-hash.c ldso/ldso/i386/elfinterp.c ldso/ldso/m68k/elfinterp.c ldso/ldso/mips/elfinterp.c ldso/ldso/powerpc/elfinterp.c ldso/ldso/sh/elfinterp.c ldso/ldso/sh64/elfinterp.c ldso/ldso/sparc/elfinterp.c ldso/ldso/x86_64/elfinterp.c ldso/ldso/xtensa/elfinterp.c ldso/libdl/libdl.c Signed-off-by: Carmelo Amoroso <carmelo.amoroso@st.com>
-rw-r--r--Makefile.in12
-rw-r--r--Rules.mak2
-rw-r--r--ldso/include/dl-hash.h23
-rw-r--r--ldso/ldso/arm/elfinterp.c23
-rw-r--r--ldso/ldso/avr32/elfinterp.c16
-rw-r--r--ldso/ldso/bfin/elfinterp.c22
-rw-r--r--ldso/ldso/cris/elfinterp.c12
-rw-r--r--ldso/ldso/dl-debug.c21
-rw-r--r--ldso/ldso/dl-hash.c28
-rw-r--r--ldso/ldso/i386/elfinterp.c23
-rw-r--r--ldso/ldso/ldso.c15
-rw-r--r--ldso/ldso/m68k/elfinterp.c21
-rw-r--r--ldso/ldso/mips/elfinterp.c41
-rw-r--r--ldso/ldso/powerpc/elfinterp.c27
-rw-r--r--ldso/ldso/sh/elfinterp.c50
-rw-r--r--ldso/ldso/sh64/elfinterp.c13
-rw-r--r--ldso/ldso/sparc/elfinterp.c32
-rw-r--r--ldso/ldso/x86_64/elfinterp.c28
-rw-r--r--ldso/ldso/xtensa/elfinterp.c17
-rw-r--r--ldso/libdl/libdl.c7
-rw-r--r--libc/misc/syslog/syslog.c2
-rw-r--r--libc/stdio/_scanf.c5
-rw-r--r--libc/sysdeps/linux/cris/sys/user.h81
-rw-r--r--libc/sysdeps/linux/cris/sysdep.h2
-rw-r--r--libpthread/nptl/allocatestack.c2
-rw-r--r--libpthread/nptl/pthreadP.h14
-rw-r--r--libpthread/nptl/pthread_cancel.c2
-rw-r--r--libpthread/nptl/pthread_create.c4
-rw-r--r--libpthread/nptl/sysdeps/pthread/createthread.c2
-rw-r--r--libpthread/nptl/sysdeps/unix/sysv/linux/pt-raise.c4
-rw-r--r--libpthread/nptl/sysdeps/unix/sysv/linux/pthread_kill.c2
-rw-r--r--libpthread/nptl/sysdeps/unix/sysv/linux/raise.c8
32 files changed, 318 insertions, 243 deletions
diff --git a/Makefile.in b/Makefile.in
index d7a5fca60..ab5ab7286 100644
--- a/Makefile.in
+++ b/Makefile.in
@@ -23,7 +23,7 @@ export KCONFIG_CONFIG
ifeq ($(HAVE_DOT_CONFIG),y)
-all: headers pregen libs
+all: pregen libs
libs: pregen
# In this section, we need .config
@@ -158,11 +158,12 @@ headers_clean-y += HEADERCLEAN_common
# libc/sysdeps/linux/Makefile.commonarch to headers-y
headers-y += $(target-headers-sysdep)
-headers: $(top_builddir)include/bits/uClibc_config.h $(top_builddir)include/bits/sysnum.h | subdirs
+headers: $(top_builddir)include/bits/uClibc_config.h | subdirs
subdirs: $(addprefix $(top_builddir),$(subdirs))
-pregen-headers: $(pregen-headers-y)
+pregen-headers: $(top_builddir)include/bits/sysnum.h $(pregen-headers-y)
pregen: pregen-headers
$(Q)$(if $(UCLIBC_HAS_LOCALE),$(MAKE) -C extra/locale locale_headers)
+
$(top_builddir)include/bits/sysnum.h: $(top_srcdir)extra/scripts/gen_bits_syscall_h.sh | $(top_builddir)include/bits
@$(disp_gen)
$(Q)set -e; \
@@ -241,7 +242,7 @@ HEADERS_RM-$(UCLIBC_HAS_GNU_ERROR) += error.h
HEADERS_RM-$(UCLIBC_HAS_GNU_GETOPT)$(UCLIBC_HAS_GETOPT_LONG) += getopt.h
HEADERS_RM-$(UCLIBC_HAS_IPV6) += netinet/ip6.h netinet/icmp6.h
HEADERS_RM-$(UCLIBC_HAS_BACKTRACE) += execinfo.h
-HEADERS_RM-$(UCLIBC_HAS_LOCALE) += iconv.h
+HEADERS_RM-$(UCLIBC_HAS_LOCALE) += iconv.h bits/uClibc_ctype.h
HEADERS_RM-$(UCLIBC_HAS_PTY) += pty.h
HEADERS_RM-$(UCLIBC_HAS_REALTIME) += mqueue.h bits/mqueue.h sched.h \
bits/sched.h \
@@ -260,7 +261,6 @@ HEADERS_RM-$(UCLIBC_HAS_WCHAR) += wchar.h wctype.h
HEADERS_RM-$(UCLIBC_HAS_WORDEXP) += wordexp.h
HEADERS_RM-$(UCLIBC_HAS_XATTR) += sys/xattr.h
HEADERS_RM-$(UCLIBC_HAS_XLOCALE) += xlocale.h
-HEADERS_RM-$(UCLIBC_HAS_LOCALE) += bits/uClibc_ctype.h
HEADERS_RM-$(UCLIBC_LINUX_SPECIFIC) += sys/fsuid.h sys/inotify.h sys/perm.h \
sys/personality.h \
sys/prctl.h \
@@ -476,7 +476,7 @@ distclean: clean
dist release:
$(RM) ../uClibc-$(VERSION).tar
- git archive HEAD --format=tar --prefix=uClibc-$(VERSION)/ \
+ git archive --format=tar --prefix=uClibc-$(VERSION)/ HEAD \
> ../uClibc-$(VERSION).tar
cat ../uClibc-$(VERSION).tar | bzip2 -c9 > ../uClibc-$(VERSION).tar.bz2
cat ../uClibc-$(VERSION).tar | xz -e -c8 > ../uClibc-$(VERSION).tar.xz
diff --git a/Rules.mak b/Rules.mak
index eecdc6426..8165ccabe 100644
--- a/Rules.mak
+++ b/Rules.mak
@@ -106,7 +106,7 @@ export RUNTIME_PREFIX DEVEL_PREFIX KERNEL_HEADERS MULTILIB_DIR
MAJOR_VERSION := 0
MINOR_VERSION := 9
SUBLEVEL := 32
-EXTRAVERSION :=-rc1-git
+EXTRAVERSION :=-rc2-git
VERSION := $(MAJOR_VERSION).$(MINOR_VERSION).$(SUBLEVEL)
ABI_VERSION := $(MAJOR_VERSION)
ifneq ($(EXTRAVERSION),)
diff --git a/ldso/include/dl-hash.h b/ldso/include/dl-hash.h
index b1927e49a..c7effc588 100644
--- a/ldso/include/dl-hash.h
+++ b/ldso/include/dl-hash.h
@@ -25,9 +25,9 @@ struct dyn_elf {
struct dyn_elf * prev;
};
-struct sym_val {
- const ElfW(Sym) *s;
- struct elf_resolve *m;
+struct symbol_ref {
+ const ElfW(Sym) *sym;
+ struct elf_resolve *tpnt;
};
/* Structure to describe a single list of scope elements. The lookup
@@ -156,20 +156,9 @@ extern struct elf_resolve * _dl_add_elf_hash_table(const char * libname,
DL_LOADADDR_TYPE loadaddr, unsigned long * dynamic_info,
unsigned long dynamic_addr, unsigned long dynamic_size);
-/* Only need extra arg with some configurations */
-#if !((defined(USE_TLS) && USE_TLS) || defined __FDPIC__)
-# define _dl_lookup_hash(n, r, m, s, c, tpnt) _dl_lookup_hash(n, r, m, s, c)
-# define _dl_find_hash(n, r, m, s, t, tpntp) _dl_find_hash(n, r, m, s, t)
-#endif
-extern char *_dl_lookup_hash(const char *name, struct r_scope_elem *scope,
- struct elf_resolve *mytpnt, struct sym_val *symbol, int type_class,
- struct elf_resolve **tpntp);
-static __always_inline char *_dl_find_hash(const char *name, struct r_scope_elem *scope,
- struct elf_resolve *mytpnt, struct sym_val *symbol, int type_class,
- struct elf_resolve **tpntp)
-{
- return _dl_lookup_hash(name, scope, mytpnt, symbol, type_class, tpntp);
-}
+extern char *_dl_find_hash(const char *name, struct r_scope_elem *scope,
+ struct elf_resolve *mytpnt, int type_class,
+ struct symbol_ref *symbol);
extern int _dl_linux_dynamic_link(void);
diff --git a/ldso/ldso/arm/elfinterp.c b/ldso/ldso/arm/elfinterp.c
index ee2d1e559..5ae85dd2e 100644
--- a/ldso/ldso/arm/elfinterp.c
+++ b/ldso/ldso/arm/elfinterp.c
@@ -70,7 +70,7 @@ unsigned long _dl_linux_resolver(struct elf_resolve *tpnt, int reloc_entry)
/* Get the address of the GOT entry */
new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope,
- tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ tpnt, ELF_RTYPE_CLASS_PLT, NULL);
if (unlikely(!new_addr)) {
_dl_dprintf(2, "%s: can't resolve symbol '%s'\n",
_dl_progname, symname);
@@ -189,22 +189,21 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct r_scope_elem *scope,
unsigned long *reloc_addr;
unsigned long symbol_addr;
const Elf32_Sym *def = 0;
+ struct symbol_ref sym_ref;
struct elf_resolve *def_mod = 0;
int goof = 0;
- struct sym_val current_value = { NULL, NULL };
-
reloc_addr = (unsigned long *) (tpnt->loadaddr + (unsigned long) rpnt->r_offset);
reloc_type = ELF32_R_TYPE(rpnt->r_info);
symtab_index = ELF32_R_SYM(rpnt->r_info);
symbol_addr = 0;
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
- if (symtab_index &&
- (ELF32_ST_VISIBILITY(symtab[symtab_index].st_other)
- != STV_PROTECTED)) {
+ if (symtab_index) {
symbol_addr = _dl_find_hash(strtab + symtab[symtab_index].st_name,
- scope, tpnt, &current_value, elf_machine_type_class(reloc_type), &def_mod);
+ scope, tpnt, elf_machine_type_class(reloc_type), &sym_ref);
/*
* We want to allow undefined references to weak symbols - this might
@@ -219,19 +218,15 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct r_scope_elem *scope,
}
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
+ def_mod = sym_ref.tpnt;
} else {
/*
* Relocs against STN_UNDEF are usually treated as using a
* symbol value of zero, and using the module containing the
* reloc itself.
*/
- if (symtab_index)
- symbol_addr = DL_FIND_HASH_VALUE(tpnt, elf_machine_type_class(reloc_type),
- &symtab[symtab_index]);
- else
- symbol_addr = symtab[symtab_index].st_value;
-
+ symbol_addr = symtab[symtab_index].st_value;
def_mod = tpnt;
}
diff --git a/ldso/ldso/avr32/elfinterp.c b/ldso/ldso/avr32/elfinterp.c
index e741fd60e..c3c5b4907 100644
--- a/ldso/ldso/avr32/elfinterp.c
+++ b/ldso/ldso/avr32/elfinterp.c
@@ -50,9 +50,9 @@ unsigned long _dl_linux_resolver(unsigned long got_offset, unsigned long *got)
strtab = (char *)(tpnt->dynamic_info[DT_STRTAB] + tpnt->loadaddr);
symname = strtab + sym->st_name;
- new_addr = (unsigned long) _dl_find_hash(strtab + sym->st_name,
+ new_addr = (unsigned long) _dl_find_hash(symname,
&_dl_loaded_modules->symbol_scope, tpnt,
- NULL, 0, resolver);
+ ELF_RTYPE_CLASS_PLT, NULL);
entry = (unsigned long *)(got + local_gotno + sym_index - gotsym);
*entry = new_addr;
@@ -127,20 +127,20 @@ static int _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
#if defined(__SUPPORT_LD_DEBUG__)
unsigned long old_val;
#endif
-
- struct sym_val current_value = { NULL, NULL };
+ struct symbol_ref sym_ref;
reloc_addr = (unsigned long *)(tpnt->loadaddr + rpnt->r_offset);
reloc_type = ELF32_R_TYPE(rpnt->r_info);
symtab_index = ELF32_R_SYM(rpnt->r_info);
symbol_addr = 0;
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
symname = strtab + symtab[symtab_index].st_name;
if (symtab_index) {
symbol_addr = (unsigned long)
- _dl_find_hash(strtab + symtab[symtab_index].st_name,
- scope, tpnt, &current_value,
- elf_machine_type_class(reloc_type), NULL);
+ _dl_find_hash(symname, scope, tpnt,
+ elf_machine_type_class(reloc_type), &sym_ref);
/* Allow undefined references to weak symbols */
if (!symbol_addr &&
@@ -151,7 +151,7 @@ static int _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
}
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
}
#if defined(__SUPPORT_LD_DEBUG__)
diff --git a/ldso/ldso/bfin/elfinterp.c b/ldso/ldso/bfin/elfinterp.c
index 466a3b4c1..42c113c50 100644
--- a/ldso/ldso/bfin/elfinterp.c
+++ b/ldso/ldso/bfin/elfinterp.c
@@ -46,11 +46,11 @@ _dl_linux_resolver (struct elf_resolve *tpnt, int reloc_entry)
ElfW(Sym) *symtab;
int symtab_index;
char *rel_addr;
- struct elf_resolve *new_tpnt;
char *new_addr;
struct funcdesc_value funcval;
struct funcdesc_value volatile *got_entry;
char *symname;
+ struct symbol_ref sym_ref;
rel_addr = (char *)tpnt->dynamic_info[DT_JMPREL];
@@ -59,15 +59,17 @@ _dl_linux_resolver (struct elf_resolve *tpnt, int reloc_entry)
symtab = (Elf32_Sym *) tpnt->dynamic_info[DT_SYMTAB];
strtab = (char *) tpnt->dynamic_info[DT_STRTAB];
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
symname= strtab + symtab[symtab_index].st_name;
/* Address of GOT entry fix up */
got_entry = (struct funcdesc_value *) DL_RELOC_ADDR(tpnt->loadaddr, this_reloc->r_offset);
/* Get the address to be used to fill in the GOT entry. */
- new_addr = _dl_lookup_hash(symname, &_dl_loaded_modules->symbol_scope, NULL, NULL, 0, &new_tpnt);
+ new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, NULL, 0, &sym_ref);
if (!new_addr) {
- new_addr = _dl_lookup_hash(symname, NULL, NULL, NULL, 0, &new_tpnt);
+ new_addr = _dl_find_hash(symname, NULL, NULL, 0, &sym_ref);
if (!new_addr) {
_dl_dprintf(2, "%s: can't resolve symbol '%s'\n",
_dl_progname, symname);
@@ -76,7 +78,7 @@ _dl_linux_resolver (struct elf_resolve *tpnt, int reloc_entry)
}
funcval.entry_point = new_addr;
- funcval.got_value = new_tpnt->loadaddr.got_value;
+ funcval.got_value = sym_ref.tpnt->loadaddr.got_value;
#if defined (__SUPPORT_LD_DEBUG__)
if (_dl_debug_bindings) {
@@ -165,14 +167,15 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct r_scope_elem *scope,
#if defined (__SUPPORT_LD_DEBUG__)
unsigned long old_val;
#endif
-
- struct sym_val current_value = { NULL, NULL };
+ struct symbol_ref sym_ref;
reloc_addr = (unsigned long *) DL_RELOC_ADDR(tpnt->loadaddr, rpnt->r_offset);
__asm__ ("" : "=r" (reloc_addr_packed) : "0" (reloc_addr));
reloc_type = ELF_R_TYPE(rpnt->r_info);
symtab_index = ELF_R_SYM(rpnt->r_info);
symbol_addr = 0;
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
symname = strtab + symtab[symtab_index].st_name;
if (ELF_ST_BIND (symtab[symtab_index].st_info) == STB_LOCAL) {
@@ -181,7 +184,7 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct r_scope_elem *scope,
} else {
symbol_addr = (unsigned long)
- _dl_lookup_hash(symname, scope, NULL, &current_value, 0, &symbol_tpnt);
+ _dl_find_hash(symname, scope, NULL, 0, &sym_ref);
/*
* We want to allow undefined references to weak symbols - this might
@@ -191,12 +194,13 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct r_scope_elem *scope,
if (!symbol_addr && ELF_ST_BIND(symtab[symtab_index].st_info) != STB_WEAK) {
_dl_dprintf (2, "%s: can't resolve symbol '%s'\n",
- _dl_progname, strtab + symtab[symtab_index].st_name);
+ _dl_progname, symname);
_dl_exit (1);
}
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
+ symbol_tpnt = sym_ref.tpnt;
}
#if defined (__SUPPORT_LD_DEBUG__)
diff --git a/ldso/ldso/cris/elfinterp.c b/ldso/ldso/cris/elfinterp.c
index 48802aa7c..c3af90b99 100644
--- a/ldso/ldso/cris/elfinterp.c
+++ b/ldso/ldso/cris/elfinterp.c
@@ -66,7 +66,7 @@ _dl_linux_resolver(struct elf_resolve *tpnt, int reloc_entry)
got_addr = (char **)instr_addr;
/* Get the address of the GOT entry. */
- new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
if (unlikely(!new_addr)) {
_dl_dprintf(2, "%s: Can't resolve symbol '%s'\n", _dl_progname, symname);
_dl_exit(1);
@@ -161,13 +161,14 @@ _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
#if defined (__SUPPORT_LD_DEBUG__)
unsigned long old_val;
#endif
-
- struct sym_val current_value = { NULL, NULL };
+ struct symbol_ref sym_ref;
reloc_addr = (unsigned long *)(intptr_t)(tpnt->loadaddr + (unsigned long)rpnt->r_offset);
reloc_type = ELF32_R_TYPE(rpnt->r_info);
symtab_index = ELF32_R_SYM(rpnt->r_info);
symbol_addr = 0;
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
symname = strtab + symtab[symtab_index].st_name;
if (symtab_index) {
@@ -176,17 +177,18 @@ _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
symbol_addr = (unsigned long)tpnt->loadaddr;
} else {
symbol_addr = (unsigned long)_dl_find_hash(symname, scope, tpnt,
- &current_value, elf_machine_type_class(reloc_type), NULL);
+ elf_machine_type_class(reloc_type), &sym_ref);
}
if (unlikely(!symbol_addr && ELF32_ST_BIND(symtab[symtab_index].st_info) != STB_WEAK)) {
_dl_dprintf(2, "%s: can't resolve symbol '%s'\n", _dl_progname, symname);
_dl_exit(1);
}
+
symbol_addr += rpnt->r_addend;
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
}
#if defined (__SUPPORT_LD_DEBUG__)
diff --git a/ldso/ldso/dl-debug.c b/ldso/ldso/dl-debug.c
index 47b32316e..8a548195f 100644
--- a/ldso/ldso/dl-debug.c
+++ b/ldso/ldso/dl-debug.c
@@ -109,7 +109,7 @@ static void debug_reloc(ElfW(Sym) *symtab, char *strtab, ELF_RELOC *rpnt)
static void
internal_function
_dl_debug_lookup (const char *undef_name, struct elf_resolve *undef_map,
- const ElfW(Sym) *ref, struct sym_val *value, int type_class)
+ const ElfW(Sym) *ref, struct symbol_ref *value, int type_class)
{
#ifdef SHARED
unsigned long symbol_addr;
@@ -117,8 +117,7 @@ _dl_debug_lookup (const char *undef_name, struct elf_resolve *undef_map,
if (_dl_trace_prelink)
{
int conflict = 0;
- struct elf_resolve *tls_tpnt = NULL;
- struct sym_val val = { NULL, NULL };
+ struct symbol_ref val = { NULL, NULL };
if ((_dl_trace_prelink_map == NULL
|| _dl_trace_prelink_map == _dl_loaded_modules)
@@ -126,14 +125,14 @@ _dl_debug_lookup (const char *undef_name, struct elf_resolve *undef_map,
{
symbol_addr = (unsigned long)
_dl_find_hash(undef_name, &undef_map->symbol_scope,
- undef_map, &val, type_class, &tls_tpnt);
+ undef_map, type_class, &val);
- if (val.s != value->s || val.m != value->m)
+ if (val.sym != value->sym || val.tpnt != value->tpnt)
conflict = 1;
}
- if (value->s
- && (__builtin_expect (ELF_ST_TYPE(value->s->st_info)
+ if (value->sym
+ && (__builtin_expect (ELF_ST_TYPE(value->sym->st_info)
== STT_TLS, 0)))
type_class = 4;
@@ -146,12 +145,12 @@ _dl_debug_lookup (const char *undef_name, struct elf_resolve *undef_map,
conflict ? "conflict" : "lookup",
(size_t) undef_map->mapaddr,
(size_t) (((ElfW(Addr)) ref) - undef_map->mapaddr),
- (size_t) (value->m ? value->m->mapaddr : 0),
- (size_t) (value->s ? value->s->st_value : 0));
+ (size_t) (value->tpnt ? value->tpnt->mapaddr : 0),
+ (size_t) (value->sym ? value->sym->st_value : 0));
if (conflict)
_dl_dprintf (1, "x %x %x ",
- (size_t) (val.m ? val.m->mapaddr : 0),
- (size_t) (val.s ? val.s->st_value : 0));
+ (size_t) (val.tpnt ? val.tpnt->mapaddr : 0),
+ (size_t) (val.sym ? val.sym->st_value : 0));
_dl_dprintf (1, "/%x %s\n", type_class, undef_name);
}
}
diff --git a/ldso/ldso/dl-hash.c b/ldso/ldso/dl-hash.c
index bb4c56b04..2ec883a86 100644
--- a/ldso/ldso/dl-hash.c
+++ b/ldso/ldso/dl-hash.c
@@ -267,8 +267,8 @@ _dl_lookup_sysv_hash(struct elf_resolve *tpnt, ElfW(Sym) *symtab, unsigned long
* This function resolves externals, and this is either called when we process
* relocations or when we call an entry in the PLT table for the first time.
*/
-char *_dl_lookup_hash(const char *name, struct r_scope_elem *scope, struct elf_resolve *mytpnt,
- struct sym_val *symbol, int type_class, struct elf_resolve **tpntp)
+char *_dl_find_hash(const char *name, struct r_scope_elem *scope, struct elf_resolve *mytpnt,
+ int type_class, struct symbol_ref *sym_ref)
{
struct elf_resolve *tpnt = NULL;
ElfW(Sym) *symtab;
@@ -284,6 +284,11 @@ char *_dl_lookup_hash(const char *name, struct r_scope_elem *scope, struct elf_r
unsigned long gnu_hash_number = _dl_gnu_hash((const unsigned char *)name);
#endif
+ if ((sym_ref) && (sym_ref->sym) && (ELF32_ST_VISIBILITY(sym_ref->sym->st_other) == STV_PROTECTED)) {
+ sym = sym_ref->sym;
+ if (mytpnt)
+ tpnt = mytpnt;
+ } else
for (loop_scope = scope; loop_scope && !sym; loop_scope = loop_scope->next) {
for (i = 0; i < loop_scope->r_nlist; i++) {
tpnt = loop_scope->r_list[i];
@@ -338,16 +343,15 @@ char *_dl_lookup_hash(const char *name, struct r_scope_elem *scope, struct elf_r
}
if (sym) {
- if (symbol) {
- symbol->s = sym;
- symbol->m = tpnt;
+ if (sym_ref) {
+ sym_ref->sym = sym;
+ sym_ref->tpnt = tpnt;
}
/* At this point we have found the requested symbol, do binding */
#if defined(USE_TLS) && USE_TLS
if (ELF_ST_TYPE(sym->st_info) == STT_TLS) {
- _dl_assert(tpntp != NULL);
- *tpntp = tpnt;
-
+ _dl_assert(sym_ref != NULL);
+ sym_ref->tpnt = tpnt;
return (char *)sym->st_value;
}
#endif
@@ -363,8 +367,8 @@ char *_dl_lookup_hash(const char *name, struct r_scope_elem *scope, struct elf_r
#endif
case STB_GLOBAL:
#ifdef __FDPIC__
- if (tpntp)
- *tpntp = tpnt;
+ if (sym_ref)
+ sym_ref->tpnt = tpnt;
#endif
return (char *)DL_FIND_HASH_VALUE(tpnt, type_class, sym);
default: /* Local symbols not handled here */
@@ -372,8 +376,8 @@ char *_dl_lookup_hash(const char *name, struct r_scope_elem *scope, struct elf_r
}
}
#ifdef __FDPIC__
- if (tpntp)
- *tpntp = tpnt;
+ if (sym_ref)
+ sym_ref->tpnt = tpnt;
#endif
return weak_result;
}
diff --git a/ldso/ldso/i386/elfinterp.c b/ldso/ldso/i386/elfinterp.c
index 0c821ce8b..33c14402a 100644
--- a/ldso/ldso/i386/elfinterp.c
+++ b/ldso/ldso/i386/elfinterp.c
@@ -71,7 +71,7 @@ _dl_linux_resolver(struct elf_resolve *tpnt, int reloc_entry)
got_addr = (char **)instr_addr;
/* Get the address of the GOT entry. */
- new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
if (unlikely(!new_addr)) {
_dl_dprintf(2, "%s: can't resolve symbol '%s' in lib '%s'.\n", _dl_progname, symname, tpnt->libname);
_dl_exit(1);
@@ -168,20 +168,19 @@ _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
#if defined (__SUPPORT_LD_DEBUG__)
unsigned long old_val;
#endif
-
- struct sym_val current_value = { NULL, NULL };
+ struct symbol_ref sym_ref;
reloc_addr = (unsigned long *)(intptr_t)(tpnt->loadaddr + (unsigned long)rpnt->r_offset);
reloc_type = ELF32_R_TYPE(rpnt->r_info);
symtab_index = ELF32_R_SYM(rpnt->r_info);
symbol_addr = 0;
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
symname = strtab + symtab[symtab_index].st_name;
- if (symtab_index &&
- (ELF32_ST_VISIBILITY(symtab[symtab_index].st_other)
- != STV_PROTECTED)) {
+ if (symtab_index) {
symbol_addr = (unsigned long)_dl_find_hash(symname, scope, tpnt,
- &current_value, elf_machine_type_class(reloc_type), &tls_tpnt);
+ elf_machine_type_class(reloc_type), &sym_ref);
/*
* We want to allow undefined references to weak symbols - this
@@ -191,16 +190,12 @@ _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
if (unlikely(!symbol_addr && (ELF_ST_TYPE(symtab[symtab_index].st_info) != STT_TLS)
&& ELF32_ST_BIND(symtab[symtab_index].st_info) != STB_WEAK))
return 1;
-
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
+ tls_tpnt = sym_ref.tpnt;
} else {
- if (symtab_index)
- symbol_addr = DL_FIND_HASH_VALUE(tpnt, elf_machine_type_class(reloc_type),
- &symtab[symtab_index]);
- else
- symbol_addr = symtab[symtab_index].st_value;
+ symbol_addr = symtab[symtab_index].st_value;
tls_tpnt = tpnt;
}
diff --git a/ldso/ldso/ldso.c b/ldso/ldso/ldso.c
index e0d323a9f..2ff441194 100644
--- a/ldso/ldso/ldso.c
+++ b/ldso/ldso/ldso.c
@@ -380,7 +380,7 @@ void *_dl_get_ready_to_run(struct elf_resolve *tpnt, DL_LOADADDR_TYPE load_addr,
ElfW(Phdr) *ppnt;
ElfW(Dyn) *dpnt;
char *lpntstr;
- unsigned int i, cnt, k, nscope_elem;
+ unsigned int i, cnt, nscope_elem;
int unlazy = 0, trace_loaded_objects = 0;
struct dyn_elf *rpnt;
struct elf_resolve *tcurr;
@@ -1128,6 +1128,7 @@ of this helper program; chances are you did not intend to run this program.\n\
local_scope = _dl_malloc(nscope_elem * sizeof(struct elf_resolve *));
i = 1;
for (tcurr = _dl_loaded_modules->next; tcurr; tcurr = tcurr->next) {
+ unsigned int k;
cnt = _dl_build_local_scope(local_scope, scope_elem_list[i++]);
tcurr->symbol_scope.r_list = _dl_malloc(cnt * sizeof(struct elf_resolve *));
tcurr->symbol_scope.r_nlist = cnt;
@@ -1312,7 +1313,7 @@ of this helper program; chances are you did not intend to run this program.\n\
* ld.so.1, so we have to look up each symbol individually.
*/
- _dl_envp = (unsigned long *) (intptr_t) _dl_find_hash(__C_SYMBOL_PREFIX__ "__environ", global_scope, NULL, NULL, 0, NULL);
+ _dl_envp = (unsigned long *) (intptr_t) _dl_find_hash(__C_SYMBOL_PREFIX__ "__environ", global_scope, NULL, 0, NULL);
if (_dl_envp)
*_dl_envp = (unsigned long) envp;
@@ -1368,21 +1369,21 @@ of this helper program; chances are you did not intend to run this program.\n\
/* Find the real malloc function and make ldso functions use that from now on */
_dl_malloc_function = (void* (*)(size_t)) (intptr_t) _dl_find_hash(__C_SYMBOL_PREFIX__ "malloc",
- global_scope, NULL, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ global_scope, NULL, ELF_RTYPE_CLASS_PLT, NULL);
#if defined(USE_TLS) && USE_TLS
/* Find the real functions and make ldso functions use them from now on */
_dl_calloc_function = (void* (*)(size_t, size_t)) (intptr_t)
- _dl_find_hash(__C_SYMBOL_PREFIX__ "calloc", global_scope, NULL, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ _dl_find_hash(__C_SYMBOL_PREFIX__ "calloc", global_scope, NULL, ELF_RTYPE_CLASS_PLT, NULL);
_dl_realloc_function = (void* (*)(void *, size_t)) (intptr_t)
- _dl_find_hash(__C_SYMBOL_PREFIX__ "realloc", global_scope, NULL, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ _dl_find_hash(__C_SYMBOL_PREFIX__ "realloc", global_scope, NULL, ELF_RTYPE_CLASS_PLT, NULL);
_dl_free_function = (void (*)(void *)) (intptr_t)
- _dl_find_hash(__C_SYMBOL_PREFIX__ "free", global_scope, NULL, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ _dl_find_hash(__C_SYMBOL_PREFIX__ "free", global_scope, NULL, ELF_RTYPE_CLASS_PLT, NULL);
_dl_memalign_function = (void* (*)(size_t, size_t)) (intptr_t)
- _dl_find_hash(__C_SYMBOL_PREFIX__ "memalign", global_scope, NULL, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ _dl_find_hash(__C_SYMBOL_PREFIX__ "memalign", global_scope, NULL, ELF_RTYPE_CLASS_PLT, NULL);
#endif
diff --git a/ldso/ldso/m68k/elfinterp.c b/ldso/ldso/m68k/elfinterp.c
index 195dba5e5..8ad4ae58b 100644
--- a/ldso/ldso/m68k/elfinterp.c
+++ b/ldso/ldso/m68k/elfinterp.c
@@ -70,7 +70,7 @@ _dl_linux_resolver(struct elf_resolve *tpnt, int reloc_entry)
got_addr = (char **)instr_addr;
/* Get the address of the GOT entry. */
- new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
if (unlikely(!new_addr)) {
_dl_dprintf(2, "%s: Can't resolve symbol '%s'\n", _dl_progname, symname);
_dl_exit(1);
@@ -157,37 +157,36 @@ _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
int reloc_type;
int symtab_index;
char *symname;
- ElfW(Sym) *sym;
+ struct symbol_ref sym_ref;
ElfW(Addr) *reloc_addr;
ElfW(Addr) symbol_addr;
#if defined (__SUPPORT_LD_DEBUG__)
ElfW(Addr) old_val;
#endif
- struct sym_val current_value = { NULL, NULL };
-
reloc_addr = (ElfW(Addr)*)(tpnt->loadaddr + (unsigned long)rpnt->r_offset);
reloc_type = ELF_R_TYPE(rpnt->r_info);
symtab_index = ELF_R_SYM(rpnt->r_info);
- sym = &symtab[symtab_index];
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
symbol_addr = 0;
- symname = strtab + sym->st_name;
+ symname = strtab + sym_ref.sym->st_name;
if (symtab_index) {
symbol_addr = (ElfW(Addr))_dl_find_hash(symname, scope, tpnt,
- &current_value, elf_machine_type_class(reloc_type), NULL);
+ elf_machine_type_class(reloc_type), &sym_ref);
/*
* We want to allow undefined references to weak symbols - this
* might have been intentional. We should not be linking local
* symbols here, so all bases should be covered.
*/
- if (unlikely(!symbol_addr && ELF_ST_BIND(sym->st_info) != STB_WEAK)) {
+ if (unlikely(!symbol_addr && ELF_ST_BIND(sym_ref.sym->st_info) != STB_WEAK)) {
_dl_dprintf(2, "%s: can't resolve symbol '%s'\n", _dl_progname, symname);
_dl_exit(1);
}
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
}
#if defined (__SUPPORT_LD_DEBUG__)
@@ -235,12 +234,12 @@ _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
if (_dl_debug_move)
_dl_dprintf(_dl_debug_file,
"\t%s move %d bytes from %x to %x\n",
- symname, sym->st_size,
+ symname, sym_ref.sym->st_size,
symbol_addr, reloc_addr);
#endif
_dl_memcpy ((void *) reloc_addr,
(void *) symbol_addr,
- sym->st_size);
+ sym_ref.sym->st_size);
} else
_dl_dprintf(_dl_debug_file, "no symbol_addr to copy !?\n");
break;
diff --git a/ldso/ldso/mips/elfinterp.c b/ldso/ldso/mips/elfinterp.c
index 2a433e282..3ca403609 100644
--- a/ldso/ldso/mips/elfinterp.c
+++ b/ldso/ldso/mips/elfinterp.c
@@ -56,7 +56,7 @@ unsigned long __dl_runtime_resolve(unsigned long sym_index,
symname = strtab + sym->st_name;
new_addr = (unsigned long) _dl_find_hash(symname,
- &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
if (unlikely(!new_addr)) {
_dl_dprintf (2, "%s: can't resolve symbol '%s'\n",
_dl_progname, symname);
@@ -111,7 +111,7 @@ __dl_runtime_pltresolve(struct elf_resolve *tpnt, int reloc_entry)
got_addr = (char **)instr_addr;
/* Get the address of the GOT entry. */
- new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
if (unlikely(!new_addr)) {
_dl_dprintf(2, "%s: can't resolve symbol '%s' in lib '%s'.\n", _dl_progname, symname, tpnt->libname);
_dl_exit(1);
@@ -161,8 +161,7 @@ int _dl_parse_relocation_information(struct dyn_elf *xpnt,
unsigned long old_val=0;
#endif
- struct sym_val current_value = { NULL, NULL };
-
+ struct symbol_ref sym_ref = { NULL, NULL };
/* Now parse the relocation information */
rel_size = rel_size / sizeof(ElfW(Rel));
rpnt = (ELF_RELOC *) rel_addr;
@@ -171,6 +170,7 @@ int _dl_parse_relocation_information(struct dyn_elf *xpnt,
strtab = (char *) tpnt->dynamic_info[DT_STRTAB];
got = (unsigned long *) tpnt->dynamic_info[DT_PLTGOT];
+
for (i = 0; i < rel_size; i++, rpnt++) {
reloc_addr = (unsigned long *) (tpnt->loadaddr +
(unsigned long) rpnt->r_offset);
@@ -189,13 +189,13 @@ int _dl_parse_relocation_information(struct dyn_elf *xpnt,
if (reloc_type == R_MIPS_JUMP_SLOT || reloc_type == R_MIPS_COPY) {
symbol_addr = (unsigned long)_dl_find_hash(symname,
scope,
- tpnt, &current_value,
- elf_machine_type_class(reloc_type), NULL);
+ tpnt,
+ elf_machine_type_class(reloc_type), &sym_ref);
if (unlikely(!symbol_addr && ELF32_ST_BIND(symtab[symtab_index].st_info) != STB_WEAK))
return 1;
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
}
if (!symtab_index) {
/* Relocs against STN_UNDEF are usually treated as using a
@@ -217,23 +217,26 @@ int _dl_parse_relocation_information(struct dyn_elf *xpnt,
case R_MIPS_TLS_TPREL32:
# endif
{
- struct elf_resolve *tpnt_tls = NULL;
+ struct elf_resolve *tls_tpnt = NULL;
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
if (ELF32_ST_BIND(symtab[symtab_index].st_info) != STB_LOCAL) {
symbol_addr = (unsigned long) _dl_find_hash(symname, scope,
- tpnt, &current_value, elf_machine_type_class(reloc_type), &tpnt_tls);
+ tpnt, elf_machine_type_class(reloc_type), &sym_ref);
+ tls_tpnt = sym_ref.tpnt;
}
- /* In case of a TLS reloc, tpnt_tls NULL means we have an 'anonymous'
+ /* In case of a TLS reloc, tls_tpnt NULL means we have an 'anonymous'
symbol. This is the case for a static tls variable, so the lookup
module is just that one is referencing the tls variable. */
- if (!tpnt_tls)
- tpnt_tls = tpnt;
+ if (!tls_tpnt)
+ tls_tpnt = tpnt;
switch (reloc_type) {
case R_MIPS_TLS_DTPMOD64:
case R_MIPS_TLS_DTPMOD32:
- if (tpnt_tls)
- *(ElfW(Word) *)reloc_addr = tpnt_tls->l_tls_modid;
+ if (tls_tpnt)
+ *(ElfW(Word) *)reloc_addr = tls_tpnt->l_tls_modid;
#ifdef __SUPPORT_LD_DEBUG__
_dl_dprintf(2, "TLS_DTPMOD : %s, %d, %d\n",
symname, old_val, *((unsigned int *)reloc_addr));
@@ -252,9 +255,9 @@ int _dl_parse_relocation_information(struct dyn_elf *xpnt,
case R_MIPS_TLS_TPREL32:
case R_MIPS_TLS_TPREL64:
- CHECK_STATIC_TLS((struct link_map *)tpnt_tls);
+ CHECK_STATIC_TLS((struct link_map *)tls_tpnt);
*(ElfW(Word) *)reloc_addr +=
- TLS_TPREL_VALUE (tpnt_tls, symbol_addr);
+ TLS_TPREL_VALUE (tls_tpnt, symbol_addr);
#ifdef __SUPPORT_LD_DEBUG__
_dl_dprintf(2, "TLS_TPREL : %s, %x, %x\n",
symname, old_val, *((unsigned int *)reloc_addr));
@@ -362,12 +365,12 @@ void _dl_perform_mips_global_got_relocations(struct elf_resolve *tpnt, int lazy)
}
else {
*got_entry = (unsigned long) _dl_find_hash(strtab +
- sym->st_name, &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ sym->st_name, &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
}
}
else if (sym->st_shndx == SHN_COMMON) {
*got_entry = (unsigned long) _dl_find_hash(strtab +
- sym->st_name, &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ sym->st_name, &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
}
else if (ELF_ST_TYPE(sym->st_info) == STT_FUNC &&
*got_entry != sym->st_value && tmp_lazy) {
@@ -379,7 +382,7 @@ void _dl_perform_mips_global_got_relocations(struct elf_resolve *tpnt, int lazy)
}
else {
*got_entry = (unsigned long) _dl_find_hash(strtab +
- sym->st_name, &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ sym->st_name, &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
}
got_entry++;
diff --git a/ldso/ldso/powerpc/elfinterp.c b/ldso/ldso/powerpc/elfinterp.c
index 043534ed1..78085ecb0 100644
--- a/ldso/ldso/powerpc/elfinterp.c
+++ b/ldso/ldso/powerpc/elfinterp.c
@@ -139,7 +139,7 @@ unsigned long _dl_linux_resolver(struct elf_resolve *tpnt, int reloc_entry)
/* Get the address of the GOT entry */
finaladdr = (Elf32_Addr) _dl_find_hash(symname,
- &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
if (unlikely(!finaladdr)) {
_dl_dprintf(2, "%s: can't resolve symbol '%s' in lib '%s'.\n", _dl_progname, symname, tpnt->libname);
_dl_exit(1);
@@ -187,7 +187,7 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct r_scope_elem *scope,
{
int reloc_type;
int symtab_index;
- ElfW(Sym) *sym;
+ struct symbol_ref sym_ref;
Elf32_Addr *reloc_addr;
Elf32_Addr finaladdr;
struct elf_resolve *tls_tpnt = NULL;
@@ -197,33 +197,32 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct r_scope_elem *scope,
unsigned long old_val;
#endif
- struct sym_val current_value = { NULL, NULL };
-
symbol_addr = tpnt->loadaddr; /* For R_PPC_RELATIVE */
reloc_addr = (Elf32_Addr *)(intptr_t) (symbol_addr + (unsigned long) rpnt->r_offset);
reloc_type = ELF32_R_TYPE(rpnt->r_info);
symtab_index = ELF32_R_SYM(rpnt->r_info);
- sym = &symtab[symtab_index];
- symname = strtab + sym->st_name;
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
+ symname = strtab + sym_ref.sym->st_name;
if (symtab_index) {
symbol_addr = (unsigned long) _dl_find_hash(symname, scope, tpnt,
- &current_value, elf_machine_type_class(reloc_type), &tls_tpnt);
+ elf_machine_type_class(reloc_type), &sym_ref);
/* We want to allow undefined references to weak symbols - this might
* have been intentional. We should not be linking local symbols
* here, so all bases should be covered.
*/
if (unlikely(!symbol_addr
- && (ELF32_ST_TYPE(sym->st_info) != STT_TLS
- && ELF32_ST_BIND(sym->st_info) != STB_WEAK)))
+ && (ELF32_ST_TYPE(sym_ref.sym->st_info) != STT_TLS
+ && ELF32_ST_BIND(sym_ref.sym->st_info) != STB_WEAK)))
return 1;
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
+ tls_tpnt = sym_ref.tpnt;
} else {
- symbol_addr = sym->st_value;
+ symbol_addr = sym_ref.sym->st_value;
tls_tpnt = tpnt;
}
-
#if defined (__SUPPORT_LD_DEBUG__)
old_val = *reloc_addr;
#endif
@@ -271,10 +270,10 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct r_scope_elem *scope,
#if defined (__SUPPORT_LD_DEBUG__)
if (_dl_debug_move)
_dl_dprintf(_dl_debug_file,"\n%s move %x bytes from %x to %x",
- symname, sym->st_size,
+ symname, sym_ref.sym->st_size,
symbol_addr, reloc_addr);
#endif
- _dl_memcpy((char *) reloc_addr, (char *) finaladdr, sym->st_size);
+ _dl_memcpy((char *) reloc_addr, (char *) finaladdr, sym_ref.sym->st_size);
goto out_nocode; /* No code code modified */
case R_PPC_ADDR16_HA:
finaladdr += 0x8000; /* fall through. */
diff --git a/ldso/ldso/sh/elfinterp.c b/ldso/ldso/sh/elfinterp.c
index 928a84b40..293bfe31e 100644
--- a/ldso/ldso/sh/elfinterp.c
+++ b/ldso/ldso/sh/elfinterp.c
@@ -69,7 +69,7 @@ unsigned long _dl_linux_resolver(struct elf_resolve *tpnt, int reloc_entry)
got_addr = (char **) instr_addr;
/* Get the address of the GOT entry */
- new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
if (unlikely(!new_addr)) {
_dl_dprintf(2, "%s: can't resolve symbol '%s'\n", _dl_progname, symname);
@@ -161,42 +161,38 @@ _dl_do_reloc (struct elf_resolve *tpnt, struct r_scope_elem *scope,
#endif
struct elf_resolve *tls_tpnt = NULL;
- struct sym_val current_value = { NULL, NULL };
+ struct symbol_ref sym_ref;
reloc_addr = (unsigned long *)(intptr_t) (tpnt->loadaddr + (unsigned long) rpnt->r_offset);
reloc_type = ELF32_R_TYPE(rpnt->r_info);
symtab_index = ELF32_R_SYM(rpnt->r_info);
symbol_addr = 0;
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
if (symtab_index) {
symname = strtab + symtab[symtab_index].st_name;
- if (ELF32_ST_VISIBILITY(symtab[symtab_index].st_other)
- != STV_PROTECTED) {
- symbol_addr = (unsigned long) _dl_find_hash(symname, scope, tpnt, &current_value,
- elf_machine_type_class(reloc_type), &tls_tpnt);
- /*
- * We want to allow undefined references to weak symbols - this might
- * have been intentional. We should not be linking local symbols
- * here, so all bases should be covered.
- */
-
- if (!symbol_addr
- && (ELF_ST_TYPE(symtab[symtab_index].st_info) != STT_TLS)
- && (ELF32_ST_BIND(symtab[symtab_index].st_info) != STB_WEAK)) {
- _dl_dprintf(2, "%s: can't resolve symbol '%s'\n",
- _dl_progname, strtab + symtab[symtab_index].st_name);
-
- /* Let the caller to handle the error: it may be non fatal if called from dlopen */
- return 1;
- }
- } else
- /* Resolve protected symbols locally */
- symbol_addr = DL_FIND_HASH_VALUE(tpnt, elf_machine_type_class(reloc_type),
- &symtab[symtab_index]);
-
+ symbol_addr = (unsigned long) _dl_find_hash(symname, scope, tpnt,
+ elf_machine_type_class(reloc_type), &sym_ref);
+ /*
+ * We want to allow undefined references to weak symbols - this might
+ * have been intentional. We should not be linking local symbols
+ * here, so all bases should be covered.
+ */
+
+ if (!symbol_addr
+ && (ELF_ST_TYPE(symtab[symtab_index].st_info) != STT_TLS)
+ && (ELF32_ST_BIND(symtab[symtab_index].st_info) != STB_WEAK)) {
+ _dl_dprintf(2, "%s: can't resolve symbol '%s'\n",
+ _dl_progname, symname);
+
+ /* Let the caller to handle the error: it may be non fatal if called from dlopen */
+ return 1;
+ }
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
+ tls_tpnt = sym_ref.tpnt;
}
#if defined (__SUPPORT_LD_DEBUG__)
diff --git a/ldso/ldso/sh64/elfinterp.c b/ldso/ldso/sh64/elfinterp.c
index 8f6b32067..caf9f0e14 100644
--- a/ldso/ldso/sh64/elfinterp.c
+++ b/ldso/ldso/sh64/elfinterp.c
@@ -73,7 +73,7 @@ unsigned long _dl_linux_resolver(struct elf_resolve *tpnt, int reloc_entry)
/* Get the address of the GOT entry */
- new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
if (unlikely(!new_addr)) {
_dl_dprintf(2, "%s: can't resolve symbol '%s'\n",
_dl_progname, symname);
@@ -173,13 +173,14 @@ static int _dl_do_reloc(struct elf_resolve *tpnt,struct r_scope_elem *scope,
#ifdef __SUPPORT_LD_DEBUG__
unsigned long old_val;
#endif
-
- struct sym_val current_value = { NULL, NULL };
+ struct symbol_ref sym_ref;
reloc_type = ELF32_R_TYPE(rpnt->r_info);
symtab_index = ELF32_R_SYM(rpnt->r_info);
symbol_addr = 0;
lsb = !!(symtab[symtab_index].st_other & STO_SH5_ISA32);
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
symname = strtab + symtab[symtab_index].st_name;
reloc_addr = (unsigned long *)(intptr_t)
(tpnt->loadaddr + (unsigned long)rpnt->r_offset);
@@ -188,7 +189,7 @@ static int _dl_do_reloc(struct elf_resolve *tpnt,struct r_scope_elem *scope,
int stb;
symbol_addr = (unsigned long)_dl_find_hash(symname, scope, tpnt,
- &current_value, elf_machine_type_class(reloc_type), NULL);
+ elf_machine_type_class(reloc_type), &sym_ref);
/*
* We want to allow undefined references to weak symbols - this
@@ -199,12 +200,12 @@ static int _dl_do_reloc(struct elf_resolve *tpnt,struct r_scope_elem *scope,
if (stb != STB_WEAK && !symbol_addr) {
_dl_dprintf (2, "%s: can't resolve symbol '%s'\n",
- _dl_progname, strtab + symtab[symtab_index].st_name);
+ _dl_progname, symname);
_dl_exit (1);
}
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
}
#ifdef __SUPPORT_LD_DEBUG__
diff --git a/ldso/ldso/sparc/elfinterp.c b/ldso/ldso/sparc/elfinterp.c
index b33ad91b1..3c928073b 100644
--- a/ldso/ldso/sparc/elfinterp.c
+++ b/ldso/ldso/sparc/elfinterp.c
@@ -80,7 +80,7 @@ _dl_linux_resolver(struct elf_resolve *tpnt, int reloc_entry)
got_addr = (char **)instr_addr;
/* Get the address of the GOT entry */
- new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
if (unlikely(!new_addr)) {
_dl_dprintf(2, "%s: Can't resolve symbol '%s'\n", _dl_progname, symname);
_dl_exit(1);
@@ -171,44 +171,44 @@ _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
int symtab_index;
char *symname;
struct elf_resolve *tls_tpnt = 0;
- ElfW(Sym) *sym;
+ struct symbol_ref sym_ref;
ElfW(Addr) *reloc_addr;
ElfW(Addr) symbol_addr;
#if defined (__SUPPORT_LD_DEBUG__)
ElfW(Addr) old_val;
#endif
- struct sym_val current_value = { NULL, NULL };
-
reloc_addr = (ElfW(Addr)*)(tpnt->loadaddr + (unsigned long)rpnt->r_offset);
reloc_type = ELF_R_TYPE(rpnt->r_info);
symtab_index = ELF_R_SYM(rpnt->r_info);
- sym = &symtab[symtab_index];
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
symbol_addr = 0;
- symname = strtab + sym->st_name;
+ symname = strtab + sym_ref.sym->st_name;
if (symtab_index) {
- symbol_addr = (ElfW(Addr))_dl_find_hash(symname, scope, tpnt, &current_value,
- elf_machine_type_class(reloc_type), &tls_tpnt);
+ symbol_addr = (ElfW(Addr))_dl_find_hash(symname, scope, tpnt,
+ elf_machine_type_class(reloc_type), &sym_ref);
/*
* We want to allow undefined references to weak symbols - this
* might have been intentional. We should not be linking local
* symbols here, so all bases should be covered.
*/
- if (unlikely(!symbol_addr && (ELF_ST_TYPE(sym->st_info) != STT_TLS)
- && (ELF_ST_BIND(sym->st_info) != STB_WEAK))) {
+ if (unlikely(!symbol_addr && (ELF_ST_TYPE(sym_ref.sym->st_info) != STT_TLS)
+ && (ELF_ST_BIND(sym_ref.sym->st_info) != STB_WEAK))) {
/* This may be non-fatal if called from dlopen. */
return 1;
}
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
+ tls_tpnt = sym_ref.tpnt;
} else {
/* Relocs against STN_UNDEF are usually treated as using a
* symbol value of zero, and using the module containing the
* reloc itself. */
- symbol_addr = sym->st_value;
+ symbol_addr = sym_ref.sym->st_value;
tls_tpnt = tpnt;
}
@@ -267,13 +267,13 @@ _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
if (_dl_debug_move)
_dl_dprintf(_dl_debug_file,
"\t%s move %d bytes from %x to %x\n",
- symname, sym->st_size,
+ symname, sym_ref.sym->st_size,
symbol_addr, reloc_addr);
#endif
_dl_memcpy((char *)reloc_addr,
(char *)symbol_addr,
- sym->st_size);
+ sym_ref.sym->st_size);
} else
_dl_dprintf(_dl_debug_file, "no symbol_addr to copy !?\n");
break;
@@ -285,7 +285,7 @@ _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
case R_SPARC_TLS_DTPOFF32:
/* During relocation all TLS symbols are defined and used.
* Therefore the offset is already correct. */
- *reloc_addr = sym->st_value + rpnt->r_addend;
+ *reloc_addr = sym_ref.sym->st_value + rpnt->r_addend;
break;
case R_SPARC_TLS_TPOFF32:
@@ -294,7 +294,7 @@ _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
* It is a negative value which will be added to the
* thread pointer. */
CHECK_STATIC_TLS ((struct link_map *) tls_tpnt);
- *reloc_addr = sym->st_value - tls_tpnt->l_tls_offset + rpnt->r_addend;
+ *reloc_addr = sym_ref.sym->st_value - tls_tpnt->l_tls_offset + rpnt->r_addend;
break;
#endif
default:
diff --git a/ldso/ldso/x86_64/elfinterp.c b/ldso/ldso/x86_64/elfinterp.c
index de5a8c01e..a36b1154c 100644
--- a/ldso/ldso/x86_64/elfinterp.c
+++ b/ldso/ldso/x86_64/elfinterp.c
@@ -70,7 +70,7 @@ _dl_linux_resolver(struct elf_resolve *tpnt, int reloc_entry)
got_addr = (char **)instr_addr;
/* Get the address of the GOT entry. */
- new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, NULL, ELF_RTYPE_CLASS_PLT, NULL);
+ new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL);
if (unlikely(!new_addr)) {
_dl_dprintf(2, "%s: Can't resolve symbol '%s'\n", _dl_progname, symname);
_dl_exit(1);
@@ -158,43 +158,43 @@ _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
int symtab_index;
char *symname;
struct elf_resolve *tls_tpnt = 0;
- ElfW(Sym) *sym;
+ struct symbol_ref sym_ref;
ElfW(Addr) *reloc_addr;
ElfW(Addr) symbol_addr;
#if defined (__SUPPORT_LD_DEBUG__)
ElfW(Addr) old_val;
#endif
- struct sym_val current_value = { NULL, NULL };
-
reloc_addr = (ElfW(Addr)*)(tpnt->loadaddr + (unsigned long)rpnt->r_offset);
reloc_type = ELF_R_TYPE(rpnt->r_info);
symtab_index = ELF_R_SYM(rpnt->r_info);
- sym = &symtab[symtab_index];
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
symbol_addr = 0;
- symname = strtab + sym->st_name;
+ symname = strtab + sym_ref.sym->st_name;
if (symtab_index) {
- symbol_addr = (ElfW(Addr))_dl_find_hash(symname, scope, tpnt, &current_value,
- elf_machine_type_class(reloc_type), &tls_tpnt);
+ symbol_addr = (ElfW(Addr))_dl_find_hash(symname, scope, tpnt,
+ elf_machine_type_class(reloc_type), &sym_ref);
/*
* We want to allow undefined references to weak symbols - this
* might have been intentional. We should not be linking local
* symbols here, so all bases should be covered.
*/
- if (unlikely(!symbol_addr && (ELF_ST_TYPE(sym->st_info) != STT_TLS)
- && (ELF_ST_BIND(sym->st_info) != STB_WEAK))) {
+ if (unlikely(!symbol_addr && (ELF_ST_TYPE(sym_ref.sym->st_info) != STT_TLS)
+ && (ELF_ST_BIND(sym_ref.sym->st_info) != STB_WEAK))) {
/* This may be non-fatal if called from dlopen. */
return 1;
}
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
+ tls_tpnt = sym_ref.tpnt;
} else {
/* Relocs against STN_UNDEF are usually treated as using a
* symbol value of zero, and using the module containing the
* reloc itself. */
- symbol_addr = sym->st_value;
+ symbol_addr = sym_ref.sym->st_value;
tls_tpnt = tpnt;
}
@@ -253,13 +253,13 @@ _dl_do_reloc(struct elf_resolve *tpnt, struct r_scope_elem *scope,
if (_dl_debug_move)
_dl_dprintf(_dl_debug_file,
"\t%s move %d bytes from %x to %x\n",
- symname, sym->st_size,
+ symname, sym_ref.sym->st_size,
symbol_addr, reloc_addr);
#endif
_dl_memcpy((char *)reloc_addr,
(char *)symbol_addr,
- sym->st_size);
+ sym_ref.sym->st_size);
} else
_dl_dprintf(_dl_debug_file, "no symbol_addr to copy !?\n");
break;
diff --git a/ldso/ldso/xtensa/elfinterp.c b/ldso/ldso/xtensa/elfinterp.c
index 59f641571..93edc1ff2 100644
--- a/ldso/ldso/xtensa/elfinterp.c
+++ b/ldso/ldso/xtensa/elfinterp.c
@@ -146,26 +146,25 @@ _dl_do_reloc (struct elf_resolve *tpnt, struct r_scope_elem *scope,
int reloc_type;
int symtab_index;
char *symname;
- Elf32_Sym *sym;
+ struct symbol_ref sym_ref;
Elf32_Addr *reloc_addr;
Elf32_Addr symbol_addr;
#if defined (__SUPPORT_LD_DEBUG__)
Elf32_Addr old_val;
#endif
- struct sym_val current_value = { NULL, NULL };
-
reloc_addr = (Elf32_Addr *) (tpnt->loadaddr + rpnt->r_offset);
reloc_type = ELF32_R_TYPE (rpnt->r_info);
symtab_index = ELF32_R_SYM (rpnt->r_info);
- sym = &symtab[symtab_index];
+ sym_ref.sym = &symtab[symtab_index];
+ sym_ref.tpnt = NULL;
symbol_addr = 0;
- symname = strtab + sym->st_name;
+ symname = strtab + sym_ref.sym->st_name;
if (symtab_index) {
symbol_addr = (Elf32_Addr)
- _dl_find_hash (symname, scope, tpnt, &current_value,
- elf_machine_type_class (reloc_type), NULL);
+ _dl_find_hash (symname, scope, tpnt,
+ elf_machine_type_class (reloc_type), &sym_ref);
/*
* We want to allow undefined references to weak symbols - this might
@@ -173,14 +172,14 @@ _dl_do_reloc (struct elf_resolve *tpnt, struct r_scope_elem *scope,
* here, so all bases should be covered.
*/
if (unlikely (!symbol_addr &&
- ELF32_ST_BIND (sym->st_info) != STB_WEAK)) {
+ ELF32_ST_BIND (sym_ref.sym->st_info) != STB_WEAK)) {
_dl_dprintf (2, "%s: can't resolve symbol '%s'\n",
_dl_progname, symname);
_dl_exit (1);
}
if (_dl_trace_prelink)
_dl_debug_lookup (symname, tpnt, &symtab[symtab_index],
- &current_value, elf_machine_type_class(reloc_type));
+ &sym_ref, elf_machine_type_class(reloc_type));
}
#if defined (__SUPPORT_LD_DEBUG__)
diff --git a/ldso/libdl/libdl.c b/ldso/libdl/libdl.c
index 3b49216d4..f95341be7 100644
--- a/ldso/libdl/libdl.c
+++ b/ldso/libdl/libdl.c
@@ -652,6 +652,7 @@ void *dlsym(void *vhandle, const char *name)
struct dyn_elf *rpnt;
void *ret;
struct elf_resolve *tls_tpnt = NULL;
+ struct symbol_ref sym_ref = { NULL, NULL };
/* Nastiness to support underscore prefixes. */
#ifdef __UCLIBC_UNDERSCORES__
char tmp_buf[80];
@@ -706,13 +707,13 @@ void *dlsym(void *vhandle, const char *name)
tpnt = NULL;
if (handle == _dl_symbol_tables)
tpnt = handle->dyn; /* Only search RTLD_GLOBAL objs if global object */
- ret = _dl_find_hash(name2, &handle->dyn->symbol_scope, NULL, NULL, 0, &tls_tpnt);
+ ret = _dl_find_hash(name2, &handle->dyn->symbol_scope, tpnt, 0, &sym_ref);
#if defined(USE_TLS) && USE_TLS && defined SHARED
- if (tls_tpnt) {
+ if (sym_ref.tpnt) {
/* The found symbol is a thread-local storage variable.
Return the address for to the current thread. */
- ret = _dl_tls_symaddr ((struct link_map *)tls_tpnt, (Elf32_Addr)ret);
+ ret = _dl_tls_symaddr ((struct link_map *)sym_ref.tpnt, (Elf32_Addr)ret);
}
#endif
diff --git a/libc/misc/syslog/syslog.c b/libc/misc/syslog/syslog.c
index b10a55615..f1b848f0b 100644
--- a/libc/misc/syslog/syslog.c
+++ b/libc/misc/syslog/syslog.c
@@ -205,7 +205,7 @@ vsyslog(int pri, const char *fmt, va_list ap)
if ((LogMask & LOG_MASK(LOG_PRI(pri))) == 0)
goto getout;
if (LogFile < 0 || !connected)
- openlog_intern(NULL, LogStat | LOG_NDELAY, LOG_USER);
+ openlog_intern(NULL, LogStat | LOG_NDELAY, (int)LogFacility << 3);
/* Set default facility if none specified. */
if ((pri & LOG_FACMASK) == 0)
diff --git a/libc/stdio/_scanf.c b/libc/stdio/_scanf.c
index 34c1c9abd..28cd21e30 100644
--- a/libc/stdio/_scanf.c
+++ b/libc/stdio/_scanf.c
@@ -924,7 +924,10 @@ int attribute_hidden __psfs_parse_spec(register psfs_t *psfs)
goto ERROR_EINVAL;
}
- if ((p_m_spec_chars >= CONV_c)
+ if (p_m_spec_chars == CONV_p) {
+ /* a pointer has the same size as 'long int' */
+ psfs->dataargtype = PA_FLAG_LONG;
+ } else if ((p_m_spec_chars >= CONV_c)
&& (psfs->dataargtype & PA_FLAG_LONG)) {
p_m_spec_chars -= 3; /* lc -> C, ls -> S, l[ -> ?? */
}
diff --git a/libc/sysdeps/linux/cris/sys/user.h b/libc/sysdeps/linux/cris/sys/user.h
new file mode 100644
index 000000000..d629c30d7
--- /dev/null
+++ b/libc/sysdeps/linux/cris/sys/user.h
@@ -0,0 +1,81 @@
+#ifndef __ASM_CRIS_USER_H
+#define __ASM_CRIS_USER_H
+
+/* User-mode register used for core dumps. */
+
+struct user_fpregs {
+};
+
+struct user_regs_struct {
+ unsigned long r0; /* General registers. */
+ unsigned long r1;
+ unsigned long r2;
+ unsigned long r3;
+ unsigned long r4;
+ unsigned long r5;
+ unsigned long r6;
+ unsigned long r7;
+ unsigned long r8;
+ unsigned long r9;
+ unsigned long r10;
+ unsigned long r11;
+ unsigned long r12;
+ unsigned long r13;
+ unsigned long sp; /* R14, Stack pointer. */
+ unsigned long acr; /* R15, Address calculation register. */
+ unsigned long bz; /* P0, Constant zero (8-bits). */
+ unsigned long vr; /* P1, Version register (8-bits). */
+ unsigned long pid; /* P2, Process ID (8-bits). */
+ unsigned long srs; /* P3, Support register select (8-bits). */
+ unsigned long wz; /* P4, Constant zero (16-bits). */
+ unsigned long exs; /* P5, Exception status. */
+ unsigned long eda; /* P6, Exception data address. */
+ unsigned long mof; /* P7, Multiply overflow regiter. */
+ unsigned long dz; /* P8, Constant zero (32-bits). */
+ unsigned long ebp; /* P9, Exception base pointer. */
+ unsigned long erp; /* P10, Exception return pointer. */
+ unsigned long srp; /* P11, Subroutine return pointer. */
+ unsigned long nrp; /* P12, NMI return pointer. */
+ unsigned long ccs; /* P13, Condition code stack. */
+ unsigned long usp; /* P14, User mode stack pointer. */
+ unsigned long spc; /* P15, Single step PC. */
+};
+
+/*
+ * Core file format: The core file is written in such a way that gdb
+ * can understand it and provide useful information to the user (under
+ * linux we use the `trad-core' bfd). The file contents are as follows:
+ *
+ * upage: 1 page consisting of a user struct that tells gdb
+ * what is present in the file. Directly after this is a
+ * copy of the task_struct, which is currently not used by gdb,
+ * but it may come in handy at some point. All of the registers
+ * are stored as part of the upage. The upage should always be
+ * only one page long.
+ * data: The data segment follows next. We use current->end_text to
+ * current->brk to pick up all of the user variables, plus any memory
+ * that may have been sbrk'ed. No attempt is made to determine if a
+ * page is demand-zero or if a page is totally unused, we just cover
+ * the entire range. All of the addresses are rounded in such a way
+ * that an integral number of pages is written.
+ * stack: We need the stack information in order to get a meaningful
+ * backtrace. We need to write the data from usp to
+ * current->start_stack, so we round each of these in order to be able
+ * to write an integer number of pages.
+ */
+
+struct user {
+ struct user_regs_struct regs; /* entire machine state */
+ size_t u_tsize; /* text size (pages) */
+ size_t u_dsize; /* data size (pages) */
+ size_t u_ssize; /* stack size (pages) */
+ unsigned long start_code; /* text starting address */
+ unsigned long start_data; /* data starting address */
+ unsigned long start_stack; /* stack starting address */
+ long int signal; /* signal causing core dump */
+ unsigned long u_ar0; /* help gdb find registers */
+ unsigned long magic; /* identifies a core file */
+ char u_comm[32]; /* user command name */
+};
+
+#endif /* __ASM_CRIS_USER_H */
diff --git a/libc/sysdeps/linux/cris/sysdep.h b/libc/sysdeps/linux/cris/sysdep.h
index 593e7772e..5960fe235 100644
--- a/libc/sysdeps/linux/cris/sysdep.h
+++ b/libc/sysdeps/linux/cris/sysdep.h
@@ -20,6 +20,8 @@
#ifndef _SYSDEP_H_
#define _SYSDEP_H_
+#include <sys/syscall.h>
+
#ifndef C_LABEL
/* Define a macro we can use to construct the asm name for a C symbol. */
diff --git a/libpthread/nptl/allocatestack.c b/libpthread/nptl/allocatestack.c
index 9ffa7e7e2..1c549cee1 100644
--- a/libpthread/nptl/allocatestack.c
+++ b/libpthread/nptl/allocatestack.c
@@ -993,7 +993,7 @@ setxid_signal_thread (struct xid_command *cmdp, struct pthread *t)
int val;
INTERNAL_SYSCALL_DECL (err);
-#if __ASSUME_TGKILL
+#if defined (__ASSUME_TGKILL) && __ASSUME_TGKILL
val = INTERNAL_SYSCALL (tgkill, err, 3, THREAD_GETMEM (THREAD_SELF, pid),
t->tid, SIGSETXID);
#else
diff --git a/libpthread/nptl/pthreadP.h b/libpthread/nptl/pthreadP.h
index c45bd1170..fbac7d08f 100644
--- a/libpthread/nptl/pthreadP.h
+++ b/libpthread/nptl/pthreadP.h
@@ -274,6 +274,8 @@ __do_cancel (void)
#define CANCEL_RESET(oldtype) \
__pthread_disable_asynccancel (oldtype)
+#define __LABEL_PREFIX__ __stringify(__USER_LABEL_PREFIX__)
+
#if !defined NOT_IN_libc
/* Same as CANCEL_ASYNC, but for use in libc.so. */
# define LIBC_CANCEL_ASYNC() \
@@ -282,22 +284,22 @@ __do_cancel (void)
# define LIBC_CANCEL_RESET(oldtype) \
__libc_disable_asynccancel (oldtype)
# define LIBC_CANCEL_HANDLED() \
- __asm__ (".globl " __USER_LABEL_PREFIX__ "__libc_enable_asynccancel"); \
- __asm__ (".globl " __USER_LABEL_PREFIX__ "__libc_disable_asynccancel")
+ __asm__ (".globl " __LABEL_PREFIX__ "__libc_enable_asynccancel"); \
+ __asm__ (".globl " __LABEL_PREFIX__ "__libc_disable_asynccancel")
#elif defined NOT_IN_libc && defined IS_IN_libpthread
# define LIBC_CANCEL_ASYNC() CANCEL_ASYNC ()
# define LIBC_CANCEL_RESET(val) CANCEL_RESET (val)
# define LIBC_CANCEL_HANDLED() \
- __asm__ (".globl " __USER_LABEL_PREFIX__ "__pthread_enable_asynccancel"); \
- __asm__ (".globl " __USER_LABEL_PREFIX__ "__pthread_disable_asynccancel")
+ __asm__ (".globl " __LABEL_PREFIX__ "__pthread_enable_asynccancel"); \
+ __asm__ (".globl " __LABEL_PREFIX__ "__pthread_disable_asynccancel")
#elif defined NOT_IN_libc && defined IS_IN_librt
# define LIBC_CANCEL_ASYNC() \
__librt_enable_asynccancel ()
# define LIBC_CANCEL_RESET(val) \
__librt_disable_asynccancel (val)
# define LIBC_CANCEL_HANDLED() \
- __asm__ (".globl " __USER_LABEL_PREFIX__ "__librt_enable_asynccancel"); \
- __asm__ (".globl " __USER_LABEL_PREFIX__ "__librt_disable_asynccancel")
+ __asm__ (".globl " __LABEL_PREFIX__ "__librt_enable_asynccancel"); \
+ __asm__ (".globl " __LABEL_PREFIX__ "__librt_disable_asynccancel")
#else
# define LIBC_CANCEL_ASYNC() 0 /* Just a dummy value. */
# define LIBC_CANCEL_RESET(val) ((void)(val)) /* Nothing, but evaluate it. */
diff --git a/libpthread/nptl/pthread_cancel.c b/libpthread/nptl/pthread_cancel.c
index 4a958bcde..163fa0243 100644
--- a/libpthread/nptl/pthread_cancel.c
+++ b/libpthread/nptl/pthread_cancel.c
@@ -76,7 +76,7 @@ pthread_cancel (
a signal handler. But this is no allowed, pthread_cancel
is not guaranteed to be async-safe. */
int val;
-#if __ASSUME_TGKILL
+#if defined(__ASSUME_TGKILL) && __ASSUME_TGKILL
val = INTERNAL_SYSCALL (tgkill, err, 3,
THREAD_GETMEM (THREAD_SELF, pid), pd->tid,
SIGCANCEL);
diff --git a/libpthread/nptl/pthread_create.c b/libpthread/nptl/pthread_create.c
index 63e5588d5..86ff1488b 100644
--- a/libpthread/nptl/pthread_create.c
+++ b/libpthread/nptl/pthread_create.c
@@ -379,11 +379,11 @@ start_thread (void *arg)
/* Mark the memory of the stack as usable to the kernel. We free
everything except for the space used for the TCB itself. */
size_t pagesize_m1 = __getpagesize () - 1;
-#ifdef _STACK_GROWS_DOWN
char *sp = CURRENT_STACK_FRAME;
+#ifdef _STACK_GROWS_DOWN
size_t freesize = (sp - (char *) pd->stackblock) & ~pagesize_m1;
#else
-# error "to do"
+ size_t freesize = ((char *) pd->stackblock - sp) & ~pagesize_m1;
#endif
assert (freesize < pd->stackblock_size);
if (freesize > PTHREAD_STACK_MIN)
diff --git a/libpthread/nptl/sysdeps/pthread/createthread.c b/libpthread/nptl/sysdeps/pthread/createthread.c
index a676e277f..ce86f5f33 100644
--- a/libpthread/nptl/sysdeps/pthread/createthread.c
+++ b/libpthread/nptl/sysdeps/pthread/createthread.c
@@ -106,7 +106,7 @@ do_clone (struct pthread *pd, const struct pthread_attr *attr,
send it the cancellation signal. */
INTERNAL_SYSCALL_DECL (err2);
err_out:
-#if __ASSUME_TGKILL
+#if defined (__ASSUME_TGKILL) && __ASSUME_TGKILL
(void) INTERNAL_SYSCALL (tgkill, err2, 3,
THREAD_GETMEM (THREAD_SELF, pid),
pd->tid, SIGCANCEL);
diff --git a/libpthread/nptl/sysdeps/unix/sysv/linux/pt-raise.c b/libpthread/nptl/sysdeps/unix/sysv/linux/pt-raise.c
index d256ebcb0..622bb66ca 100644
--- a/libpthread/nptl/sysdeps/unix/sysv/linux/pt-raise.c
+++ b/libpthread/nptl/sysdeps/unix/sysv/linux/pt-raise.c
@@ -28,7 +28,7 @@ int
raise (
int sig)
{
-#if __ASSUME_TGKILL || defined __NR_tgkill
+#if (defined(__ASSUME_TGKILL) && __ASSUME_TGKILL) || defined __NR_tgkill
/* raise is an async-safe function. It could be called while the
fork function temporarily invalidated the PID field. Adjust for
that. */
@@ -37,7 +37,7 @@ raise (
pid = -pid;
#endif
-#if __ASSUME_TGKILL
+#if defined(__ASSUME_TGKILL) && __ASSUME_TGKILL
return INLINE_SYSCALL (tgkill, 3, pid, THREAD_GETMEM (THREAD_SELF, tid),
sig);
#else
diff --git a/libpthread/nptl/sysdeps/unix/sysv/linux/pthread_kill.c b/libpthread/nptl/sysdeps/unix/sysv/linux/pthread_kill.c
index 3a70c3764..2d6bb8002 100644
--- a/libpthread/nptl/sysdeps/unix/sysv/linux/pthread_kill.c
+++ b/libpthread/nptl/sysdeps/unix/sysv/linux/pthread_kill.c
@@ -59,7 +59,7 @@ __pthread_kill (
fork, it would have to happen in a signal handler. But this is
no allowed, pthread_kill is not guaranteed to be async-safe. */
int val;
-#if __ASSUME_TGKILL
+#if defined(__ASSUME_TGKILL) && __ASSUME_TGKILL
val = INTERNAL_SYSCALL (tgkill, err, 3, THREAD_GETMEM (THREAD_SELF, pid),
tid, signo);
#else
diff --git a/libpthread/nptl/sysdeps/unix/sysv/linux/raise.c b/libpthread/nptl/sysdeps/unix/sysv/linux/raise.c
index da35cfe9f..708ed6d76 100644
--- a/libpthread/nptl/sysdeps/unix/sysv/linux/raise.c
+++ b/libpthread/nptl/sysdeps/unix/sysv/linux/raise.c
@@ -30,7 +30,7 @@ raise (
int sig)
{
struct pthread *pd = THREAD_SELF;
-#if __ASSUME_TGKILL || defined __NR_tgkill
+#if (defined(__ASSUME_TGKILL) && __ASSUME_TGKILL) || defined __NR_tgkill
pid_t pid = THREAD_GETMEM (pd, pid);
#endif
pid_t selftid = THREAD_GETMEM (pd, tid);
@@ -45,13 +45,13 @@ raise (
#endif
THREAD_SETMEM (pd, tid, selftid);
-#if __ASSUME_TGKILL || defined __NR_tgkill
+#if (defined(__ASSUME_TGKILL) && __ASSUME_TGKILL) || defined __NR_tgkill
/* We do not set the PID field in the TID here since we might be
called from a signal handler while the thread executes fork. */
pid = selftid;
#endif
}
-#if __ASSUME_TGKILL || defined __NR_tgkill
+#if (defined(__ASSUME_TGKILL) && __ASSUME_TGKILL) || defined __NR_tgkill
else
/* raise is an async-safe function. It could be called while the
fork/vfork function temporarily invalidated the PID field. Adjust for
@@ -60,7 +60,7 @@ raise (
pid = (pid & INT_MAX) == 0 ? selftid : -pid;
#endif
-#if __ASSUME_TGKILL
+#if defined(__ASSUME_TGKILL) && __ASSUME_TGKILL
return INLINE_SYSCALL (tgkill, 3, pid, selftid, sig);
#else
# ifdef __NR_tgkill