]>
Commit | Line | Data |
---|---|---|
49bd1d27 | 1 | /* Machine description patterns for PowerPC running Darwin (Mac OS X). |
85ec4feb | 2 | Copyright (C) 2004-2018 Free Software Foundation, Inc. |
49bd1d27 SS |
3 | Contributed by Apple Computer Inc. |
4 | ||
713e31f4 | 5 | This file is part of GCC. |
49bd1d27 SS |
6 | |
7 | GNU CC is free software; you can redistribute it and/or modify | |
8 | it under the terms of the GNU General Public License as published by | |
2f83c7d6 | 9 | the Free Software Foundation; either version 3, or (at your option) |
49bd1d27 SS |
10 | any later version. |
11 | ||
12 | GNU CC is distributed in the hope that it will be useful, | |
13 | but WITHOUT ANY WARRANTY; without even the implied warranty of | |
14 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
15 | GNU General Public License for more details. | |
16 | ||
17 | You should have received a copy of the GNU General Public License | |
2f83c7d6 NC |
18 | ;; along with GCC; see the file COPYING3. If not see |
19 | ;; <http://www.gnu.org/licenses/>. */ | |
49bd1d27 SS |
20 | |
21 | (define_insn "adddi3_high" | |
22 | [(set (match_operand:DI 0 "gpc_reg_operand" "=b") | |
23 | (plus:DI (match_operand:DI 1 "gpc_reg_operand" "b") | |
24 | (high:DI (match_operand 2 "" ""))))] | |
25 | "TARGET_MACHO && TARGET_64BIT" | |
6b39bc38 | 26 | "addis %0,%1,ha16(%2)" |
49bd1d27 SS |
27 | [(set_attr "length" "4")]) |
28 | ||
b8a55285 | 29 | (define_insn "movdf_low_si" |
c5dce79b | 30 | [(set (match_operand:DF 0 "gpc_reg_operand" "=f,!r") |
b8a55285 AP |
31 | (mem:DF (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b,b") |
32 | (match_operand 2 "" ""))))] | |
11d8d07e | 33 | "TARGET_MACHO && TARGET_HARD_FLOAT && !TARGET_64BIT" |
b8a55285 AP |
34 | { |
35 | switch (which_alternative) | |
36 | { | |
37 | case 0: | |
6c332313 | 38 | return "lfd %0,lo16(%2)(%1)"; |
b8a55285 AP |
39 | case 1: |
40 | { | |
b8a55285 AP |
41 | if (TARGET_POWERPC64 && TARGET_32BIT) |
42 | /* Note, old assemblers didn't support relocation here. */ | |
6c332313 | 43 | return "ld %0,lo16(%2)(%1)"; |
b8a55285 | 44 | else |
af8e8908 | 45 | { |
6c332313 SB |
46 | output_asm_insn ("la %0,lo16(%2)(%1)", operands); |
47 | output_asm_insn ("lwz %L0,4(%0)", operands); | |
48 | return ("lwz %0,0(%0)"); | |
af8e8908 | 49 | } |
b8a55285 AP |
50 | } |
51 | default: | |
992d08b1 | 52 | gcc_unreachable (); |
b8a55285 | 53 | } |
6c332313 | 54 | } |
b8a55285 AP |
55 | [(set_attr "type" "load") |
56 | (set_attr "length" "4,12")]) | |
57 | ||
58 | ||
49bd1d27 SS |
59 | (define_insn "movdf_low_di" |
60 | [(set (match_operand:DF 0 "gpc_reg_operand" "=f,!r") | |
61 | (mem:DF (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b,b") | |
62 | (match_operand 2 "" ""))))] | |
11d8d07e | 63 | "TARGET_MACHO && TARGET_HARD_FLOAT && TARGET_64BIT" |
49bd1d27 SS |
64 | { |
65 | switch (which_alternative) | |
66 | { | |
67 | case 0: | |
6c332313 | 68 | return "lfd %0,lo16(%2)(%1)"; |
49bd1d27 | 69 | case 1: |
6c332313 | 70 | return "ld %0,lo16(%2)(%1)"; |
49bd1d27 | 71 | default: |
992d08b1 | 72 | gcc_unreachable (); |
49bd1d27 | 73 | } |
6c332313 | 74 | } |
49bd1d27 | 75 | [(set_attr "type" "load") |
e87d92f4 | 76 | (set_attr "length" "4,4")]) |
49bd1d27 | 77 | |
b8a55285 AP |
78 | (define_insn "movdf_low_st_si" |
79 | [(set (mem:DF (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b") | |
80 | (match_operand 2 "" ""))) | |
81 | (match_operand:DF 0 "gpc_reg_operand" "f"))] | |
11d8d07e | 82 | "TARGET_MACHO && TARGET_HARD_FLOAT && ! TARGET_64BIT" |
b8a55285 AP |
83 | "stfd %0,lo16(%2)(%1)" |
84 | [(set_attr "type" "store") | |
85 | (set_attr "length" "4")]) | |
86 | ||
49bd1d27 SS |
87 | (define_insn "movdf_low_st_di" |
88 | [(set (mem:DF (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b") | |
89 | (match_operand 2 "" ""))) | |
90 | (match_operand:DF 0 "gpc_reg_operand" "f"))] | |
11d8d07e | 91 | "TARGET_MACHO && TARGET_HARD_FLOAT && TARGET_64BIT" |
49bd1d27 SS |
92 | "stfd %0,lo16(%2)(%1)" |
93 | [(set_attr "type" "store") | |
94 | (set_attr "length" "4")]) | |
95 | ||
b8a55285 AP |
96 | (define_insn "movsf_low_si" |
97 | [(set (match_operand:SF 0 "gpc_reg_operand" "=f,!r") | |
98 | (mem:SF (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b,b") | |
99 | (match_operand 2 "" ""))))] | |
11d8d07e | 100 | "TARGET_MACHO && TARGET_HARD_FLOAT && ! TARGET_64BIT" |
b8a55285 AP |
101 | "@ |
102 | lfs %0,lo16(%2)(%1) | |
6b39bc38 | 103 | lwz %0,lo16(%2)(%1)" |
b8a55285 AP |
104 | [(set_attr "type" "load") |
105 | (set_attr "length" "4")]) | |
106 | ||
49bd1d27 SS |
107 | (define_insn "movsf_low_di" |
108 | [(set (match_operand:SF 0 "gpc_reg_operand" "=f,!r") | |
109 | (mem:SF (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b,b") | |
110 | (match_operand 2 "" ""))))] | |
11d8d07e | 111 | "TARGET_MACHO && TARGET_HARD_FLOAT && TARGET_64BIT" |
49bd1d27 SS |
112 | "@ |
113 | lfs %0,lo16(%2)(%1) | |
6b39bc38 | 114 | lwz %0,lo16(%2)(%1)" |
49bd1d27 SS |
115 | [(set_attr "type" "load") |
116 | (set_attr "length" "4")]) | |
117 | ||
b8a55285 AP |
118 | (define_insn "movsf_low_st_si" |
119 | [(set (mem:SF (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b,b") | |
120 | (match_operand 2 "" ""))) | |
121 | (match_operand:SF 0 "gpc_reg_operand" "f,!r"))] | |
11d8d07e | 122 | "TARGET_MACHO && TARGET_HARD_FLOAT && ! TARGET_64BIT" |
b8a55285 AP |
123 | "@ |
124 | stfs %0,lo16(%2)(%1) | |
6b39bc38 | 125 | stw %0,lo16(%2)(%1)" |
b8a55285 AP |
126 | [(set_attr "type" "store") |
127 | (set_attr "length" "4")]) | |
128 | ||
49bd1d27 SS |
129 | (define_insn "movsf_low_st_di" |
130 | [(set (mem:SF (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b,b") | |
131 | (match_operand 2 "" ""))) | |
132 | (match_operand:SF 0 "gpc_reg_operand" "f,!r"))] | |
11d8d07e | 133 | "TARGET_MACHO && TARGET_HARD_FLOAT && TARGET_64BIT" |
49bd1d27 SS |
134 | "@ |
135 | stfs %0,lo16(%2)(%1) | |
6b39bc38 | 136 | stw %0,lo16(%2)(%1)" |
49bd1d27 SS |
137 | [(set_attr "type" "store") |
138 | (set_attr "length" "4")]) | |
139 | ||
140 | ;; 64-bit MachO load/store support | |
141 | (define_insn "movdi_low" | |
f4becba8 MM |
142 | [(set (match_operand:DI 0 "gpc_reg_operand" "=r,*!d") |
143 | (mem:DI (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b,b") | |
49bd1d27 SS |
144 | (match_operand 2 "" ""))))] |
145 | "TARGET_MACHO && TARGET_64BIT" | |
f4becba8 | 146 | "@ |
6b39bc38 | 147 | ld %0,lo16(%2)(%1) |
f4becba8 | 148 | lfd %0,lo16(%2)(%1)" |
49bd1d27 SS |
149 | [(set_attr "type" "load") |
150 | (set_attr "length" "4")]) | |
151 | ||
b8a55285 AP |
152 | (define_insn "movsi_low_st" |
153 | [(set (mem:SI (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b") | |
154 | (match_operand 2 "" ""))) | |
155 | (match_operand:SI 0 "gpc_reg_operand" "r"))] | |
156 | "TARGET_MACHO && ! TARGET_64BIT" | |
6b39bc38 | 157 | "stw %0,lo16(%2)(%1)" |
b8a55285 AP |
158 | [(set_attr "type" "store") |
159 | (set_attr "length" "4")]) | |
160 | ||
49bd1d27 | 161 | (define_insn "movdi_low_st" |
f4becba8 | 162 | [(set (mem:DI (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b,b") |
49bd1d27 | 163 | (match_operand 2 "" ""))) |
f4becba8 | 164 | (match_operand:DI 0 "gpc_reg_operand" "r,*!d"))] |
49bd1d27 | 165 | "TARGET_MACHO && TARGET_64BIT" |
f4becba8 | 166 | "@ |
6b39bc38 | 167 | std %0,lo16(%2)(%1) |
f4becba8 | 168 | stfd %0,lo16(%2)(%1)" |
49bd1d27 SS |
169 | [(set_attr "type" "store") |
170 | (set_attr "length" "4")]) | |
171 | ||
b8a55285 AP |
172 | ;; Mach-O PIC trickery. |
173 | (define_expand "macho_high" | |
174 | [(set (match_operand 0 "" "") | |
175 | (high (match_operand 1 "" "")))] | |
176 | "TARGET_MACHO" | |
177 | { | |
178 | if (TARGET_64BIT) | |
179 | emit_insn (gen_macho_high_di (operands[0], operands[1])); | |
180 | else | |
181 | emit_insn (gen_macho_high_si (operands[0], operands[1])); | |
182 | ||
183 | DONE; | |
184 | }) | |
185 | ||
186 | (define_insn "macho_high_si" | |
187 | [(set (match_operand:SI 0 "gpc_reg_operand" "=b*r") | |
188 | (high:SI (match_operand 1 "" "")))] | |
189 | "TARGET_MACHO && ! TARGET_64BIT" | |
6b39bc38 | 190 | "lis %0,ha16(%1)") |
b8a55285 AP |
191 | |
192 | ||
49bd1d27 SS |
193 | (define_insn "macho_high_di" |
194 | [(set (match_operand:DI 0 "gpc_reg_operand" "=b*r") | |
195 | (high:DI (match_operand 1 "" "")))] | |
196 | "TARGET_MACHO && TARGET_64BIT" | |
6b39bc38 | 197 | "lis %0,ha16(%1)") |
49bd1d27 | 198 | |
b8a55285 AP |
199 | (define_expand "macho_low" |
200 | [(set (match_operand 0 "" "") | |
201 | (lo_sum (match_operand 1 "" "") | |
202 | (match_operand 2 "" "")))] | |
203 | "TARGET_MACHO" | |
204 | { | |
205 | if (TARGET_64BIT) | |
206 | emit_insn (gen_macho_low_di (operands[0], operands[1], operands[2])); | |
207 | else | |
208 | emit_insn (gen_macho_low_si (operands[0], operands[1], operands[2])); | |
209 | ||
210 | DONE; | |
211 | }) | |
212 | ||
213 | (define_insn "macho_low_si" | |
76f93d99 SB |
214 | [(set (match_operand:SI 0 "gpc_reg_operand" "=r") |
215 | (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b") | |
b8a55285 AP |
216 | (match_operand 2 "" "")))] |
217 | "TARGET_MACHO && ! TARGET_64BIT" | |
76f93d99 | 218 | "la %0,lo16(%2)(%1)") |
b8a55285 | 219 | |
49bd1d27 | 220 | (define_insn "macho_low_di" |
76f93d99 SB |
221 | [(set (match_operand:DI 0 "gpc_reg_operand" "=r") |
222 | (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b") | |
49bd1d27 SS |
223 | (match_operand 2 "" "")))] |
224 | "TARGET_MACHO && TARGET_64BIT" | |
76f93d99 | 225 | "la %0,lo16(%2)(%1)") |
49bd1d27 SS |
226 | |
227 | (define_split | |
228 | [(set (mem:V4SI (plus:DI (match_operand:DI 0 "gpc_reg_operand" "") | |
229 | (match_operand:DI 1 "short_cint_operand" ""))) | |
230 | (match_operand:V4SI 2 "register_operand" "")) | |
231 | (clobber (match_operand:DI 3 "gpc_reg_operand" ""))] | |
232 | "TARGET_MACHO && TARGET_64BIT" | |
233 | [(set (match_dup 3) (plus:DI (match_dup 0) (match_dup 1))) | |
234 | (set (mem:V4SI (match_dup 3)) | |
235 | (match_dup 2))] | |
236 | "") | |
237 | ||
b8a55285 | 238 | (define_expand "load_macho_picbase" |
893fc0a0 | 239 | [(set (reg:SI LR_REGNO) |
316fbf19 | 240 | (unspec [(match_operand 0 "" "")] |
b8a55285 AP |
241 | UNSPEC_LD_MPIC))] |
242 | "(DEFAULT_ABI == ABI_DARWIN) && flag_pic" | |
243 | { | |
244 | if (TARGET_32BIT) | |
316fbf19 | 245 | emit_insn (gen_load_macho_picbase_si (operands[0])); |
b8a55285 | 246 | else |
316fbf19 | 247 | emit_insn (gen_load_macho_picbase_di (operands[0])); |
b8a55285 AP |
248 | |
249 | DONE; | |
250 | }) | |
251 | ||
252 | (define_insn "load_macho_picbase_si" | |
893fc0a0 | 253 | [(set (reg:SI LR_REGNO) |
e65a3857 | 254 | (unspec:SI [(match_operand:SI 0 "immediate_operand" "s") |
d5b5b8bf | 255 | (pc)] UNSPEC_LD_MPIC))] |
b8a55285 | 256 | "(DEFAULT_ABI == ABI_DARWIN) && flag_pic" |
e1c5c877 | 257 | { |
bd9534e2 | 258 | #if TARGET_MACHO |
e1c5c877 | 259 | machopic_should_output_picbase_label (); /* Update for new func. */ |
bd9534e2 IS |
260 | #else |
261 | gcc_unreachable (); | |
262 | #endif | |
6c332313 | 263 | return "bcl 20,31,%0\n%0:"; |
e1c5c877 | 264 | } |
b8a55285 | 265 | [(set_attr "type" "branch") |
38dce2c3 | 266 | (set_attr "cannot_copy" "yes") |
b8a55285 AP |
267 | (set_attr "length" "4")]) |
268 | ||
49bd1d27 | 269 | (define_insn "load_macho_picbase_di" |
893fc0a0 | 270 | [(set (reg:DI LR_REGNO) |
e65a3857 | 271 | (unspec:DI [(match_operand:DI 0 "immediate_operand" "s") |
d5b5b8bf | 272 | (pc)] UNSPEC_LD_MPIC))] |
ac9e2cff | 273 | "(DEFAULT_ABI == ABI_DARWIN) && flag_pic && TARGET_64BIT" |
e1c5c877 | 274 | { |
bd9534e2 | 275 | #if TARGET_MACHO |
e1c5c877 | 276 | machopic_should_output_picbase_label (); /* Update for new func. */ |
bd9534e2 IS |
277 | #else |
278 | gcc_unreachable (); | |
279 | #endif | |
6c332313 | 280 | return "bcl 20,31,%0\n%0:"; |
e1c5c877 | 281 | } |
49bd1d27 | 282 | [(set_attr "type" "branch") |
38dce2c3 | 283 | (set_attr "cannot_copy" "yes") |
49bd1d27 SS |
284 | (set_attr "length" "4")]) |
285 | ||
b8a55285 AP |
286 | (define_expand "macho_correct_pic" |
287 | [(set (match_operand 0 "" "") | |
288 | (plus (match_operand 1 "" "") | |
289 | (unspec [(match_operand 2 "" "") | |
290 | (match_operand 3 "" "")] | |
291 | UNSPEC_MPIC_CORRECT)))] | |
292 | "DEFAULT_ABI == ABI_DARWIN" | |
293 | { | |
294 | if (TARGET_32BIT) | |
295 | emit_insn (gen_macho_correct_pic_si (operands[0], operands[1], operands[2], | |
296 | operands[3])); | |
297 | else | |
298 | emit_insn (gen_macho_correct_pic_di (operands[0], operands[1], operands[2], | |
299 | operands[3])); | |
300 | ||
301 | DONE; | |
302 | }) | |
303 | ||
304 | (define_insn "macho_correct_pic_si" | |
305 | [(set (match_operand:SI 0 "gpc_reg_operand" "=r") | |
306 | (plus:SI (match_operand:SI 1 "gpc_reg_operand" "r") | |
307 | (unspec:SI [(match_operand:SI 2 "immediate_operand" "s") | |
308 | (match_operand:SI 3 "immediate_operand" "s")] | |
309 | UNSPEC_MPIC_CORRECT)))] | |
310 | "DEFAULT_ABI == ABI_DARWIN" | |
311 | "addis %0,%1,ha16(%2-%3)\n\taddi %0,%0,lo16(%2-%3)" | |
312 | [(set_attr "length" "8")]) | |
313 | ||
49bd1d27 SS |
314 | (define_insn "macho_correct_pic_di" |
315 | [(set (match_operand:DI 0 "gpc_reg_operand" "=r") | |
316 | (plus:DI (match_operand:DI 1 "gpc_reg_operand" "r") | |
317 | (unspec:DI [(match_operand:DI 2 "immediate_operand" "s") | |
318 | (match_operand:DI 3 "immediate_operand" "s")] | |
319 | 16)))] | |
ac9e2cff | 320 | "DEFAULT_ABI == ABI_DARWIN && TARGET_64BIT" |
49bd1d27 SS |
321 | "addis %0,%1,ha16(%2-%3)\n\taddi %0,%0,lo16(%2-%3)" |
322 | [(set_attr "length" "8")]) | |
323 | ||
324 | (define_insn "*call_indirect_nonlocal_darwin64" | |
325 | [(call (mem:SI (match_operand:DI 0 "register_operand" "c,*l,c,*l")) | |
326 | (match_operand 1 "" "g,g,g,g")) | |
327 | (use (match_operand:SI 2 "immediate_operand" "O,O,n,n")) | |
893fc0a0 | 328 | (clobber (reg:SI LR_REGNO))] |
ac9e2cff | 329 | "DEFAULT_ABI == ABI_DARWIN && TARGET_64BIT" |
49bd1d27 SS |
330 | { |
331 | return "b%T0l"; | |
332 | } | |
333 | [(set_attr "type" "jmpreg,jmpreg,jmpreg,jmpreg") | |
334 | (set_attr "length" "4,4,8,8")]) | |
335 | ||
336 | (define_insn "*call_nonlocal_darwin64" | |
337 | [(call (mem:SI (match_operand:DI 0 "symbol_ref_operand" "s,s")) | |
338 | (match_operand 1 "" "g,g")) | |
339 | (use (match_operand:SI 2 "immediate_operand" "O,n")) | |
893fc0a0 | 340 | (clobber (reg:SI LR_REGNO))] |
49bd1d27 SS |
341 | "(DEFAULT_ABI == ABI_DARWIN) |
342 | && (INTVAL (operands[2]) & CALL_LONG) == 0" | |
343 | { | |
344 | #if TARGET_MACHO | |
345 | return output_call(insn, operands, 0, 2); | |
13a98f14 | 346 | #else |
992d08b1 | 347 | gcc_unreachable (); |
49bd1d27 SS |
348 | #endif |
349 | } | |
350 | [(set_attr "type" "branch,branch") | |
351 | (set_attr "length" "4,8")]) | |
352 | ||
353 | (define_insn "*call_value_indirect_nonlocal_darwin64" | |
354 | [(set (match_operand 0 "" "") | |
355 | (call (mem:SI (match_operand:DI 1 "register_operand" "c,*l,c,*l")) | |
356 | (match_operand 2 "" "g,g,g,g"))) | |
357 | (use (match_operand:SI 3 "immediate_operand" "O,O,n,n")) | |
893fc0a0 | 358 | (clobber (reg:SI LR_REGNO))] |
49bd1d27 SS |
359 | "DEFAULT_ABI == ABI_DARWIN" |
360 | { | |
361 | return "b%T1l"; | |
362 | } | |
363 | [(set_attr "type" "jmpreg,jmpreg,jmpreg,jmpreg") | |
364 | (set_attr "length" "4,4,8,8")]) | |
365 | ||
366 | (define_insn "*call_value_nonlocal_darwin64" | |
367 | [(set (match_operand 0 "" "") | |
368 | (call (mem:SI (match_operand:DI 1 "symbol_ref_operand" "s,s")) | |
369 | (match_operand 2 "" "g,g"))) | |
370 | (use (match_operand:SI 3 "immediate_operand" "O,n")) | |
893fc0a0 | 371 | (clobber (reg:SI LR_REGNO))] |
49bd1d27 SS |
372 | "(DEFAULT_ABI == ABI_DARWIN) |
373 | && (INTVAL (operands[3]) & CALL_LONG) == 0" | |
374 | { | |
375 | #if TARGET_MACHO | |
376 | return output_call(insn, operands, 1, 3); | |
13a98f14 | 377 | #else |
992d08b1 | 378 | gcc_unreachable (); |
13a98f14 | 379 | #endif |
49bd1d27 SS |
380 | } |
381 | [(set_attr "type" "branch,branch") | |
382 | (set_attr "length" "4,8")]) | |
e1c5c877 IS |
383 | |
384 | (define_expand "reload_macho_picbase" | |
893fc0a0 | 385 | [(set (reg:SI LR_REGNO) |
e1c5c877 IS |
386 | (unspec [(match_operand 0 "" "")] |
387 | UNSPEC_RELD_MPIC))] | |
388 | "(DEFAULT_ABI == ABI_DARWIN) && flag_pic" | |
389 | { | |
390 | if (TARGET_32BIT) | |
391 | emit_insn (gen_reload_macho_picbase_si (operands[0])); | |
392 | else | |
393 | emit_insn (gen_reload_macho_picbase_di (operands[0])); | |
394 | ||
395 | DONE; | |
396 | }) | |
397 | ||
398 | (define_insn "reload_macho_picbase_si" | |
893fc0a0 | 399 | [(set (reg:SI LR_REGNO) |
e1c5c877 IS |
400 | (unspec:SI [(match_operand:SI 0 "immediate_operand" "s") |
401 | (pc)] UNSPEC_RELD_MPIC))] | |
402 | "(DEFAULT_ABI == ABI_DARWIN) && flag_pic" | |
403 | { | |
bd9534e2 | 404 | #if TARGET_MACHO |
e1c5c877 IS |
405 | if (machopic_should_output_picbase_label ()) |
406 | { | |
407 | static char tmp[64]; | |
408 | const char *cnam = machopic_get_function_picbase (); | |
6c332313 | 409 | snprintf (tmp, 64, "bcl 20,31,%s\n%s:\n%%0:", cnam, cnam); |
e1c5c877 IS |
410 | return tmp; |
411 | } | |
412 | else | |
bd9534e2 IS |
413 | #else |
414 | gcc_unreachable (); | |
415 | #endif | |
6c332313 | 416 | return "bcl 20,31,%0\n%0:"; |
e1c5c877 IS |
417 | } |
418 | [(set_attr "type" "branch") | |
38dce2c3 | 419 | (set_attr "cannot_copy" "yes") |
e1c5c877 IS |
420 | (set_attr "length" "4")]) |
421 | ||
422 | (define_insn "reload_macho_picbase_di" | |
893fc0a0 | 423 | [(set (reg:DI LR_REGNO) |
e1c5c877 IS |
424 | (unspec:DI [(match_operand:DI 0 "immediate_operand" "s") |
425 | (pc)] UNSPEC_RELD_MPIC))] | |
426 | "(DEFAULT_ABI == ABI_DARWIN) && flag_pic && TARGET_64BIT" | |
427 | { | |
bd9534e2 | 428 | #if TARGET_MACHO |
e1c5c877 IS |
429 | if (machopic_should_output_picbase_label ()) |
430 | { | |
431 | static char tmp[64]; | |
432 | const char *cnam = machopic_get_function_picbase (); | |
6c332313 | 433 | snprintf (tmp, 64, "bcl 20,31,%s\n%s:\n%%0:", cnam, cnam); |
e1c5c877 IS |
434 | return tmp; |
435 | } | |
436 | else | |
bd9534e2 IS |
437 | #else |
438 | gcc_unreachable (); | |
439 | #endif | |
6c332313 | 440 | return "bcl 20,31,%0\n%0:"; |
e1c5c877 IS |
441 | } |
442 | [(set_attr "type" "branch") | |
38dce2c3 | 443 | (set_attr "cannot_copy" "yes") |
e1c5c877 IS |
444 | (set_attr "length" "4")]) |
445 | ||
446 | ;; We need to restore the PIC register, at the site of nonlocal label. | |
447 | ||
448 | (define_insn_and_split "nonlocal_goto_receiver" | |
449 | [(unspec_volatile [(const_int 0)] UNSPECV_NLGR)] | |
450 | "TARGET_MACHO && flag_pic" | |
451 | "#" | |
452 | "&& reload_completed" | |
453 | [(const_int 0)] | |
454 | { | |
bd9534e2 | 455 | #if TARGET_MACHO |
e1c5c877 IS |
456 | if (crtl->uses_pic_offset_table) |
457 | { | |
458 | static unsigned n = 0; | |
459 | rtx picrtx = gen_rtx_SYMBOL_REF (Pmode, MACHOPIC_FUNCTION_BASE_NAME); | |
460 | rtx picreg = gen_rtx_REG (Pmode, RS6000_PIC_OFFSET_TABLE_REGNUM); | |
461 | rtx tmplrtx; | |
462 | char tmplab[20]; | |
463 | ||
464 | ASM_GENERATE_INTERNAL_LABEL(tmplab, "Lnlgr", ++n); | |
465 | tmplrtx = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (tmplab)); | |
466 | ||
467 | emit_insn (gen_reload_macho_picbase (tmplrtx)); | |
468 | emit_move_insn (picreg, gen_rtx_REG (Pmode, LR_REGNO)); | |
469 | emit_insn (gen_macho_correct_pic (picreg, picreg, picrtx, tmplrtx)); | |
470 | } | |
471 | else | |
472 | /* Not using PIC reg, no reload needed. */ | |
473 | emit_note (NOTE_INSN_DELETED); | |
bd9534e2 IS |
474 | #else |
475 | gcc_unreachable (); | |
476 | #endif | |
e1c5c877 IS |
477 | DONE; |
478 | }) |