[BZ #19129][ARM] Fix _dl_tlsdesc_resolve_hold to save r0

_dl_tlsdesc_resolve_hold calls into a C function that clobbers r0,
but it assumes the original argument is still in r0 after the call.
This can cause crash in case of concurrent TLS access when TLSDESC
is in use (-mtls-dialect=gnu2).

Run into this while fixing BZ 18572.

Both r0 and r1 are saved/restored so the stack remains 8 byte aligned.

	[BZ #19129]
	* sysdeps/arm/dl-tlsdesc.S (_dl_tlsdesc_resolve_hold): Save and restore
	r0 and r1.
This commit is contained in:
Szabolcs Nagy 2015-10-14 16:58:41 +01:00
parent f45e45a3e0
commit 1fae5a6800
3 changed files with 25 additions and 10 deletions

View File

@ -1,3 +1,9 @@
2015-10-14 Szabolcs Nagy <szabolcs.nagy@arm.com>
[BZ #19129]
* sysdeps/arm/dl-tlsdesc.S (_dl_tlsdesc_resolve_hold): Save and restore
r0 and r1.
2015-10-14 Namhyung Kim <namhyung@gmail.com>
* manaual/argp.texi (Specifying Argp Parsers): Fix typo.

2
NEWS
View File

@ -20,7 +20,7 @@ Version 2.23
18966, 18967, 18969, 18970, 18977, 18980, 18981, 18985, 19003, 19007,
19012, 19016, 19018, 19032, 19046, 19049, 19050, 19059, 19071, 19074,
19076, 19077, 19078, 19079, 19085, 19086, 19088, 19094, 19095, 19124,
19125
19125, 19129
* The obsolete header <regexp.h> has been removed. Programs that require
this header must be updated to use <regex.h> instead.

View File

@ -196,21 +196,30 @@ _dl_tlsdesc_lazy_resolver:
eabi_fnstart
.align 2
_dl_tlsdesc_resolve_hold:
eabi_save ({r2,r3,ip,lr})
push {r2, r3, ip, lr}
cfi_adjust_cfa_offset (16)
cfi_rel_offset (r2, 0)
cfi_rel_offset (r3, 4)
cfi_rel_offset (ip, 8)
cfi_rel_offset (lr, 12)
/* r0 is saved so its original value can be used after the call and
r1 is saved only to keep the stack aligned. (r0 points to the tls
descriptor, it is passed to _dl_tlsdesc_resolve_hold_fixup which
is a void function that may clobber r0, later r0 is used to load
the new resolver.) */
eabi_save ({r0,r1,r2,r3,ip,lr})
push {r0, r1, r2, r3, ip, lr}
cfi_adjust_cfa_offset (24)
cfi_rel_offset (r0, 0)
cfi_rel_offset (r1, 4)
cfi_rel_offset (r2, 8)
cfi_rel_offset (r3, 12)
cfi_rel_offset (ip, 16)
cfi_rel_offset (lr, 20)
adr r1, _dl_tlsdesc_resolve_hold
bl _dl_tlsdesc_resolve_hold_fixup
pop {r2, r3, ip, lr}
cfi_adjust_cfa_offset (-16)
pop {r0, r1, r2, r3, ip, lr}
cfi_adjust_cfa_offset (-24)
cfi_restore (lr)
cfi_restore (ip)
cfi_restore (r3)
cfi_restore (r2)
cfi_restore (r1)
cfi_restore (r0)
sfi_breg r0, \
ldr r1, [\B, #4]
BX (r1)