1 /* PLT trampolines. ARM version.
2 Copyright (C) 2005-2013 Free Software Foundation, Inc.
3 This file is part of the GNU C Library.
5 The GNU C Library is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Lesser General Public
7 License as published by the Free Software Foundation; either
8 version 2.1 of the License, or (at your option) any later version.
10 The GNU C Library is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Lesser General Public License for more details.
15 You should have received a copy of the GNU Lesser General Public
16 License along with the GNU C Library. If not, see
17 <http://www.gnu.org/licenses/>. */
19 /* ??? Needs more rearrangement for the LDM to handle thumb mode. */
22 #include <libc-symbols.h>
24 #if defined(__USE_BX__)
27 #define BX(x) mov pc, x
31 .globl _dl_runtime_resolve
32 .type _dl_runtime_resolve, #function
37 cfi_adjust_cfa_offset (4)
38 cfi_rel_offset (lr, 0)
41 @ stack[0] contains the return address from this call
42 @ ip contains &GOT[n+3] (pointer to function)
43 @ lr points to &GOT[2]
45 @ Save arguments. We save r4 to realign the stack.
47 cfi_adjust_cfa_offset (20)
48 cfi_rel_offset (r0, 0)
49 cfi_rel_offset (r1, 4)
50 cfi_rel_offset (r2, 8)
51 cfi_rel_offset (r3, 12)
53 @ get pointer to linker struct
56 @ prepare to call _dl_fixup()
57 @ change &GOT[n+3] into 8*n NOTE: reloc are 8 bytes each
68 @ get arguments and return address back. We restore r4
69 @ only to realign the stack.
71 cfi_adjust_cfa_offset (-24)
73 @ jump to the newly found address
77 .size _dl_runtime_resolve, .-_dl_runtime_resolve
80 .globl _dl_runtime_profile
81 .type _dl_runtime_profile, #function
86 cfi_adjust_cfa_offset (4)
87 cfi_rel_offset (lr, 0)
90 @ stack[0] contains the return address from this call
91 @ ip contains &GOT[n+3] (pointer to function)
92 @ lr points to &GOT[2]
96 @ 208 - framesize returned from pltenter
98 @ 8 - Saved two arguments to _dl_profile_fixup
99 @ 4 - Saved result of _dl_profile_fixup
100 @ 0 - outgoing argument to _dl_profile_fixup
101 @ For now, we only save the general purpose registers.
104 cfi_adjust_cfa_offset (196)
106 cfi_rel_offset (r0, 0)
107 cfi_rel_offset (r1, 4)
108 cfi_rel_offset (r2, 8)
109 cfi_rel_offset (r3, 12)
112 cfi_adjust_cfa_offset (16)
120 @ get pointer to linker struct
123 @ prepare to call _dl_profile_fixup()
124 @ change &GOT[n+3] into 8*n NOTE: reloc are 8 bytes each
129 @ Save these two arguments for pltexit.
133 @ Set up extra args for _dl_profile_fixup.
134 @ r2 and r3 are already loaded.
138 @ call profiling fixup routine
141 @ The address to call is now in r0.
143 @ Check whether we're wrapping this function.
152 @ get arguments and return address back
154 cfi_adjust_cfa_offset (-16)
155 ldmia sp, {r0-r3,sp,lr}
156 cfi_adjust_cfa_offset (-200)
158 @ jump to the newly found address
163 @ The new frame size is in ip.
167 @ 264 - saved result of _dl_profile_fixup
169 @ 64 - Saved two arguments to _dl_profile_fixup
171 @ For now, we only save the general purpose registers.
173 @ Build the new frame.
175 cfi_rel_offset (r7, 212)
177 cfi_def_cfa_register (r7)
178 cfi_adjust_cfa_offset (56)
182 @ Save the _dl_profile_fixup result around the call to memcpy.
185 @ Copy the stack arguments.
209 cfi_def_cfa_register (sp)
213 cfi_adjust_cfa_offset (-272)
217 .size _dl_runtime_profile, .-_dl_runtime_profile