]> git.ipfire.org Git - thirdparty/glibc.git/blob - sysdeps/powerpc/powerpc64/setjmp-common.S
Update copyright dates with scripts/update-copyrights.
[thirdparty/glibc.git] / sysdeps / powerpc / powerpc64 / setjmp-common.S
1 /* setjmp for PowerPC64.
2 Copyright (C) 1995-2016 Free Software Foundation, Inc.
3 This file is part of the GNU C Library.
4
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.
9
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.
14
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/>. */
18
19 #include <sysdep.h>
20 #include <stap-probe.h>
21 #define _ASM
22 #ifdef __NO_VMX__
23 #include <novmxsetjmp.h>
24 #else
25 #include <jmpbuf-offsets.h>
26 #endif
27
28 #ifndef __NO_VMX__
29 .section ".toc","aw"
30 .LC__dl_hwcap:
31 # ifdef SHARED
32 # if IS_IN (rtld)
33 /* Inside ld.so we use the local alias to avoid runtime GOT
34 relocations. */
35 .tc _rtld_local_ro[TC],_rtld_local_ro
36 # else
37 .tc _rtld_global_ro[TC],_rtld_global_ro
38 # endif
39 # else
40 .tc _dl_hwcap[TC],_dl_hwcap
41 # endif
42 .section ".text"
43 #endif
44
45 .machine "altivec"
46 ENTRY (setjmp_symbol)
47 CALL_MCOUNT 1
48 li r4,1 /* Set second argument to 1. */
49 b JUMPTARGET (GLUE(__sigsetjmp_symbol,_ent))
50 END (setjmp_symbol)
51
52 #if defined SHARED && !IS_IN (rtld) && !defined __NO_VMX__
53 /* When called from within libc we need a special version of _setjmp
54 that saves r2 since the call won't go via a plt call stub. See
55 bugz #269. __GI__setjmp is used in csu/libc-start.c when
56 HAVE_CLEANUP_JMP_BUF is defined. */
57 ENTRY (__GI__setjmp)
58 std r2,FRAME_TOC_SAVE(r1) /* Save the callers TOC in the save area. */
59 CALL_MCOUNT 1
60 li r4,0 /* Set second argument to 0. */
61 b JUMPTARGET (GLUE(__sigsetjmp_symbol,_ent))
62 END (__GI__setjmp)
63 #endif
64
65 ENTRY (_setjmp_symbol)
66 CALL_MCOUNT 1
67 li r4,0 /* Set second argument to 0. */
68 b JUMPTARGET (GLUE(__sigsetjmp_symbol,_ent))
69 END (_setjmp_symbol)
70 libc_hidden_def (_setjmp_symbol)
71
72 ENTRY (__sigsetjmp_symbol)
73 CALL_MCOUNT 2
74 JUMPTARGET(GLUE(__sigsetjmp_symbol,_ent)):
75 #ifdef PTR_MANGLE
76 mr r5, r1
77 PTR_MANGLE (r5, r6)
78 std r5,(JB_GPR1*8)(3)
79 #else
80 std r1,(JB_GPR1*8)(3)
81 #endif
82 mflr r0
83 #if defined SHARED && !IS_IN (rtld)
84 ld r5,FRAME_TOC_SAVE(r1) /* Retrieve the callers TOC. */
85 std r5,(JB_GPR2*8)(3)
86 #else
87 std r2,(JB_GPR2*8)(3)
88 #endif
89 /* setjmp probe expects longjmp first argument (8@3), second argument
90 (-4@4), and target address (8@0), respectively. */
91 LIBC_PROBE (setjmp, 3, 8@3, -4@4, 8@0)
92 std r14,((JB_GPRS+0)*8)(3)
93 stfd fp14,((JB_FPRS+0)*8)(3)
94 #ifdef PTR_MANGLE
95 PTR_MANGLE2 (r0, r6)
96 #endif
97 std r0,(JB_LR*8)(3)
98 std r15,((JB_GPRS+1)*8)(3)
99 stfd fp15,((JB_FPRS+1)*8)(3)
100 mfcr r0
101 std r16,((JB_GPRS+2)*8)(3)
102 stfd fp16,((JB_FPRS+2)*8)(3)
103 stw r0,((JB_CR*8)+4)(3) /* 32-bit CR. */
104 std r17,((JB_GPRS+3)*8)(3)
105 stfd fp17,((JB_FPRS+3)*8)(3)
106 std r18,((JB_GPRS+4)*8)(3)
107 stfd fp18,((JB_FPRS+4)*8)(3)
108 std r19,((JB_GPRS+5)*8)(3)
109 stfd fp19,((JB_FPRS+5)*8)(3)
110 std r20,((JB_GPRS+6)*8)(3)
111 stfd fp20,((JB_FPRS+6)*8)(3)
112 std r21,((JB_GPRS+7)*8)(3)
113 stfd fp21,((JB_FPRS+7)*8)(3)
114 std r22,((JB_GPRS+8)*8)(3)
115 stfd fp22,((JB_FPRS+8)*8)(3)
116 std r23,((JB_GPRS+9)*8)(3)
117 stfd fp23,((JB_FPRS+9)*8)(3)
118 std r24,((JB_GPRS+10)*8)(3)
119 stfd fp24,((JB_FPRS+10)*8)(3)
120 std r25,((JB_GPRS+11)*8)(3)
121 stfd fp25,((JB_FPRS+11)*8)(3)
122 std r26,((JB_GPRS+12)*8)(3)
123 stfd fp26,((JB_FPRS+12)*8)(3)
124 std r27,((JB_GPRS+13)*8)(3)
125 stfd fp27,((JB_FPRS+13)*8)(3)
126 std r28,((JB_GPRS+14)*8)(3)
127 stfd fp28,((JB_FPRS+14)*8)(3)
128 std r29,((JB_GPRS+15)*8)(3)
129 stfd fp29,((JB_FPRS+15)*8)(3)
130 std r30,((JB_GPRS+16)*8)(3)
131 stfd fp30,((JB_FPRS+16)*8)(3)
132 std r31,((JB_GPRS+17)*8)(3)
133 stfd fp31,((JB_FPRS+17)*8)(3)
134 #ifndef __NO_VMX__
135 ld r6,.LC__dl_hwcap@toc(r2)
136 # ifdef SHARED
137 /* Load _rtld-global._dl_hwcap. */
138 ld r6,RTLD_GLOBAL_RO_DL_HWCAP_OFFSET(r6)
139 # else
140 ld r6,0(r6) /* Load extern _dl_hwcap. */
141 # endif
142 andis. r6,r6,(PPC_FEATURE_HAS_ALTIVEC >> 16)
143 beq L(no_vmx)
144 la r5,((JB_VRS)*8)(3)
145 andi. r6,r5,0xf
146 mfspr r0,VRSAVE
147 stw r0,((JB_VRSAVE)*8)(3) /* 32-bit VRSAVE. */
148 addi r6,r5,16
149 beq+ L(aligned_save_vmx)
150
151 lvsr v0,0,r5
152 lvsl v1,0,r5
153 addi r6,r5,-16
154
155 # define save_misaligned_vmx(savevr,prevvr,shiftvr,tmpvr,savegpr,addgpr) \
156 addi addgpr,addgpr,32; \
157 vperm tmpvr,prevvr,savevr,shiftvr; \
158 stvx tmpvr,0,savegpr
159
160 /*
161 * We have to be careful not to corrupt the data below v20 and
162 * above v31. To keep things simple we just rotate both ends in
163 * the opposite direction to our main permute so we can use
164 * the common macro.
165 */
166
167 /* load and rotate data below v20 */
168 lvx v2,0,r5
169 vperm v2,v2,v2,v1
170 save_misaligned_vmx(v20,v2,v0,v3,r5,r6)
171 save_misaligned_vmx(v21,v20,v0,v3,r6,r5)
172 save_misaligned_vmx(v22,v21,v0,v3,r5,r6)
173 save_misaligned_vmx(v23,v22,v0,v3,r6,r5)
174 save_misaligned_vmx(v24,v23,v0,v3,r5,r6)
175 save_misaligned_vmx(v25,v24,v0,v3,r6,r5)
176 save_misaligned_vmx(v26,v25,v0,v3,r5,r6)
177 save_misaligned_vmx(v27,v26,v0,v3,r6,r5)
178 save_misaligned_vmx(v28,v27,v0,v3,r5,r6)
179 save_misaligned_vmx(v29,v28,v0,v3,r6,r5)
180 save_misaligned_vmx(v30,v29,v0,v3,r5,r6)
181 save_misaligned_vmx(v31,v30,v0,v3,r6,r5)
182 /* load and rotate data above v31 */
183 lvx v2,0,r6
184 vperm v2,v2,v2,v1
185 save_misaligned_vmx(v2,v31,v0,v3,r5,r6)
186
187 b L(no_vmx)
188
189 L(aligned_save_vmx):
190 stvx 20,0,r5
191 addi r5,r5,32
192 stvx 21,0,r6
193 addi r6,r6,32
194 stvx 22,0,r5
195 addi r5,r5,32
196 stvx 23,0,r6
197 addi r6,r6,32
198 stvx 24,0,r5
199 addi r5,r5,32
200 stvx 25,0,r6
201 addi r6,r6,32
202 stvx 26,0,r5
203 addi r5,r5,32
204 stvx 27,0,r6
205 addi r6,r6,32
206 stvx 28,0,r5
207 addi r5,r5,32
208 stvx 29,0,r6
209 addi r6,r6,32
210 stvx 30,0,r5
211 stvx 31,0,r6
212 L(no_vmx):
213 #else
214 li r6,0
215 #endif
216 #if IS_IN (rtld)
217 li r3,0
218 blr
219 #elif defined SHARED
220 b JUMPTARGET (__sigjmp_save_symbol)
221 #else
222 mflr r0
223 std r0,FRAME_LR_SAVE(r1)
224 stdu r1,-FRAME_MIN_SIZE(r1)
225 cfi_adjust_cfa_offset(FRAME_MIN_SIZE)
226 cfi_offset(lr,FRAME_LR_SAVE)
227 bl JUMPTARGET (__sigjmp_save_symbol)
228 nop
229 ld r0,FRAME_MIN_SIZE+FRAME_LR_SAVE(r1)
230 addi r1,r1,FRAME_MIN_SIZE
231 mtlr r0
232 blr
233 #endif
234 END (__sigsetjmp_symbol)