ARM: Add .cantunwind to _start and _dl_start_user
diff mbox

Message ID 87vb7r7nql.fsf@samsung.com
State New
Headers show

Commit Message

Yury Usishchev Dec. 21, 2015, 4:47 p.m. UTC
Hi all!

This patch fixes the problem with wrong unwind info in rtld for arm.

In last stage of linking ld.so we get (from previous relocatable links) two
sections: '.text' and '.text.unlikely'. They are merged to resulting '.text'
section and '.text.unlikely' goes first.

If we are built with '-funwind-tables' both these sections has some unwind
info and in '.text' first unwind item is not aligned with start of section (we
have '_start' and '_dl_start_user' there and they don't have unwind info). So
when the two sections are merged we get a gap in unwind info.

When libgcc unwinder reaches '_dl_start_user', it searches for unwind
information and finds entry from previous section '.text.unlikely' (function
'oom' in my case).  Unwinding continues with wrong info and it's result is
unpredictable (can even cause segfault in unwinder).

BR,
Yury Usishchev

ChangeLog

2015-12-21 Yury Usishchev <y.usishchev@samsung.com>

     * sysdeps/arm/dl-machine.h (_start): Add .cantunwind
     (_dl_start_user): Add .cantunwind

Patch
diff mbox

From 94241f03333d93428866367d14b70e813824b681 Mon Sep 17 00:00:00 2001
From: Yury Usishchev <y.usishchev@samsung.com>
Date: Mon, 21 Dec 2015 17:58:52 +0300
Subject: [PATCH] Add .cantunwind to _start and _dl_start_user

---
 sysdeps/arm/dl-machine.h | 6 ++++++
 1 file changed, 6 insertions(+)

diff --git a/sysdeps/arm/dl-machine.h b/sysdeps/arm/dl-machine.h
index 6fb20bd..5e50f4d 100644
--- a/sysdeps/arm/dl-machine.h
+++ b/sysdeps/arm/dl-machine.h
@@ -140,6 +140,7 @@  elf_machine_runtime_setup (struct link_map *l, int lazy, int profile)
 .globl _dl_start_user\n\
 .type _dl_start_user, %function\n\
 _start:\n\
+	.fnstart\n\
 	@ we are PIC code, so get global offset table\n\
 	ldr	sl, .L_GET_GOT\n\
 	@ See if we were run as a command with the executable file\n\
@@ -149,7 +150,10 @@  _start:\n\
 	mov	r0, sp\n\
 	bl	_dl_start\n\
 	@ returns user entry point in r0\n\
+	.cantunwind\n\
+	.fnend\n\
 _dl_start_user:\n\
+	.fnstart\n\
 	adr	r6, .L_GET_GOT\n\
 	add	sl, sl, r6\n\
 	ldr	r4, [sl, r4]\n\
@@ -206,6 +210,8 @@  _dl_start_user:\n\
 	ldr	r3, .L_ARGV\n\
 	str	r2, [sl, r3]\n\
 	b	.L_done_fixup\n\
+	.cantunwind\n\
+	.fnend\n\
 \n\
 .L_GET_GOT:\n\
 	.word	_GLOBAL_OFFSET_TABLE_ - .L_GET_GOT\n\
-- 
2.6.4