]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/config/rs6000/rs6000.c
TODO: Update.
[thirdparty/gcc.git] / gcc / config / rs6000 / rs6000.c
CommitLineData
9878760c 1/* Subroutines used for code generation on IBM RS/6000.
f676971a 2 Copyright (C) 1991, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
337bde91
DE
3 2000, 2001, 2002, 2003, 2004, 2005, 2006
4 Free Software Foundation, Inc.
fab3bcc3 5 Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu)
9878760c 6
5de601cf 7 This file is part of GCC.
9878760c 8
5de601cf
NC
9 GCC is free software; you can redistribute it and/or modify it
10 under the terms of the GNU General Public License as published
11 by the Free Software Foundation; either version 2, or (at your
12 option) any later version.
9878760c 13
5de601cf
NC
14 GCC is distributed in the hope that it will be useful, but WITHOUT
15 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
16 or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
17 License for more details.
9878760c 18
5de601cf
NC
19 You should have received a copy of the GNU General Public License
20 along with GCC; see the file COPYING. If not, write to the
39d14dda
KC
21 Free Software Foundation, 51 Franklin Street, Fifth Floor, Boston,
22 MA 02110-1301, USA. */
9878760c 23
956d6950 24#include "config.h"
c4d38ccb 25#include "system.h"
4977bab6
ZW
26#include "coretypes.h"
27#include "tm.h"
9878760c
RK
28#include "rtl.h"
29#include "regs.h"
30#include "hard-reg-set.h"
31#include "real.h"
32#include "insn-config.h"
33#include "conditions.h"
9878760c
RK
34#include "insn-attr.h"
35#include "flags.h"
36#include "recog.h"
9878760c 37#include "obstack.h"
9b30bae2 38#include "tree.h"
dfafc897 39#include "expr.h"
2fc1c679 40#include "optabs.h"
2a430ec1 41#include "except.h"
a7df97e6 42#include "function.h"
296b8152 43#include "output.h"
d5fa86ba 44#include "basic-block.h"
d0101753 45#include "integrate.h"
296b8152 46#include "toplev.h"
c8023011 47#include "ggc.h"
9ebbca7d
GK
48#include "hashtab.h"
49#include "tm_p.h"
672a6f42
NB
50#include "target.h"
51#include "target-def.h"
3ac88239 52#include "langhooks.h"
24ea750e 53#include "reload.h"
117dca74 54#include "cfglayout.h"
79ae11c4 55#include "sched-int.h"
cd3ce9b4 56#include "tree-gimple.h"
4d3e6fae 57#include "intl.h"
59d6560b 58#include "params.h"
279bb624 59#include "tm-constrs.h"
1bc7c5b6
ZW
60#if TARGET_XCOFF
61#include "xcoffout.h" /* get declarations of xcoff_*_section_name */
62#endif
93a27b7b
ZW
63#if TARGET_MACHO
64#include "gstab.h" /* for N_SLINE */
65#endif
9b30bae2 66
7509c759
MM
67#ifndef TARGET_NO_PROTOTYPE
68#define TARGET_NO_PROTOTYPE 0
69#endif
70
9878760c
RK
71#define min(A,B) ((A) < (B) ? (A) : (B))
72#define max(A,B) ((A) > (B) ? (A) : (B))
73
d1d0c603
JJ
74/* Structure used to define the rs6000 stack */
75typedef struct rs6000_stack {
76 int first_gp_reg_save; /* first callee saved GP register used */
77 int first_fp_reg_save; /* first callee saved FP register used */
78 int first_altivec_reg_save; /* first callee saved AltiVec register used */
79 int lr_save_p; /* true if the link reg needs to be saved */
80 int cr_save_p; /* true if the CR reg needs to be saved */
81 unsigned int vrsave_mask; /* mask of vec registers to save */
d1d0c603
JJ
82 int push_p; /* true if we need to allocate stack space */
83 int calls_p; /* true if the function makes any calls */
c4ad648e 84 int world_save_p; /* true if we're saving *everything*:
d62294f5 85 r13-r31, cr, f14-f31, vrsave, v20-v31 */
d1d0c603
JJ
86 enum rs6000_abi abi; /* which ABI to use */
87 int gp_save_offset; /* offset to save GP regs from initial SP */
88 int fp_save_offset; /* offset to save FP regs from initial SP */
89 int altivec_save_offset; /* offset to save AltiVec regs from initial SP */
90 int lr_save_offset; /* offset to save LR from initial SP */
91 int cr_save_offset; /* offset to save CR from initial SP */
92 int vrsave_save_offset; /* offset to save VRSAVE from initial SP */
93 int spe_gp_save_offset; /* offset to save spe 64-bit gprs */
d1d0c603
JJ
94 int varargs_save_offset; /* offset to save the varargs registers */
95 int ehrd_offset; /* offset to EH return data */
96 int reg_size; /* register size (4 or 8) */
d1d0c603
JJ
97 HOST_WIDE_INT vars_size; /* variable save area size */
98 int parm_size; /* outgoing parameter size */
99 int save_size; /* save area size */
100 int fixed_size; /* fixed size of stack frame */
101 int gp_size; /* size of saved GP registers */
102 int fp_size; /* size of saved FP registers */
103 int altivec_size; /* size of saved AltiVec registers */
104 int cr_size; /* size to hold CR if not in save_size */
d1d0c603
JJ
105 int vrsave_size; /* size to hold VRSAVE if not in save_size */
106 int altivec_padding_size; /* size of altivec alignment padding if
107 not in save_size */
108 int spe_gp_size; /* size of 64-bit GPR save size for SPE */
109 int spe_padding_size;
d1d0c603
JJ
110 HOST_WIDE_INT total_size; /* total bytes allocated for stack */
111 int spe_64bit_regs_used;
112} rs6000_stack_t;
113
5b667039
JJ
114/* A C structure for machine-specific, per-function data.
115 This is added to the cfun structure. */
116typedef struct machine_function GTY(())
117{
118 /* Flags if __builtin_return_address (n) with n >= 1 was used. */
119 int ra_needs_full_frame;
120 /* Some local-dynamic symbol. */
121 const char *some_ld_name;
122 /* Whether the instruction chain has been scanned already. */
123 int insn_chain_scanned_p;
124 /* Flags if __builtin_return_address (0) was used. */
125 int ra_need_lr;
126 /* Offset from virtual_stack_vars_rtx to the start of the ABI_V4
127 varargs save area. */
128 HOST_WIDE_INT varargs_save_offset;
129} machine_function;
130
5248c961
RK
131/* Target cpu type */
132
133enum processor_type rs6000_cpu;
8e3f41e7
MM
134struct rs6000_cpu_select rs6000_select[3] =
135{
815cdc52
MM
136 /* switch name, tune arch */
137 { (const char *)0, "--with-cpu=", 1, 1 },
138 { (const char *)0, "-mcpu=", 1, 1 },
139 { (const char *)0, "-mtune=", 1, 0 },
8e3f41e7 140};
5248c961 141
ec507f2d
DE
142/* Always emit branch hint bits. */
143static GTY(()) bool rs6000_always_hint;
144
145/* Schedule instructions for group formation. */
146static GTY(()) bool rs6000_sched_groups;
147
569fa502
DN
148/* Support for -msched-costly-dep option. */
149const char *rs6000_sched_costly_dep_str;
150enum rs6000_dependence_cost rs6000_sched_costly_dep;
151
cbe26ab8
DN
152/* Support for -minsert-sched-nops option. */
153const char *rs6000_sched_insert_nops_str;
154enum rs6000_nop_insertion rs6000_sched_insert_nops;
155
7ccf35ed 156/* Support targetm.vectorize.builtin_mask_for_load. */
13c62176 157static GTY(()) tree altivec_builtin_mask_for_load;
7ccf35ed 158
602ea4d3 159/* Size of long double. */
6fa3f289
ZW
160int rs6000_long_double_type_size;
161
602ea4d3
JJ
162/* IEEE quad extended precision long double. */
163int rs6000_ieeequad;
164
165/* Whether -mabi=altivec has appeared. */
6fa3f289
ZW
166int rs6000_altivec_abi;
167
a3170dc6
AH
168/* Nonzero if we want SPE ABI extensions. */
169int rs6000_spe_abi;
170
5da702b1
AH
171/* Nonzero if floating point operations are done in the GPRs. */
172int rs6000_float_gprs = 0;
173
594a51fe
SS
174/* Nonzero if we want Darwin's struct-by-value-in-regs ABI. */
175int rs6000_darwin64_abi;
176
a0ab749a 177/* Set to nonzero once AIX common-mode calls have been defined. */
bbfb86aa 178static GTY(()) int common_mode_defined;
c81bebd7 179
9878760c
RK
180/* Save information from a "cmpxx" operation until the branch or scc is
181 emitted. */
9878760c
RK
182rtx rs6000_compare_op0, rs6000_compare_op1;
183int rs6000_compare_fp_p;
874a0744 184
874a0744
MM
185/* Label number of label created for -mrelocatable, to call to so we can
186 get the address of the GOT section */
187int rs6000_pic_labelno;
c81bebd7 188
b91da81f 189#ifdef USING_ELFOS_H
c81bebd7 190/* Which abi to adhere to */
9739c90c 191const char *rs6000_abi_name;
d9407988
MM
192
193/* Semantics of the small data area */
194enum rs6000_sdata_type rs6000_sdata = SDATA_DATA;
195
196/* Which small data model to use */
815cdc52 197const char *rs6000_sdata_name = (char *)0;
9ebbca7d
GK
198
199/* Counter for labels which are to be placed in .fixup. */
200int fixuplabelno = 0;
874a0744 201#endif
4697a36c 202
c4501e62
JJ
203/* Bit size of immediate TLS offsets and string from which it is decoded. */
204int rs6000_tls_size = 32;
205const char *rs6000_tls_size_string;
206
b6c9286a
MM
207/* ABI enumeration available for subtarget to use. */
208enum rs6000_abi rs6000_current_abi;
209
85b776df
AM
210/* Whether to use variant of AIX ABI for PowerPC64 Linux. */
211int dot_symbols;
212
38c1f2d7 213/* Debug flags */
815cdc52 214const char *rs6000_debug_name;
38c1f2d7
MM
215int rs6000_debug_stack; /* debug stack applications */
216int rs6000_debug_arg; /* debug argument handling */
217
aabcd309 218/* Value is TRUE if register/mode pair is acceptable. */
0d1fbc8c
AH
219bool rs6000_hard_regno_mode_ok_p[NUM_MACHINE_MODES][FIRST_PSEUDO_REGISTER];
220
58646b77
PB
221/* Built in types. */
222
223tree rs6000_builtin_types[RS6000_BTI_MAX];
224tree rs6000_builtin_decls[RS6000_BUILTIN_COUNT];
8bb418a3 225
57ac7be9
AM
226const char *rs6000_traceback_name;
227static enum {
228 traceback_default = 0,
229 traceback_none,
230 traceback_part,
231 traceback_full
232} rs6000_traceback;
233
38c1f2d7
MM
234/* Flag to say the TOC is initialized */
235int toc_initialized;
9ebbca7d 236char toc_label_name[10];
38c1f2d7 237
d6b5193b
RS
238static GTY(()) section *read_only_data_section;
239static GTY(()) section *private_data_section;
240static GTY(()) section *read_only_private_data_section;
241static GTY(()) section *sdata2_section;
242static GTY(()) section *toc_section;
243
a3c9585f
KH
244/* Control alignment for fields within structures. */
245/* String from -malign-XXXXX. */
025d9908
KH
246int rs6000_alignment_flags;
247
78f5898b
AH
248/* True for any options that were explicitly set. */
249struct {
df01da37 250 bool aix_struct_ret; /* True if -maix-struct-ret was used. */
78f5898b 251 bool alignment; /* True if -malign- was used. */
d3603e8c 252 bool abi; /* True if -mabi=spe/nospe was used. */
78f5898b
AH
253 bool spe; /* True if -mspe= was used. */
254 bool float_gprs; /* True if -mfloat-gprs= was used. */
255 bool isel; /* True if -misel was used. */
256 bool long_double; /* True if -mlong-double- was used. */
d3603e8c 257 bool ieee; /* True if -mabi=ieee/ibmlongdouble used. */
78f5898b
AH
258} rs6000_explicit_options;
259
a3170dc6
AH
260struct builtin_description
261{
262 /* mask is not const because we're going to alter it below. This
263 nonsense will go away when we rewrite the -march infrastructure
264 to give us more target flag bits. */
265 unsigned int mask;
266 const enum insn_code icode;
267 const char *const name;
268 const enum rs6000_builtins code;
269};
8b897cfa
RS
270\f
271/* Target cpu costs. */
272
273struct processor_costs {
c4ad648e 274 const int mulsi; /* cost of SImode multiplication. */
8b897cfa
RS
275 const int mulsi_const; /* cost of SImode multiplication by constant. */
276 const int mulsi_const9; /* cost of SImode mult by short constant. */
c4ad648e
AM
277 const int muldi; /* cost of DImode multiplication. */
278 const int divsi; /* cost of SImode division. */
279 const int divdi; /* cost of DImode division. */
280 const int fp; /* cost of simple SFmode and DFmode insns. */
281 const int dmul; /* cost of DFmode multiplication (and fmadd). */
282 const int sdiv; /* cost of SFmode division (fdivs). */
283 const int ddiv; /* cost of DFmode division (fdiv). */
8b897cfa
RS
284};
285
286const struct processor_costs *rs6000_cost;
287
288/* Processor costs (relative to an add) */
289
290/* Instruction size costs on 32bit processors. */
291static const
292struct processor_costs size32_cost = {
06a67bdd
RS
293 COSTS_N_INSNS (1), /* mulsi */
294 COSTS_N_INSNS (1), /* mulsi_const */
295 COSTS_N_INSNS (1), /* mulsi_const9 */
296 COSTS_N_INSNS (1), /* muldi */
297 COSTS_N_INSNS (1), /* divsi */
298 COSTS_N_INSNS (1), /* divdi */
299 COSTS_N_INSNS (1), /* fp */
300 COSTS_N_INSNS (1), /* dmul */
301 COSTS_N_INSNS (1), /* sdiv */
302 COSTS_N_INSNS (1), /* ddiv */
8b897cfa
RS
303};
304
305/* Instruction size costs on 64bit processors. */
306static const
307struct processor_costs size64_cost = {
06a67bdd
RS
308 COSTS_N_INSNS (1), /* mulsi */
309 COSTS_N_INSNS (1), /* mulsi_const */
310 COSTS_N_INSNS (1), /* mulsi_const9 */
311 COSTS_N_INSNS (1), /* muldi */
312 COSTS_N_INSNS (1), /* divsi */
313 COSTS_N_INSNS (1), /* divdi */
314 COSTS_N_INSNS (1), /* fp */
315 COSTS_N_INSNS (1), /* dmul */
316 COSTS_N_INSNS (1), /* sdiv */
317 COSTS_N_INSNS (1), /* ddiv */
8b897cfa
RS
318};
319
320/* Instruction costs on RIOS1 processors. */
321static const
322struct processor_costs rios1_cost = {
06a67bdd
RS
323 COSTS_N_INSNS (5), /* mulsi */
324 COSTS_N_INSNS (4), /* mulsi_const */
325 COSTS_N_INSNS (3), /* mulsi_const9 */
326 COSTS_N_INSNS (5), /* muldi */
327 COSTS_N_INSNS (19), /* divsi */
328 COSTS_N_INSNS (19), /* divdi */
329 COSTS_N_INSNS (2), /* fp */
330 COSTS_N_INSNS (2), /* dmul */
331 COSTS_N_INSNS (19), /* sdiv */
332 COSTS_N_INSNS (19), /* ddiv */
8b897cfa
RS
333};
334
335/* Instruction costs on RIOS2 processors. */
336static const
337struct processor_costs rios2_cost = {
06a67bdd
RS
338 COSTS_N_INSNS (2), /* mulsi */
339 COSTS_N_INSNS (2), /* mulsi_const */
340 COSTS_N_INSNS (2), /* mulsi_const9 */
341 COSTS_N_INSNS (2), /* muldi */
342 COSTS_N_INSNS (13), /* divsi */
343 COSTS_N_INSNS (13), /* divdi */
344 COSTS_N_INSNS (2), /* fp */
345 COSTS_N_INSNS (2), /* dmul */
346 COSTS_N_INSNS (17), /* sdiv */
347 COSTS_N_INSNS (17), /* ddiv */
8b897cfa
RS
348};
349
350/* Instruction costs on RS64A processors. */
351static const
352struct processor_costs rs64a_cost = {
06a67bdd
RS
353 COSTS_N_INSNS (20), /* mulsi */
354 COSTS_N_INSNS (12), /* mulsi_const */
355 COSTS_N_INSNS (8), /* mulsi_const9 */
356 COSTS_N_INSNS (34), /* muldi */
357 COSTS_N_INSNS (65), /* divsi */
358 COSTS_N_INSNS (67), /* divdi */
359 COSTS_N_INSNS (4), /* fp */
360 COSTS_N_INSNS (4), /* dmul */
361 COSTS_N_INSNS (31), /* sdiv */
362 COSTS_N_INSNS (31), /* ddiv */
8b897cfa
RS
363};
364
365/* Instruction costs on MPCCORE processors. */
366static const
367struct processor_costs mpccore_cost = {
06a67bdd
RS
368 COSTS_N_INSNS (2), /* mulsi */
369 COSTS_N_INSNS (2), /* mulsi_const */
370 COSTS_N_INSNS (2), /* mulsi_const9 */
371 COSTS_N_INSNS (2), /* muldi */
372 COSTS_N_INSNS (6), /* divsi */
373 COSTS_N_INSNS (6), /* divdi */
374 COSTS_N_INSNS (4), /* fp */
375 COSTS_N_INSNS (5), /* dmul */
376 COSTS_N_INSNS (10), /* sdiv */
377 COSTS_N_INSNS (17), /* ddiv */
8b897cfa
RS
378};
379
380/* Instruction costs on PPC403 processors. */
381static const
382struct processor_costs ppc403_cost = {
06a67bdd
RS
383 COSTS_N_INSNS (4), /* mulsi */
384 COSTS_N_INSNS (4), /* mulsi_const */
385 COSTS_N_INSNS (4), /* mulsi_const9 */
386 COSTS_N_INSNS (4), /* muldi */
387 COSTS_N_INSNS (33), /* divsi */
388 COSTS_N_INSNS (33), /* divdi */
389 COSTS_N_INSNS (11), /* fp */
390 COSTS_N_INSNS (11), /* dmul */
391 COSTS_N_INSNS (11), /* sdiv */
392 COSTS_N_INSNS (11), /* ddiv */
8b897cfa
RS
393};
394
395/* Instruction costs on PPC405 processors. */
396static const
397struct processor_costs ppc405_cost = {
06a67bdd
RS
398 COSTS_N_INSNS (5), /* mulsi */
399 COSTS_N_INSNS (4), /* mulsi_const */
400 COSTS_N_INSNS (3), /* mulsi_const9 */
401 COSTS_N_INSNS (5), /* muldi */
402 COSTS_N_INSNS (35), /* divsi */
403 COSTS_N_INSNS (35), /* divdi */
404 COSTS_N_INSNS (11), /* fp */
405 COSTS_N_INSNS (11), /* dmul */
406 COSTS_N_INSNS (11), /* sdiv */
407 COSTS_N_INSNS (11), /* ddiv */
8b897cfa
RS
408};
409
410/* Instruction costs on PPC440 processors. */
411static const
412struct processor_costs ppc440_cost = {
06a67bdd
RS
413 COSTS_N_INSNS (3), /* mulsi */
414 COSTS_N_INSNS (2), /* mulsi_const */
415 COSTS_N_INSNS (2), /* mulsi_const9 */
416 COSTS_N_INSNS (3), /* muldi */
417 COSTS_N_INSNS (34), /* divsi */
418 COSTS_N_INSNS (34), /* divdi */
419 COSTS_N_INSNS (5), /* fp */
420 COSTS_N_INSNS (5), /* dmul */
421 COSTS_N_INSNS (19), /* sdiv */
422 COSTS_N_INSNS (33), /* ddiv */
8b897cfa
RS
423};
424
425/* Instruction costs on PPC601 processors. */
426static const
427struct processor_costs ppc601_cost = {
06a67bdd
RS
428 COSTS_N_INSNS (5), /* mulsi */
429 COSTS_N_INSNS (5), /* mulsi_const */
430 COSTS_N_INSNS (5), /* mulsi_const9 */
431 COSTS_N_INSNS (5), /* muldi */
432 COSTS_N_INSNS (36), /* divsi */
433 COSTS_N_INSNS (36), /* divdi */
434 COSTS_N_INSNS (4), /* fp */
435 COSTS_N_INSNS (5), /* dmul */
436 COSTS_N_INSNS (17), /* sdiv */
437 COSTS_N_INSNS (31), /* ddiv */
8b897cfa
RS
438};
439
440/* Instruction costs on PPC603 processors. */
441static const
442struct processor_costs ppc603_cost = {
06a67bdd
RS
443 COSTS_N_INSNS (5), /* mulsi */
444 COSTS_N_INSNS (3), /* mulsi_const */
445 COSTS_N_INSNS (2), /* mulsi_const9 */
446 COSTS_N_INSNS (5), /* muldi */
447 COSTS_N_INSNS (37), /* divsi */
448 COSTS_N_INSNS (37), /* divdi */
449 COSTS_N_INSNS (3), /* fp */
450 COSTS_N_INSNS (4), /* dmul */
451 COSTS_N_INSNS (18), /* sdiv */
452 COSTS_N_INSNS (33), /* ddiv */
8b897cfa
RS
453};
454
455/* Instruction costs on PPC604 processors. */
456static const
457struct processor_costs ppc604_cost = {
06a67bdd
RS
458 COSTS_N_INSNS (4), /* mulsi */
459 COSTS_N_INSNS (4), /* mulsi_const */
460 COSTS_N_INSNS (4), /* mulsi_const9 */
461 COSTS_N_INSNS (4), /* muldi */
462 COSTS_N_INSNS (20), /* divsi */
463 COSTS_N_INSNS (20), /* divdi */
464 COSTS_N_INSNS (3), /* fp */
465 COSTS_N_INSNS (3), /* dmul */
466 COSTS_N_INSNS (18), /* sdiv */
467 COSTS_N_INSNS (32), /* ddiv */
8b897cfa
RS
468};
469
470/* Instruction costs on PPC604e processors. */
471static const
472struct processor_costs ppc604e_cost = {
06a67bdd
RS
473 COSTS_N_INSNS (2), /* mulsi */
474 COSTS_N_INSNS (2), /* mulsi_const */
475 COSTS_N_INSNS (2), /* mulsi_const9 */
476 COSTS_N_INSNS (2), /* muldi */
477 COSTS_N_INSNS (20), /* divsi */
478 COSTS_N_INSNS (20), /* divdi */
479 COSTS_N_INSNS (3), /* fp */
480 COSTS_N_INSNS (3), /* dmul */
481 COSTS_N_INSNS (18), /* sdiv */
482 COSTS_N_INSNS (32), /* ddiv */
8b897cfa
RS
483};
484
f0517163 485/* Instruction costs on PPC620 processors. */
8b897cfa
RS
486static const
487struct processor_costs ppc620_cost = {
06a67bdd
RS
488 COSTS_N_INSNS (5), /* mulsi */
489 COSTS_N_INSNS (4), /* mulsi_const */
490 COSTS_N_INSNS (3), /* mulsi_const9 */
491 COSTS_N_INSNS (7), /* muldi */
492 COSTS_N_INSNS (21), /* divsi */
493 COSTS_N_INSNS (37), /* divdi */
494 COSTS_N_INSNS (3), /* fp */
495 COSTS_N_INSNS (3), /* dmul */
496 COSTS_N_INSNS (18), /* sdiv */
497 COSTS_N_INSNS (32), /* ddiv */
f0517163
RS
498};
499
500/* Instruction costs on PPC630 processors. */
501static const
502struct processor_costs ppc630_cost = {
06a67bdd
RS
503 COSTS_N_INSNS (5), /* mulsi */
504 COSTS_N_INSNS (4), /* mulsi_const */
505 COSTS_N_INSNS (3), /* mulsi_const9 */
506 COSTS_N_INSNS (7), /* muldi */
507 COSTS_N_INSNS (21), /* divsi */
508 COSTS_N_INSNS (37), /* divdi */
509 COSTS_N_INSNS (3), /* fp */
510 COSTS_N_INSNS (3), /* dmul */
511 COSTS_N_INSNS (17), /* sdiv */
512 COSTS_N_INSNS (21), /* ddiv */
8b897cfa
RS
513};
514
515/* Instruction costs on PPC750 and PPC7400 processors. */
516static const
517struct processor_costs ppc750_cost = {
06a67bdd
RS
518 COSTS_N_INSNS (5), /* mulsi */
519 COSTS_N_INSNS (3), /* mulsi_const */
520 COSTS_N_INSNS (2), /* mulsi_const9 */
521 COSTS_N_INSNS (5), /* muldi */
522 COSTS_N_INSNS (17), /* divsi */
523 COSTS_N_INSNS (17), /* divdi */
524 COSTS_N_INSNS (3), /* fp */
525 COSTS_N_INSNS (3), /* dmul */
526 COSTS_N_INSNS (17), /* sdiv */
527 COSTS_N_INSNS (31), /* ddiv */
8b897cfa
RS
528};
529
530/* Instruction costs on PPC7450 processors. */
531static const
532struct processor_costs ppc7450_cost = {
06a67bdd
RS
533 COSTS_N_INSNS (4), /* mulsi */
534 COSTS_N_INSNS (3), /* mulsi_const */
535 COSTS_N_INSNS (3), /* mulsi_const9 */
536 COSTS_N_INSNS (4), /* muldi */
537 COSTS_N_INSNS (23), /* divsi */
538 COSTS_N_INSNS (23), /* divdi */
539 COSTS_N_INSNS (5), /* fp */
540 COSTS_N_INSNS (5), /* dmul */
541 COSTS_N_INSNS (21), /* sdiv */
542 COSTS_N_INSNS (35), /* ddiv */
8b897cfa 543};
a3170dc6 544
8b897cfa
RS
545/* Instruction costs on PPC8540 processors. */
546static const
547struct processor_costs ppc8540_cost = {
06a67bdd
RS
548 COSTS_N_INSNS (4), /* mulsi */
549 COSTS_N_INSNS (4), /* mulsi_const */
550 COSTS_N_INSNS (4), /* mulsi_const9 */
551 COSTS_N_INSNS (4), /* muldi */
552 COSTS_N_INSNS (19), /* divsi */
553 COSTS_N_INSNS (19), /* divdi */
554 COSTS_N_INSNS (4), /* fp */
555 COSTS_N_INSNS (4), /* dmul */
556 COSTS_N_INSNS (29), /* sdiv */
557 COSTS_N_INSNS (29), /* ddiv */
8b897cfa
RS
558};
559
560/* Instruction costs on POWER4 and POWER5 processors. */
561static const
562struct processor_costs power4_cost = {
06a67bdd
RS
563 COSTS_N_INSNS (3), /* mulsi */
564 COSTS_N_INSNS (2), /* mulsi_const */
565 COSTS_N_INSNS (2), /* mulsi_const9 */
566 COSTS_N_INSNS (4), /* muldi */
567 COSTS_N_INSNS (18), /* divsi */
568 COSTS_N_INSNS (34), /* divdi */
569 COSTS_N_INSNS (3), /* fp */
570 COSTS_N_INSNS (3), /* dmul */
571 COSTS_N_INSNS (17), /* sdiv */
572 COSTS_N_INSNS (17), /* ddiv */
8b897cfa
RS
573};
574
575\f
a2369ed3 576static bool rs6000_function_ok_for_sibcall (tree, tree);
2ffa9a0c 577static const char *rs6000_invalid_within_doloop (rtx);
a2369ed3
DJ
578static rtx rs6000_generate_compare (enum rtx_code);
579static void rs6000_maybe_dead (rtx);
580static void rs6000_emit_stack_tie (void);
581static void rs6000_frame_related (rtx, rtx, HOST_WIDE_INT, rtx, rtx);
582static rtx spe_synthesize_frame_save (rtx);
583static bool spe_func_has_64bit_regs_p (void);
b20a9cca 584static void emit_frame_save (rtx, rtx, enum machine_mode, unsigned int,
d1d0c603 585 int, HOST_WIDE_INT);
a2369ed3
DJ
586static rtx gen_frame_mem_offset (enum machine_mode, rtx, int);
587static void rs6000_emit_allocate_stack (HOST_WIDE_INT, int);
588static unsigned rs6000_hash_constant (rtx);
589static unsigned toc_hash_function (const void *);
590static int toc_hash_eq (const void *, const void *);
591static int constant_pool_expr_1 (rtx, int *, int *);
592static bool constant_pool_expr_p (rtx);
d04b6e6e 593static bool legitimate_small_data_p (enum machine_mode, rtx);
a2369ed3 594static bool legitimate_indexed_address_p (rtx, int);
a2369ed3
DJ
595static bool legitimate_lo_sum_address_p (enum machine_mode, rtx, int);
596static struct machine_function * rs6000_init_machine_status (void);
597static bool rs6000_assemble_integer (rtx, unsigned int, int);
6d0a8091 598static bool no_global_regs_above (int);
5add3202 599#ifdef HAVE_GAS_HIDDEN
a2369ed3 600static void rs6000_assemble_visibility (tree, int);
5add3202 601#endif
a2369ed3
DJ
602static int rs6000_ra_ever_killed (void);
603static tree rs6000_handle_longcall_attribute (tree *, tree, tree, int, bool *);
8bb418a3 604static tree rs6000_handle_altivec_attribute (tree *, tree, tree, int, bool *);
77ccdfed
EC
605static bool rs6000_ms_bitfield_layout_p (tree);
606static tree rs6000_handle_struct_attribute (tree *, tree, tree, int, bool *);
76d2b81d 607static void rs6000_eliminate_indexed_memrefs (rtx operands[2]);
f18eca82 608static const char *rs6000_mangle_fundamental_type (tree);
b86fe7b4 609extern const struct attribute_spec rs6000_attribute_table[];
a2369ed3
DJ
610static void rs6000_set_default_type_attributes (tree);
611static void rs6000_output_function_prologue (FILE *, HOST_WIDE_INT);
612static void rs6000_output_function_epilogue (FILE *, HOST_WIDE_INT);
b20a9cca
AM
613static void rs6000_output_mi_thunk (FILE *, tree, HOST_WIDE_INT, HOST_WIDE_INT,
614 tree);
a2369ed3 615static rtx rs6000_emit_set_long_const (rtx, HOST_WIDE_INT, HOST_WIDE_INT);
c6e8c921 616static bool rs6000_return_in_memory (tree, tree);
a2369ed3 617static void rs6000_file_start (void);
7c262518 618#if TARGET_ELF
a2369ed3
DJ
619static unsigned int rs6000_elf_section_type_flags (tree, const char *, int);
620static void rs6000_elf_asm_out_constructor (rtx, int);
621static void rs6000_elf_asm_out_destructor (rtx, int);
1334b570 622static void rs6000_elf_end_indicate_exec_stack (void) ATTRIBUTE_UNUSED;
d6b5193b
RS
623static void rs6000_elf_asm_init_sections (void);
624static section *rs6000_elf_select_section (tree, int, unsigned HOST_WIDE_INT);
a2369ed3 625static void rs6000_elf_unique_section (tree, int);
d6b5193b
RS
626static section *rs6000_elf_select_rtx_section (enum machine_mode, rtx,
627 unsigned HOST_WIDE_INT);
a56d7372 628static void rs6000_elf_encode_section_info (tree, rtx, int)
0e5dbd9b 629 ATTRIBUTE_UNUSED;
7c262518 630#endif
aacd3885 631static bool rs6000_use_blocks_for_constant_p (enum machine_mode, rtx);
cbaaba19 632#if TARGET_XCOFF
0d5817b2 633static void rs6000_xcoff_asm_output_anchor (rtx);
a2369ed3 634static void rs6000_xcoff_asm_globalize_label (FILE *, const char *);
d6b5193b 635static void rs6000_xcoff_asm_init_sections (void);
8210e4c4 636static void rs6000_xcoff_asm_named_section (const char *, unsigned int, tree);
d6b5193b 637static section *rs6000_xcoff_select_section (tree, int,
b20a9cca 638 unsigned HOST_WIDE_INT);
d6b5193b
RS
639static void rs6000_xcoff_unique_section (tree, int);
640static section *rs6000_xcoff_select_rtx_section
641 (enum machine_mode, rtx, unsigned HOST_WIDE_INT);
a2369ed3
DJ
642static const char * rs6000_xcoff_strip_name_encoding (const char *);
643static unsigned int rs6000_xcoff_section_type_flags (tree, const char *, int);
644static void rs6000_xcoff_file_start (void);
645static void rs6000_xcoff_file_end (void);
f1384257 646#endif
a2369ed3
DJ
647static int rs6000_variable_issue (FILE *, int, rtx, int);
648static bool rs6000_rtx_costs (rtx, int, int, int *);
649static int rs6000_adjust_cost (rtx, rtx, rtx, int);
cbe26ab8 650static bool is_microcoded_insn (rtx);
79ae11c4 651static int is_dispatch_slot_restricted (rtx);
cbe26ab8
DN
652static bool is_cracked_insn (rtx);
653static bool is_branch_slot_insn (rtx);
a2369ed3
DJ
654static int rs6000_adjust_priority (rtx, int);
655static int rs6000_issue_rate (void);
569fa502 656static bool rs6000_is_costly_dependence (rtx, rtx, rtx, int, int);
cbe26ab8
DN
657static rtx get_next_active_insn (rtx, rtx);
658static bool insn_terminates_group_p (rtx , enum group_termination);
659static bool is_costly_group (rtx *, rtx);
660static int force_new_group (int, FILE *, rtx *, rtx, bool *, int, int *);
661static int redefine_groups (FILE *, int, rtx, rtx);
662static int pad_groups (FILE *, int, rtx, rtx);
663static void rs6000_sched_finish (FILE *, int);
a2369ed3 664static int rs6000_use_sched_lookahead (void);
7ccf35ed 665static tree rs6000_builtin_mask_for_load (void);
a2369ed3 666
58646b77 667static void def_builtin (int, const char *, tree, int);
a2369ed3
DJ
668static void rs6000_init_builtins (void);
669static rtx rs6000_expand_unop_builtin (enum insn_code, tree, rtx);
670static rtx rs6000_expand_binop_builtin (enum insn_code, tree, rtx);
671static rtx rs6000_expand_ternop_builtin (enum insn_code, tree, rtx);
672static rtx rs6000_expand_builtin (tree, rtx, rtx, enum machine_mode, int);
673static void altivec_init_builtins (void);
674static void rs6000_common_init_builtins (void);
c15c90bb 675static void rs6000_init_libfuncs (void);
a2369ed3 676
b20a9cca
AM
677static void enable_mask_for_builtins (struct builtin_description *, int,
678 enum rs6000_builtins,
679 enum rs6000_builtins);
7c62e993 680static tree build_opaque_vector_type (tree, int);
a2369ed3
DJ
681static void spe_init_builtins (void);
682static rtx spe_expand_builtin (tree, rtx, bool *);
61bea3b0 683static rtx spe_expand_stv_builtin (enum insn_code, tree);
a2369ed3
DJ
684static rtx spe_expand_predicate_builtin (enum insn_code, tree, rtx);
685static rtx spe_expand_evsel_builtin (enum insn_code, tree, rtx);
686static int rs6000_emit_int_cmove (rtx, rtx, rtx, rtx);
d1d0c603
JJ
687static rs6000_stack_t *rs6000_stack_info (void);
688static void debug_stack_info (rs6000_stack_t *);
a2369ed3
DJ
689
690static rtx altivec_expand_builtin (tree, rtx, bool *);
691static rtx altivec_expand_ld_builtin (tree, rtx, bool *);
692static rtx altivec_expand_st_builtin (tree, rtx, bool *);
693static rtx altivec_expand_dst_builtin (tree, rtx, bool *);
694static rtx altivec_expand_abs_builtin (enum insn_code, tree, rtx);
f676971a 695static rtx altivec_expand_predicate_builtin (enum insn_code,
c4ad648e 696 const char *, tree, rtx);
b4a62fa0 697static rtx altivec_expand_lv_builtin (enum insn_code, tree, rtx);
a2369ed3 698static rtx altivec_expand_stv_builtin (enum insn_code, tree);
7a4eca66
DE
699static rtx altivec_expand_vec_init_builtin (tree, tree, rtx);
700static rtx altivec_expand_vec_set_builtin (tree);
701static rtx altivec_expand_vec_ext_builtin (tree, rtx);
702static int get_element_number (tree, tree);
78f5898b 703static bool rs6000_handle_option (size_t, const char *, int);
a2369ed3 704static void rs6000_parse_tls_size_option (void);
5da702b1 705static void rs6000_parse_yes_no_option (const char *, const char *, int *);
a2369ed3
DJ
706static int first_altivec_reg_to_save (void);
707static unsigned int compute_vrsave_mask (void);
9390387d 708static void compute_save_world_info (rs6000_stack_t *info_ptr);
a2369ed3
DJ
709static void is_altivec_return_reg (rtx, void *);
710static rtx generate_set_vrsave (rtx, rs6000_stack_t *, int);
711int easy_vector_constant (rtx, enum machine_mode);
58646b77 712static bool rs6000_is_opaque_type (tree);
a2369ed3
DJ
713static rtx rs6000_dwarf_register_span (rtx);
714static rtx rs6000_legitimize_tls_address (rtx, enum tls_model);
fdbe66f2 715static void rs6000_output_dwarf_dtprel (FILE *, int, rtx) ATTRIBUTE_UNUSED;
a2369ed3
DJ
716static rtx rs6000_tls_get_addr (void);
717static rtx rs6000_got_sym (void);
9390387d 718static int rs6000_tls_symbol_ref_1 (rtx *, void *);
a2369ed3
DJ
719static const char *rs6000_get_some_local_dynamic_name (void);
720static int rs6000_get_some_local_dynamic_name_1 (rtx *, void *);
ded9bf77 721static rtx rs6000_complex_function_value (enum machine_mode);
b20a9cca 722static rtx rs6000_spe_function_arg (CUMULATIVE_ARGS *,
a2369ed3 723 enum machine_mode, tree);
0b5383eb
DJ
724static void rs6000_darwin64_record_arg_advance_flush (CUMULATIVE_ARGS *,
725 HOST_WIDE_INT);
726static void rs6000_darwin64_record_arg_advance_recurse (CUMULATIVE_ARGS *,
727 tree, HOST_WIDE_INT);
728static void rs6000_darwin64_record_arg_flush (CUMULATIVE_ARGS *,
729 HOST_WIDE_INT,
730 rtx[], int *);
731static void rs6000_darwin64_record_arg_recurse (CUMULATIVE_ARGS *,
732 tree, HOST_WIDE_INT,
733 rtx[], int *);
734static rtx rs6000_darwin64_record_arg (CUMULATIVE_ARGS *, tree, int, bool);
ec6376ab 735static rtx rs6000_mixed_function_arg (enum machine_mode, tree, int);
b1917422 736static void rs6000_move_block_from_reg (int regno, rtx x, int nregs);
c6e8c921
GK
737static void setup_incoming_varargs (CUMULATIVE_ARGS *,
738 enum machine_mode, tree,
739 int *, int);
8cd5a4e0
RH
740static bool rs6000_pass_by_reference (CUMULATIVE_ARGS *, enum machine_mode,
741 tree, bool);
78a52f11
RH
742static int rs6000_arg_partial_bytes (CUMULATIVE_ARGS *, enum machine_mode,
743 tree, bool);
4d3e6fae 744static const char *invalid_arg_for_unprototyped_fn (tree, tree, tree);
efdba735
SH
745#if TARGET_MACHO
746static void macho_branch_islands (void);
747static void add_compiler_branch_island (tree, tree, int);
748static int no_previous_def (tree function_name);
749static tree get_prev_label (tree function_name);
c4e18b1c 750static void rs6000_darwin_file_start (void);
efdba735
SH
751#endif
752
c35d187f 753static tree rs6000_build_builtin_va_list (void);
23a60a04 754static tree rs6000_gimplify_va_arg (tree, tree, tree *, tree *);
fe984136 755static bool rs6000_must_pass_in_stack (enum machine_mode, tree);
00b79d54 756static bool rs6000_scalar_mode_supported_p (enum machine_mode);
f676971a 757static bool rs6000_vector_mode_supported_p (enum machine_mode);
94ff898d 758static int get_vec_cmp_insn (enum rtx_code, enum machine_mode,
21213b4c 759 enum machine_mode);
94ff898d 760static rtx rs6000_emit_vector_compare (enum rtx_code, rtx, rtx,
21213b4c
DP
761 enum machine_mode);
762static int get_vsel_insn (enum machine_mode);
763static void rs6000_emit_vector_select (rtx, rtx, rtx, rtx);
3aebbe5f 764static tree rs6000_stack_protect_fail (void);
21213b4c
DP
765
766const int INSN_NOT_AVAILABLE = -1;
93f90be6
FJ
767static enum machine_mode rs6000_eh_return_filter_mode (void);
768
17211ab5
GK
769/* Hash table stuff for keeping track of TOC entries. */
770
771struct toc_hash_struct GTY(())
772{
773 /* `key' will satisfy CONSTANT_P; in fact, it will satisfy
774 ASM_OUTPUT_SPECIAL_POOL_ENTRY_P. */
775 rtx key;
776 enum machine_mode key_mode;
777 int labelno;
778};
779
780static GTY ((param_is (struct toc_hash_struct))) htab_t toc_hash_table;
c81bebd7
MM
781\f
782/* Default register names. */
783char rs6000_reg_names[][8] =
784{
802a0058
MM
785 "0", "1", "2", "3", "4", "5", "6", "7",
786 "8", "9", "10", "11", "12", "13", "14", "15",
787 "16", "17", "18", "19", "20", "21", "22", "23",
788 "24", "25", "26", "27", "28", "29", "30", "31",
789 "0", "1", "2", "3", "4", "5", "6", "7",
790 "8", "9", "10", "11", "12", "13", "14", "15",
791 "16", "17", "18", "19", "20", "21", "22", "23",
792 "24", "25", "26", "27", "28", "29", "30", "31",
793 "mq", "lr", "ctr","ap",
794 "0", "1", "2", "3", "4", "5", "6", "7",
0ac081f6
AH
795 "xer",
796 /* AltiVec registers. */
0cd5e3a1
AH
797 "0", "1", "2", "3", "4", "5", "6", "7",
798 "8", "9", "10", "11", "12", "13", "14", "15",
799 "16", "17", "18", "19", "20", "21", "22", "23",
800 "24", "25", "26", "27", "28", "29", "30", "31",
59a4c851
AH
801 "vrsave", "vscr",
802 /* SPE registers. */
7d5175e1
JJ
803 "spe_acc", "spefscr",
804 /* Soft frame pointer. */
805 "sfp"
c81bebd7
MM
806};
807
808#ifdef TARGET_REGNAMES
8b60264b 809static const char alt_reg_names[][8] =
c81bebd7 810{
802a0058
MM
811 "%r0", "%r1", "%r2", "%r3", "%r4", "%r5", "%r6", "%r7",
812 "%r8", "%r9", "%r10", "%r11", "%r12", "%r13", "%r14", "%r15",
813 "%r16", "%r17", "%r18", "%r19", "%r20", "%r21", "%r22", "%r23",
814 "%r24", "%r25", "%r26", "%r27", "%r28", "%r29", "%r30", "%r31",
815 "%f0", "%f1", "%f2", "%f3", "%f4", "%f5", "%f6", "%f7",
816 "%f8", "%f9", "%f10", "%f11", "%f12", "%f13", "%f14", "%f15",
817 "%f16", "%f17", "%f18", "%f19", "%f20", "%f21", "%f22", "%f23",
818 "%f24", "%f25", "%f26", "%f27", "%f28", "%f29", "%f30", "%f31",
819 "mq", "lr", "ctr", "ap",
820 "%cr0", "%cr1", "%cr2", "%cr3", "%cr4", "%cr5", "%cr6", "%cr7",
0ac081f6 821 "xer",
59a4c851 822 /* AltiVec registers. */
0ac081f6 823 "%v0", "%v1", "%v2", "%v3", "%v4", "%v5", "%v6", "%v7",
59a4c851
AH
824 "%v8", "%v9", "%v10", "%v11", "%v12", "%v13", "%v14", "%v15",
825 "%v16", "%v17", "%v18", "%v19", "%v20", "%v21", "%v22", "%v23",
826 "%v24", "%v25", "%v26", "%v27", "%v28", "%v29", "%v30", "%v31",
827 "vrsave", "vscr",
828 /* SPE registers. */
7d5175e1
JJ
829 "spe_acc", "spefscr",
830 /* Soft frame pointer. */
831 "sfp"
c81bebd7
MM
832};
833#endif
9878760c 834\f
daf11973
MM
835#ifndef MASK_STRICT_ALIGN
836#define MASK_STRICT_ALIGN 0
837#endif
ffcfcb5f
AM
838#ifndef TARGET_PROFILE_KERNEL
839#define TARGET_PROFILE_KERNEL 0
840#endif
3961e8fe
RH
841
842/* The VRSAVE bitmask puts bit %v0 as the most significant bit. */
843#define ALTIVEC_REG_BIT(REGNO) (0x80000000 >> ((REGNO) - FIRST_ALTIVEC_REGNO))
672a6f42
NB
844\f
845/* Initialize the GCC target structure. */
91d231cb
JM
846#undef TARGET_ATTRIBUTE_TABLE
847#define TARGET_ATTRIBUTE_TABLE rs6000_attribute_table
a5c76ee6
ZW
848#undef TARGET_SET_DEFAULT_TYPE_ATTRIBUTES
849#define TARGET_SET_DEFAULT_TYPE_ATTRIBUTES rs6000_set_default_type_attributes
daf11973 850
301d03af
RS
851#undef TARGET_ASM_ALIGNED_DI_OP
852#define TARGET_ASM_ALIGNED_DI_OP DOUBLE_INT_ASM_OP
853
854/* Default unaligned ops are only provided for ELF. Find the ops needed
855 for non-ELF systems. */
856#ifndef OBJECT_FORMAT_ELF
cbaaba19 857#if TARGET_XCOFF
ae6c1efd 858/* For XCOFF. rs6000_assemble_integer will handle unaligned DIs on
301d03af
RS
859 64-bit targets. */
860#undef TARGET_ASM_UNALIGNED_HI_OP
861#define TARGET_ASM_UNALIGNED_HI_OP "\t.vbyte\t2,"
862#undef TARGET_ASM_UNALIGNED_SI_OP
863#define TARGET_ASM_UNALIGNED_SI_OP "\t.vbyte\t4,"
864#undef TARGET_ASM_UNALIGNED_DI_OP
865#define TARGET_ASM_UNALIGNED_DI_OP "\t.vbyte\t8,"
866#else
867/* For Darwin. */
868#undef TARGET_ASM_UNALIGNED_HI_OP
869#define TARGET_ASM_UNALIGNED_HI_OP "\t.short\t"
870#undef TARGET_ASM_UNALIGNED_SI_OP
871#define TARGET_ASM_UNALIGNED_SI_OP "\t.long\t"
49bd1d27
SS
872#undef TARGET_ASM_UNALIGNED_DI_OP
873#define TARGET_ASM_UNALIGNED_DI_OP "\t.quad\t"
874#undef TARGET_ASM_ALIGNED_DI_OP
875#define TARGET_ASM_ALIGNED_DI_OP "\t.quad\t"
301d03af
RS
876#endif
877#endif
878
879/* This hook deals with fixups for relocatable code and DI-mode objects
880 in 64-bit code. */
881#undef TARGET_ASM_INTEGER
882#define TARGET_ASM_INTEGER rs6000_assemble_integer
883
93638d7a
AM
884#ifdef HAVE_GAS_HIDDEN
885#undef TARGET_ASM_ASSEMBLE_VISIBILITY
886#define TARGET_ASM_ASSEMBLE_VISIBILITY rs6000_assemble_visibility
887#endif
888
c4501e62
JJ
889#undef TARGET_HAVE_TLS
890#define TARGET_HAVE_TLS HAVE_AS_TLS
891
892#undef TARGET_CANNOT_FORCE_CONST_MEM
a7e0b075 893#define TARGET_CANNOT_FORCE_CONST_MEM rs6000_tls_referenced_p
c4501e62 894
08c148a8
NB
895#undef TARGET_ASM_FUNCTION_PROLOGUE
896#define TARGET_ASM_FUNCTION_PROLOGUE rs6000_output_function_prologue
897#undef TARGET_ASM_FUNCTION_EPILOGUE
898#define TARGET_ASM_FUNCTION_EPILOGUE rs6000_output_function_epilogue
899
b54cf83a
DE
900#undef TARGET_SCHED_VARIABLE_ISSUE
901#define TARGET_SCHED_VARIABLE_ISSUE rs6000_variable_issue
902
c237e94a
ZW
903#undef TARGET_SCHED_ISSUE_RATE
904#define TARGET_SCHED_ISSUE_RATE rs6000_issue_rate
905#undef TARGET_SCHED_ADJUST_COST
906#define TARGET_SCHED_ADJUST_COST rs6000_adjust_cost
907#undef TARGET_SCHED_ADJUST_PRIORITY
908#define TARGET_SCHED_ADJUST_PRIORITY rs6000_adjust_priority
f676971a 909#undef TARGET_SCHED_IS_COSTLY_DEPENDENCE
569fa502 910#define TARGET_SCHED_IS_COSTLY_DEPENDENCE rs6000_is_costly_dependence
cbe26ab8
DN
911#undef TARGET_SCHED_FINISH
912#define TARGET_SCHED_FINISH rs6000_sched_finish
c237e94a 913
be12c2b0
VM
914#undef TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DFA_LOOKAHEAD
915#define TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DFA_LOOKAHEAD rs6000_use_sched_lookahead
916
7ccf35ed
DN
917#undef TARGET_VECTORIZE_BUILTIN_MASK_FOR_LOAD
918#define TARGET_VECTORIZE_BUILTIN_MASK_FOR_LOAD rs6000_builtin_mask_for_load
919
0ac081f6
AH
920#undef TARGET_INIT_BUILTINS
921#define TARGET_INIT_BUILTINS rs6000_init_builtins
922
923#undef TARGET_EXPAND_BUILTIN
924#define TARGET_EXPAND_BUILTIN rs6000_expand_builtin
925
f18eca82
ZL
926#undef TARGET_MANGLE_FUNDAMENTAL_TYPE
927#define TARGET_MANGLE_FUNDAMENTAL_TYPE rs6000_mangle_fundamental_type
928
c15c90bb
ZW
929#undef TARGET_INIT_LIBFUNCS
930#define TARGET_INIT_LIBFUNCS rs6000_init_libfuncs
931
f1384257 932#if TARGET_MACHO
0e5dbd9b 933#undef TARGET_BINDS_LOCAL_P
31920d83 934#define TARGET_BINDS_LOCAL_P darwin_binds_local_p
f1384257 935#endif
0e5dbd9b 936
77ccdfed
EC
937#undef TARGET_MS_BITFIELD_LAYOUT_P
938#define TARGET_MS_BITFIELD_LAYOUT_P rs6000_ms_bitfield_layout_p
939
3961e8fe
RH
940#undef TARGET_ASM_OUTPUT_MI_THUNK
941#define TARGET_ASM_OUTPUT_MI_THUNK rs6000_output_mi_thunk
942
3961e8fe 943#undef TARGET_ASM_CAN_OUTPUT_MI_THUNK
5b71a4e7 944#define TARGET_ASM_CAN_OUTPUT_MI_THUNK hook_bool_tree_hwi_hwi_tree_true
00b960c7 945
4977bab6
ZW
946#undef TARGET_FUNCTION_OK_FOR_SIBCALL
947#define TARGET_FUNCTION_OK_FOR_SIBCALL rs6000_function_ok_for_sibcall
948
2e3f0db6
DJ
949#undef TARGET_INVALID_WITHIN_DOLOOP
950#define TARGET_INVALID_WITHIN_DOLOOP rs6000_invalid_within_doloop
9419649c 951
3c50106f
RH
952#undef TARGET_RTX_COSTS
953#define TARGET_RTX_COSTS rs6000_rtx_costs
dcefdf67
RH
954#undef TARGET_ADDRESS_COST
955#define TARGET_ADDRESS_COST hook_int_rtx_0
3c50106f 956
c8e4f0e9 957#undef TARGET_VECTOR_OPAQUE_P
58646b77 958#define TARGET_VECTOR_OPAQUE_P rs6000_is_opaque_type
62e1dfcf 959
96714395
AH
960#undef TARGET_DWARF_REGISTER_SPAN
961#define TARGET_DWARF_REGISTER_SPAN rs6000_dwarf_register_span
962
c6e8c921
GK
963/* On rs6000, function arguments are promoted, as are function return
964 values. */
965#undef TARGET_PROMOTE_FUNCTION_ARGS
966#define TARGET_PROMOTE_FUNCTION_ARGS hook_bool_tree_true
967#undef TARGET_PROMOTE_FUNCTION_RETURN
968#define TARGET_PROMOTE_FUNCTION_RETURN hook_bool_tree_true
969
c6e8c921
GK
970#undef TARGET_RETURN_IN_MEMORY
971#define TARGET_RETURN_IN_MEMORY rs6000_return_in_memory
972
973#undef TARGET_SETUP_INCOMING_VARARGS
974#define TARGET_SETUP_INCOMING_VARARGS setup_incoming_varargs
975
976/* Always strict argument naming on rs6000. */
977#undef TARGET_STRICT_ARGUMENT_NAMING
978#define TARGET_STRICT_ARGUMENT_NAMING hook_bool_CUMULATIVE_ARGS_true
979#undef TARGET_PRETEND_OUTGOING_VARARGS_NAMED
980#define TARGET_PRETEND_OUTGOING_VARARGS_NAMED hook_bool_CUMULATIVE_ARGS_true
42ba5130
RH
981#undef TARGET_SPLIT_COMPLEX_ARG
982#define TARGET_SPLIT_COMPLEX_ARG hook_bool_tree_true
fe984136
RH
983#undef TARGET_MUST_PASS_IN_STACK
984#define TARGET_MUST_PASS_IN_STACK rs6000_must_pass_in_stack
8cd5a4e0
RH
985#undef TARGET_PASS_BY_REFERENCE
986#define TARGET_PASS_BY_REFERENCE rs6000_pass_by_reference
78a52f11
RH
987#undef TARGET_ARG_PARTIAL_BYTES
988#define TARGET_ARG_PARTIAL_BYTES rs6000_arg_partial_bytes
c6e8c921 989
c35d187f
RH
990#undef TARGET_BUILD_BUILTIN_VA_LIST
991#define TARGET_BUILD_BUILTIN_VA_LIST rs6000_build_builtin_va_list
992
cd3ce9b4
JM
993#undef TARGET_GIMPLIFY_VA_ARG_EXPR
994#define TARGET_GIMPLIFY_VA_ARG_EXPR rs6000_gimplify_va_arg
995
93f90be6
FJ
996#undef TARGET_EH_RETURN_FILTER_MODE
997#define TARGET_EH_RETURN_FILTER_MODE rs6000_eh_return_filter_mode
998
00b79d54
BE
999#undef TARGET_SCALAR_MODE_SUPPORTED_P
1000#define TARGET_SCALAR_MODE_SUPPORTED_P rs6000_scalar_mode_supported_p
1001
f676971a
EC
1002#undef TARGET_VECTOR_MODE_SUPPORTED_P
1003#define TARGET_VECTOR_MODE_SUPPORTED_P rs6000_vector_mode_supported_p
1004
4d3e6fae
FJ
1005#undef TARGET_INVALID_ARG_FOR_UNPROTOTYPED_FN
1006#define TARGET_INVALID_ARG_FOR_UNPROTOTYPED_FN invalid_arg_for_unprototyped_fn
1007
78f5898b
AH
1008#undef TARGET_HANDLE_OPTION
1009#define TARGET_HANDLE_OPTION rs6000_handle_option
1010
1011#undef TARGET_DEFAULT_TARGET_FLAGS
1012#define TARGET_DEFAULT_TARGET_FLAGS \
716019c0 1013 (TARGET_DEFAULT)
78f5898b 1014
3aebbe5f
JJ
1015#undef TARGET_STACK_PROTECT_FAIL
1016#define TARGET_STACK_PROTECT_FAIL rs6000_stack_protect_fail
1017
445cf5eb
JM
1018/* MPC604EUM 3.5.2 Weak Consistency between Multiple Processors
1019 The PowerPC architecture requires only weak consistency among
1020 processors--that is, memory accesses between processors need not be
1021 sequentially consistent and memory accesses among processors can occur
1022 in any order. The ability to order memory accesses weakly provides
1023 opportunities for more efficient use of the system bus. Unless a
1024 dependency exists, the 604e allows read operations to precede store
1025 operations. */
1026#undef TARGET_RELAXED_ORDERING
1027#define TARGET_RELAXED_ORDERING true
1028
fdbe66f2
EB
1029#ifdef HAVE_AS_TLS
1030#undef TARGET_ASM_OUTPUT_DWARF_DTPREL
1031#define TARGET_ASM_OUTPUT_DWARF_DTPREL rs6000_output_dwarf_dtprel
1032#endif
1033
aacd3885
RS
1034/* Use a 32-bit anchor range. This leads to sequences like:
1035
1036 addis tmp,anchor,high
1037 add dest,tmp,low
1038
1039 where tmp itself acts as an anchor, and can be shared between
1040 accesses to the same 64k page. */
1041#undef TARGET_MIN_ANCHOR_OFFSET
1042#define TARGET_MIN_ANCHOR_OFFSET -0x7fffffff - 1
1043#undef TARGET_MAX_ANCHOR_OFFSET
1044#define TARGET_MAX_ANCHOR_OFFSET 0x7fffffff
1045#undef TARGET_USE_BLOCKS_FOR_CONSTANT_P
1046#define TARGET_USE_BLOCKS_FOR_CONSTANT_P rs6000_use_blocks_for_constant_p
1047
f6897b10 1048struct gcc_target targetm = TARGET_INITIALIZER;
672a6f42 1049\f
0d1fbc8c
AH
1050
1051/* Value is 1 if hard register REGNO can hold a value of machine-mode
1052 MODE. */
1053static int
1054rs6000_hard_regno_mode_ok (int regno, enum machine_mode mode)
1055{
1056 /* The GPRs can hold any mode, but values bigger than one register
1057 cannot go past R31. */
1058 if (INT_REGNO_P (regno))
1059 return INT_REGNO_P (regno + HARD_REGNO_NREGS (regno, mode) - 1);
1060
a5a97921
BE
1061 /* The float registers can only hold floating modes and DImode.
1062 This also excludes decimal float modes. */
0d1fbc8c
AH
1063 if (FP_REGNO_P (regno))
1064 return
ebb109ad 1065 (SCALAR_FLOAT_MODE_P (mode)
a5a97921 1066 && !DECIMAL_FLOAT_MODE_P (mode)
0d1fbc8c
AH
1067 && FP_REGNO_P (regno + HARD_REGNO_NREGS (regno, mode) - 1))
1068 || (GET_MODE_CLASS (mode) == MODE_INT
1069 && GET_MODE_SIZE (mode) == UNITS_PER_FP_WORD);
1070
1071 /* The CR register can only hold CC modes. */
1072 if (CR_REGNO_P (regno))
1073 return GET_MODE_CLASS (mode) == MODE_CC;
1074
1075 if (XER_REGNO_P (regno))
1076 return mode == PSImode;
1077
1078 /* AltiVec only in AldyVec registers. */
1079 if (ALTIVEC_REGNO_P (regno))
1080 return ALTIVEC_VECTOR_MODE (mode);
1081
1082 /* ...but GPRs can hold SIMD data on the SPE in one register. */
1083 if (SPE_SIMD_REGNO_P (regno) && TARGET_SPE && SPE_VECTOR_MODE (mode))
1084 return 1;
1085
1086 /* We cannot put TImode anywhere except general register and it must be
1087 able to fit within the register set. */
1088
1089 return GET_MODE_SIZE (mode) <= UNITS_PER_WORD;
1090}
1091
1092/* Initialize rs6000_hard_regno_mode_ok_p table. */
1093static void
1094rs6000_init_hard_regno_mode_ok (void)
1095{
1096 int r, m;
1097
1098 for (r = 0; r < FIRST_PSEUDO_REGISTER; ++r)
1099 for (m = 0; m < NUM_MACHINE_MODES; ++m)
1100 if (rs6000_hard_regno_mode_ok (r, m))
1101 rs6000_hard_regno_mode_ok_p[m][r] = true;
1102}
1103
c1e55850
GK
1104/* If not otherwise specified by a target, make 'long double' equivalent to
1105 'double'. */
1106
1107#ifndef RS6000_DEFAULT_LONG_DOUBLE_SIZE
1108#define RS6000_DEFAULT_LONG_DOUBLE_SIZE 64
1109#endif
1110
5248c961
RK
1111/* Override command line options. Mostly we process the processor
1112 type and sometimes adjust other TARGET_ options. */
1113
1114void
d779d0dc 1115rs6000_override_options (const char *default_cpu)
5248c961 1116{
c4d38ccb 1117 size_t i, j;
8e3f41e7 1118 struct rs6000_cpu_select *ptr;
66188a7e 1119 int set_masks;
5248c961 1120
66188a7e 1121 /* Simplifications for entries below. */
85638c0d 1122
66188a7e
GK
1123 enum {
1124 POWERPC_BASE_MASK = MASK_POWERPC | MASK_NEW_MNEMONICS,
1125 POWERPC_7400_MASK = POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_ALTIVEC
1126 };
85638c0d 1127
66188a7e
GK
1128 /* This table occasionally claims that a processor does not support
1129 a particular feature even though it does, but the feature is slower
1130 than the alternative. Thus, it shouldn't be relied on as a
f676971a 1131 complete description of the processor's support.
66188a7e
GK
1132
1133 Please keep this list in order, and don't forget to update the
1134 documentation in invoke.texi when adding a new processor or
1135 flag. */
5248c961
RK
1136 static struct ptt
1137 {
8b60264b
KG
1138 const char *const name; /* Canonical processor name. */
1139 const enum processor_type processor; /* Processor type enum value. */
1140 const int target_enable; /* Target flags to enable. */
8b60264b 1141 } const processor_target_table[]
66188a7e 1142 = {{"401", PROCESSOR_PPC403, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
49a0b204 1143 {"403", PROCESSOR_PPC403,
66188a7e 1144 POWERPC_BASE_MASK | MASK_SOFT_FLOAT | MASK_STRICT_ALIGN},
131aeb82 1145 {"405", PROCESSOR_PPC405,
716019c0
JM
1146 POWERPC_BASE_MASK | MASK_SOFT_FLOAT | MASK_MULHW | MASK_DLMZB},
1147 {"405fp", PROCESSOR_PPC405,
1148 POWERPC_BASE_MASK | MASK_MULHW | MASK_DLMZB},
131aeb82 1149 {"440", PROCESSOR_PPC440,
716019c0
JM
1150 POWERPC_BASE_MASK | MASK_SOFT_FLOAT | MASK_MULHW | MASK_DLMZB},
1151 {"440fp", PROCESSOR_PPC440,
1152 POWERPC_BASE_MASK | MASK_MULHW | MASK_DLMZB},
66188a7e 1153 {"505", PROCESSOR_MPCCORE, POWERPC_BASE_MASK},
5248c961 1154 {"601", PROCESSOR_PPC601,
66188a7e
GK
1155 MASK_POWER | POWERPC_BASE_MASK | MASK_MULTIPLE | MASK_STRING},
1156 {"602", PROCESSOR_PPC603, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
1157 {"603", PROCESSOR_PPC603, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
1158 {"603e", PROCESSOR_PPC603, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
1159 {"604", PROCESSOR_PPC604, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
1160 {"604e", PROCESSOR_PPC604e, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
7ddb6568
AM
1161 {"620", PROCESSOR_PPC620,
1162 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_POWERPC64},
1163 {"630", PROCESSOR_PPC630,
1164 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_POWERPC64},
66188a7e
GK
1165 {"740", PROCESSOR_PPC750, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
1166 {"7400", PROCESSOR_PPC7400, POWERPC_7400_MASK},
1167 {"7450", PROCESSOR_PPC7450, POWERPC_7400_MASK},
1168 {"750", PROCESSOR_PPC750, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
1169 {"801", PROCESSOR_MPCCORE, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
1170 {"821", PROCESSOR_MPCCORE, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
1171 {"823", PROCESSOR_MPCCORE, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
1172 {"8540", PROCESSOR_PPC8540, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
4d4cbc0e
AH
1173 /* 8548 has a dummy entry for now. */
1174 {"8548", PROCESSOR_PPC8540, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
66188a7e 1175 {"860", PROCESSOR_MPCCORE, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
7177e720 1176 {"970", PROCESSOR_POWER4,
66188a7e
GK
1177 POWERPC_7400_MASK | MASK_PPC_GPOPT | MASK_MFCRF | MASK_POWERPC64},
1178 {"common", PROCESSOR_COMMON, MASK_NEW_MNEMONICS},
1179 {"ec603e", PROCESSOR_PPC603, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
1180 {"G3", PROCESSOR_PPC750, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
1181 {"G4", PROCESSOR_PPC7450, POWERPC_7400_MASK},
49ffe578 1182 {"G5", PROCESSOR_POWER4,
66188a7e
GK
1183 POWERPC_7400_MASK | MASK_PPC_GPOPT | MASK_MFCRF | MASK_POWERPC64},
1184 {"power", PROCESSOR_POWER, MASK_POWER | MASK_MULTIPLE | MASK_STRING},
1185 {"power2", PROCESSOR_POWER,
1186 MASK_POWER | MASK_POWER2 | MASK_MULTIPLE | MASK_STRING},
7ddb6568
AM
1187 {"power3", PROCESSOR_PPC630,
1188 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_POWERPC64},
1189 {"power4", PROCESSOR_POWER4,
fc091c8e 1190 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_MFCRF | MASK_POWERPC64},
ec507f2d 1191 {"power5", PROCESSOR_POWER5,
432218ba
DE
1192 POWERPC_BASE_MASK | MASK_POWERPC64 | MASK_PPC_GFXOPT
1193 | MASK_MFCRF | MASK_POPCNTB},
9719f3b7
DE
1194 {"power5+", PROCESSOR_POWER5,
1195 POWERPC_BASE_MASK | MASK_POWERPC64 | MASK_PPC_GFXOPT
1196 | MASK_MFCRF | MASK_POPCNTB | MASK_FPRND},
66188a7e
GK
1197 {"powerpc", PROCESSOR_POWERPC, POWERPC_BASE_MASK},
1198 {"powerpc64", PROCESSOR_POWERPC64,
98c41d98 1199 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_POWERPC64},
66188a7e
GK
1200 {"rios", PROCESSOR_RIOS1, MASK_POWER | MASK_MULTIPLE | MASK_STRING},
1201 {"rios1", PROCESSOR_RIOS1, MASK_POWER | MASK_MULTIPLE | MASK_STRING},
1202 {"rios2", PROCESSOR_RIOS2,
1203 MASK_POWER | MASK_POWER2 | MASK_MULTIPLE | MASK_STRING},
1204 {"rsc", PROCESSOR_PPC601, MASK_POWER | MASK_MULTIPLE | MASK_STRING},
1205 {"rsc1", PROCESSOR_PPC601, MASK_POWER | MASK_MULTIPLE | MASK_STRING},
98c41d98
DE
1206 {"rs64", PROCESSOR_RS64A,
1207 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_POWERPC64}
66188a7e 1208 };
5248c961 1209
ca7558fc 1210 const size_t ptt_size = ARRAY_SIZE (processor_target_table);
5248c961 1211
66188a7e
GK
1212 /* Some OSs don't support saving the high part of 64-bit registers on
1213 context switch. Other OSs don't support saving Altivec registers.
1214 On those OSs, we don't touch the MASK_POWERPC64 or MASK_ALTIVEC
1215 settings; if the user wants either, the user must explicitly specify
1216 them and we won't interfere with the user's specification. */
1217
1218 enum {
1219 POWER_MASKS = MASK_POWER | MASK_POWER2 | MASK_MULTIPLE | MASK_STRING,
f676971a 1220 POWERPC_MASKS = (POWERPC_BASE_MASK | MASK_PPC_GPOPT
66188a7e 1221 | MASK_PPC_GFXOPT | MASK_POWERPC64 | MASK_ALTIVEC
716019c0
JM
1222 | MASK_MFCRF | MASK_POPCNTB | MASK_FPRND | MASK_MULHW
1223 | MASK_DLMZB)
66188a7e 1224 };
0d1fbc8c
AH
1225
1226 rs6000_init_hard_regno_mode_ok ();
1227
c4ad648e 1228 set_masks = POWER_MASKS | POWERPC_MASKS | MASK_SOFT_FLOAT;
66188a7e
GK
1229#ifdef OS_MISSING_POWERPC64
1230 if (OS_MISSING_POWERPC64)
1231 set_masks &= ~MASK_POWERPC64;
1232#endif
1233#ifdef OS_MISSING_ALTIVEC
1234 if (OS_MISSING_ALTIVEC)
1235 set_masks &= ~MASK_ALTIVEC;
1236#endif
1237
768875a8
AM
1238 /* Don't override by the processor default if given explicitly. */
1239 set_masks &= ~target_flags_explicit;
957211c3 1240
a4f6c312 1241 /* Identify the processor type. */
8e3f41e7 1242 rs6000_select[0].string = default_cpu;
3cb999d8 1243 rs6000_cpu = TARGET_POWERPC64 ? PROCESSOR_DEFAULT64 : PROCESSOR_DEFAULT;
8e3f41e7 1244
b6a1cbae 1245 for (i = 0; i < ARRAY_SIZE (rs6000_select); i++)
5248c961 1246 {
8e3f41e7
MM
1247 ptr = &rs6000_select[i];
1248 if (ptr->string != (char *)0 && ptr->string[0] != '\0')
5248c961 1249 {
8e3f41e7
MM
1250 for (j = 0; j < ptt_size; j++)
1251 if (! strcmp (ptr->string, processor_target_table[j].name))
1252 {
1253 if (ptr->set_tune_p)
1254 rs6000_cpu = processor_target_table[j].processor;
1255
1256 if (ptr->set_arch_p)
1257 {
66188a7e
GK
1258 target_flags &= ~set_masks;
1259 target_flags |= (processor_target_table[j].target_enable
1260 & set_masks);
8e3f41e7
MM
1261 }
1262 break;
1263 }
1264
4406229e 1265 if (j == ptt_size)
8e3f41e7 1266 error ("bad value (%s) for %s switch", ptr->string, ptr->name);
5248c961
RK
1267 }
1268 }
8a61d227 1269
993f19a8 1270 if (TARGET_E500)
a3170dc6
AH
1271 rs6000_isel = 1;
1272
dff9f1b6
DE
1273 /* If we are optimizing big endian systems for space, use the load/store
1274 multiple and string instructions. */
ef792183 1275 if (BYTES_BIG_ENDIAN && optimize_size)
957211c3 1276 target_flags |= ~target_flags_explicit & (MASK_MULTIPLE | MASK_STRING);
938937d8 1277
a4f6c312
SS
1278 /* Don't allow -mmultiple or -mstring on little endian systems
1279 unless the cpu is a 750, because the hardware doesn't support the
1280 instructions used in little endian mode, and causes an alignment
1281 trap. The 750 does not cause an alignment trap (except when the
1282 target is unaligned). */
bef84347 1283
b21fb038 1284 if (!BYTES_BIG_ENDIAN && rs6000_cpu != PROCESSOR_PPC750)
7e69e155
MM
1285 {
1286 if (TARGET_MULTIPLE)
1287 {
1288 target_flags &= ~MASK_MULTIPLE;
b21fb038 1289 if ((target_flags_explicit & MASK_MULTIPLE) != 0)
d4ee4d25 1290 warning (0, "-mmultiple is not supported on little endian systems");
7e69e155
MM
1291 }
1292
1293 if (TARGET_STRING)
1294 {
1295 target_flags &= ~MASK_STRING;
b21fb038 1296 if ((target_flags_explicit & MASK_STRING) != 0)
d4ee4d25 1297 warning (0, "-mstring is not supported on little endian systems");
7e69e155
MM
1298 }
1299 }
3933e0e1 1300
38c1f2d7
MM
1301 /* Set debug flags */
1302 if (rs6000_debug_name)
1303 {
bfc79d3b 1304 if (! strcmp (rs6000_debug_name, "all"))
38c1f2d7 1305 rs6000_debug_stack = rs6000_debug_arg = 1;
bfc79d3b 1306 else if (! strcmp (rs6000_debug_name, "stack"))
38c1f2d7 1307 rs6000_debug_stack = 1;
bfc79d3b 1308 else if (! strcmp (rs6000_debug_name, "arg"))
38c1f2d7
MM
1309 rs6000_debug_arg = 1;
1310 else
c725bd79 1311 error ("unknown -mdebug-%s switch", rs6000_debug_name);
38c1f2d7
MM
1312 }
1313
57ac7be9
AM
1314 if (rs6000_traceback_name)
1315 {
1316 if (! strncmp (rs6000_traceback_name, "full", 4))
1317 rs6000_traceback = traceback_full;
1318 else if (! strncmp (rs6000_traceback_name, "part", 4))
1319 rs6000_traceback = traceback_part;
1320 else if (! strncmp (rs6000_traceback_name, "no", 2))
1321 rs6000_traceback = traceback_none;
1322 else
9e637a26 1323 error ("unknown -mtraceback arg %qs; expecting %<full%>, %<partial%> or %<none%>",
57ac7be9
AM
1324 rs6000_traceback_name);
1325 }
1326
78f5898b
AH
1327 if (!rs6000_explicit_options.long_double)
1328 rs6000_long_double_type_size = RS6000_DEFAULT_LONG_DOUBLE_SIZE;
6fa3f289 1329
602ea4d3 1330#ifndef POWERPC_LINUX
d3603e8c 1331 if (!rs6000_explicit_options.ieee)
602ea4d3
JJ
1332 rs6000_ieeequad = 1;
1333#endif
1334
6d0ef01e
HP
1335 /* Set Altivec ABI as default for powerpc64 linux. */
1336 if (TARGET_ELF && TARGET_64BIT)
1337 {
1338 rs6000_altivec_abi = 1;
78f5898b 1339 TARGET_ALTIVEC_VRSAVE = 1;
6d0ef01e
HP
1340 }
1341
594a51fe
SS
1342 /* Set the Darwin64 ABI as default for 64-bit Darwin. */
1343 if (DEFAULT_ABI == ABI_DARWIN && TARGET_64BIT)
1344 {
1345 rs6000_darwin64_abi = 1;
9c7956fd 1346#if TARGET_MACHO
6ac49599 1347 darwin_one_byte_bool = 1;
9c7956fd 1348#endif
d9168963
SS
1349 /* Default to natural alignment, for better performance. */
1350 rs6000_alignment_flags = MASK_ALIGN_NATURAL;
594a51fe
SS
1351 }
1352
c4501e62
JJ
1353 /* Handle -mtls-size option. */
1354 rs6000_parse_tls_size_option ();
1355
a7ae18e2
AH
1356#ifdef SUBTARGET_OVERRIDE_OPTIONS
1357 SUBTARGET_OVERRIDE_OPTIONS;
1358#endif
1359#ifdef SUBSUBTARGET_OVERRIDE_OPTIONS
1360 SUBSUBTARGET_OVERRIDE_OPTIONS;
1361#endif
4d4cbc0e
AH
1362#ifdef SUB3TARGET_OVERRIDE_OPTIONS
1363 SUB3TARGET_OVERRIDE_OPTIONS;
1364#endif
a7ae18e2 1365
5da702b1
AH
1366 if (TARGET_E500)
1367 {
e4463bf1
AH
1368 if (TARGET_ALTIVEC)
1369 error ("AltiVec and E500 instructions cannot coexist");
1370
5da702b1
AH
1371 /* The e500 does not have string instructions, and we set
1372 MASK_STRING above when optimizing for size. */
1373 if ((target_flags & MASK_STRING) != 0)
1374 target_flags = target_flags & ~MASK_STRING;
1375 }
1376 else if (rs6000_select[1].string != NULL)
1377 {
1378 /* For the powerpc-eabispe configuration, we set all these by
1379 default, so let's unset them if we manually set another
1380 CPU that is not the E500. */
78f5898b 1381 if (!rs6000_explicit_options.abi)
5da702b1 1382 rs6000_spe_abi = 0;
78f5898b 1383 if (!rs6000_explicit_options.spe)
5da702b1 1384 rs6000_spe = 0;
78f5898b 1385 if (!rs6000_explicit_options.float_gprs)
5da702b1 1386 rs6000_float_gprs = 0;
78f5898b 1387 if (!rs6000_explicit_options.isel)
5da702b1 1388 rs6000_isel = 0;
78f5898b 1389 if (!rs6000_explicit_options.long_double)
c1e55850 1390 rs6000_long_double_type_size = RS6000_DEFAULT_LONG_DOUBLE_SIZE;
5da702b1 1391 }
b5044283 1392
ec507f2d
DE
1393 rs6000_always_hint = (rs6000_cpu != PROCESSOR_POWER4
1394 && rs6000_cpu != PROCESSOR_POWER5);
1395 rs6000_sched_groups = (rs6000_cpu == PROCESSOR_POWER4
1396 || rs6000_cpu == PROCESSOR_POWER5);
1397
ec507f2d
DE
1398 rs6000_sched_restricted_insns_priority
1399 = (rs6000_sched_groups ? 1 : 0);
79ae11c4 1400
569fa502 1401 /* Handle -msched-costly-dep option. */
ec507f2d
DE
1402 rs6000_sched_costly_dep
1403 = (rs6000_sched_groups ? store_to_load_dep_costly : no_dep_costly);
432218ba 1404
569fa502
DN
1405 if (rs6000_sched_costly_dep_str)
1406 {
f676971a 1407 if (! strcmp (rs6000_sched_costly_dep_str, "no"))
c4ad648e 1408 rs6000_sched_costly_dep = no_dep_costly;
569fa502 1409 else if (! strcmp (rs6000_sched_costly_dep_str, "all"))
c4ad648e 1410 rs6000_sched_costly_dep = all_deps_costly;
569fa502 1411 else if (! strcmp (rs6000_sched_costly_dep_str, "true_store_to_load"))
c4ad648e 1412 rs6000_sched_costly_dep = true_store_to_load_dep_costly;
569fa502 1413 else if (! strcmp (rs6000_sched_costly_dep_str, "store_to_load"))
c4ad648e 1414 rs6000_sched_costly_dep = store_to_load_dep_costly;
f676971a 1415 else
c4ad648e 1416 rs6000_sched_costly_dep = atoi (rs6000_sched_costly_dep_str);
cbe26ab8
DN
1417 }
1418
1419 /* Handle -minsert-sched-nops option. */
ec507f2d
DE
1420 rs6000_sched_insert_nops
1421 = (rs6000_sched_groups ? sched_finish_regroup_exact : sched_finish_none);
432218ba 1422
cbe26ab8
DN
1423 if (rs6000_sched_insert_nops_str)
1424 {
1425 if (! strcmp (rs6000_sched_insert_nops_str, "no"))
c4ad648e 1426 rs6000_sched_insert_nops = sched_finish_none;
cbe26ab8 1427 else if (! strcmp (rs6000_sched_insert_nops_str, "pad"))
c4ad648e 1428 rs6000_sched_insert_nops = sched_finish_pad_groups;
cbe26ab8 1429 else if (! strcmp (rs6000_sched_insert_nops_str, "regroup_exact"))
c4ad648e 1430 rs6000_sched_insert_nops = sched_finish_regroup_exact;
cbe26ab8 1431 else
c4ad648e 1432 rs6000_sched_insert_nops = atoi (rs6000_sched_insert_nops_str);
569fa502
DN
1433 }
1434
c81bebd7 1435#ifdef TARGET_REGNAMES
a4f6c312
SS
1436 /* If the user desires alternate register names, copy in the
1437 alternate names now. */
c81bebd7 1438 if (TARGET_REGNAMES)
4e135bdd 1439 memcpy (rs6000_reg_names, alt_reg_names, sizeof (rs6000_reg_names));
c81bebd7
MM
1440#endif
1441
df01da37 1442 /* Set aix_struct_return last, after the ABI is determined.
6fa3f289
ZW
1443 If -maix-struct-return or -msvr4-struct-return was explicitly
1444 used, don't override with the ABI default. */
df01da37
DE
1445 if (!rs6000_explicit_options.aix_struct_ret)
1446 aix_struct_return = (DEFAULT_ABI != ABI_V4 || DRAFT_V4_STRUCT_RET);
6fa3f289 1447
602ea4d3 1448 if (TARGET_LONG_DOUBLE_128 && !TARGET_IEEEQUAD)
70a01792 1449 REAL_MODE_FORMAT (TFmode) = &ibm_extended_format;
fcce224d 1450
f676971a 1451 if (TARGET_TOC)
9ebbca7d 1452 ASM_GENERATE_INTERNAL_LABEL (toc_label_name, "LCTOC", 1);
71f123ca 1453
301d03af
RS
1454 /* We can only guarantee the availability of DI pseudo-ops when
1455 assembling for 64-bit targets. */
ae6c1efd 1456 if (!TARGET_64BIT)
301d03af
RS
1457 {
1458 targetm.asm_out.aligned_op.di = NULL;
1459 targetm.asm_out.unaligned_op.di = NULL;
1460 }
1461
1494c534
DE
1462 /* Set branch target alignment, if not optimizing for size. */
1463 if (!optimize_size)
1464 {
1465 if (rs6000_sched_groups)
1466 {
1467 if (align_functions <= 0)
1468 align_functions = 16;
1469 if (align_jumps <= 0)
1470 align_jumps = 16;
1471 if (align_loops <= 0)
1472 align_loops = 16;
1473 }
1474 if (align_jumps_max_skip <= 0)
1475 align_jumps_max_skip = 15;
1476 if (align_loops_max_skip <= 0)
1477 align_loops_max_skip = 15;
1478 }
2792d578 1479
71f123ca
FS
1480 /* Arrange to save and restore machine status around nested functions. */
1481 init_machine_status = rs6000_init_machine_status;
42ba5130
RH
1482
1483 /* We should always be splitting complex arguments, but we can't break
1484 Linux and Darwin ABIs at the moment. For now, only AIX is fixed. */
18f63bfa 1485 if (DEFAULT_ABI != ABI_AIX)
42ba5130 1486 targetm.calls.split_complex_arg = NULL;
8b897cfa
RS
1487
1488 /* Initialize rs6000_cost with the appropriate target costs. */
1489 if (optimize_size)
1490 rs6000_cost = TARGET_POWERPC64 ? &size64_cost : &size32_cost;
1491 else
1492 switch (rs6000_cpu)
1493 {
1494 case PROCESSOR_RIOS1:
1495 rs6000_cost = &rios1_cost;
1496 break;
1497
1498 case PROCESSOR_RIOS2:
1499 rs6000_cost = &rios2_cost;
1500 break;
1501
1502 case PROCESSOR_RS64A:
1503 rs6000_cost = &rs64a_cost;
1504 break;
1505
1506 case PROCESSOR_MPCCORE:
1507 rs6000_cost = &mpccore_cost;
1508 break;
1509
1510 case PROCESSOR_PPC403:
1511 rs6000_cost = &ppc403_cost;
1512 break;
1513
1514 case PROCESSOR_PPC405:
1515 rs6000_cost = &ppc405_cost;
1516 break;
1517
1518 case PROCESSOR_PPC440:
1519 rs6000_cost = &ppc440_cost;
1520 break;
1521
1522 case PROCESSOR_PPC601:
1523 rs6000_cost = &ppc601_cost;
1524 break;
1525
1526 case PROCESSOR_PPC603:
1527 rs6000_cost = &ppc603_cost;
1528 break;
1529
1530 case PROCESSOR_PPC604:
1531 rs6000_cost = &ppc604_cost;
1532 break;
1533
1534 case PROCESSOR_PPC604e:
1535 rs6000_cost = &ppc604e_cost;
1536 break;
1537
1538 case PROCESSOR_PPC620:
8b897cfa
RS
1539 rs6000_cost = &ppc620_cost;
1540 break;
1541
f0517163
RS
1542 case PROCESSOR_PPC630:
1543 rs6000_cost = &ppc630_cost;
1544 break;
1545
8b897cfa
RS
1546 case PROCESSOR_PPC750:
1547 case PROCESSOR_PPC7400:
1548 rs6000_cost = &ppc750_cost;
1549 break;
1550
1551 case PROCESSOR_PPC7450:
1552 rs6000_cost = &ppc7450_cost;
1553 break;
1554
1555 case PROCESSOR_PPC8540:
1556 rs6000_cost = &ppc8540_cost;
1557 break;
1558
1559 case PROCESSOR_POWER4:
1560 case PROCESSOR_POWER5:
1561 rs6000_cost = &power4_cost;
1562 break;
1563
1564 default:
37409796 1565 gcc_unreachable ();
8b897cfa 1566 }
5248c961 1567}
5accd822 1568
7ccf35ed
DN
1569/* Implement targetm.vectorize.builtin_mask_for_load. */
1570static tree
1571rs6000_builtin_mask_for_load (void)
1572{
1573 if (TARGET_ALTIVEC)
1574 return altivec_builtin_mask_for_load;
1575 else
1576 return 0;
1577}
1578
5da702b1
AH
1579/* Handle generic options of the form -mfoo=yes/no.
1580 NAME is the option name.
1581 VALUE is the option value.
1582 FLAG is the pointer to the flag where to store a 1 or 0, depending on
1583 whether the option value is 'yes' or 'no' respectively. */
993f19a8 1584static void
5da702b1 1585rs6000_parse_yes_no_option (const char *name, const char *value, int *flag)
993f19a8 1586{
5da702b1 1587 if (value == 0)
993f19a8 1588 return;
5da702b1
AH
1589 else if (!strcmp (value, "yes"))
1590 *flag = 1;
1591 else if (!strcmp (value, "no"))
1592 *flag = 0;
08b57fb3 1593 else
5da702b1 1594 error ("unknown -m%s= option specified: '%s'", name, value);
08b57fb3
AH
1595}
1596
c4501e62
JJ
1597/* Validate and record the size specified with the -mtls-size option. */
1598
1599static void
863d938c 1600rs6000_parse_tls_size_option (void)
c4501e62
JJ
1601{
1602 if (rs6000_tls_size_string == 0)
1603 return;
1604 else if (strcmp (rs6000_tls_size_string, "16") == 0)
1605 rs6000_tls_size = 16;
1606 else if (strcmp (rs6000_tls_size_string, "32") == 0)
1607 rs6000_tls_size = 32;
1608 else if (strcmp (rs6000_tls_size_string, "64") == 0)
1609 rs6000_tls_size = 64;
1610 else
9e637a26 1611 error ("bad value %qs for -mtls-size switch", rs6000_tls_size_string);
c4501e62
JJ
1612}
1613
5accd822 1614void
a2369ed3 1615optimization_options (int level ATTRIBUTE_UNUSED, int size ATTRIBUTE_UNUSED)
5accd822 1616{
2e3f0db6
DJ
1617 if (DEFAULT_ABI == ABI_DARWIN)
1618 /* The Darwin libraries never set errno, so we might as well
1619 avoid calling them when that's the only reason we would. */
1620 flag_errno_math = 0;
59d6560b
DE
1621
1622 /* Double growth factor to counter reduced min jump length. */
1623 set_param_value ("max-grow-copy-bb-insns", 16);
5accd822 1624}
78f5898b
AH
1625
1626/* Implement TARGET_HANDLE_OPTION. */
1627
1628static bool
1629rs6000_handle_option (size_t code, const char *arg, int value)
1630{
1631 switch (code)
1632 {
1633 case OPT_mno_power:
1634 target_flags &= ~(MASK_POWER | MASK_POWER2
1635 | MASK_MULTIPLE | MASK_STRING);
c2dba4ab
AH
1636 target_flags_explicit |= (MASK_POWER | MASK_POWER2
1637 | MASK_MULTIPLE | MASK_STRING);
78f5898b
AH
1638 break;
1639 case OPT_mno_powerpc:
1640 target_flags &= ~(MASK_POWERPC | MASK_PPC_GPOPT
1641 | MASK_PPC_GFXOPT | MASK_POWERPC64);
c2dba4ab
AH
1642 target_flags_explicit |= (MASK_POWERPC | MASK_PPC_GPOPT
1643 | MASK_PPC_GFXOPT | MASK_POWERPC64);
78f5898b
AH
1644 break;
1645 case OPT_mfull_toc:
d2894ab5
DE
1646 target_flags &= ~MASK_MINIMAL_TOC;
1647 TARGET_NO_FP_IN_TOC = 0;
1648 TARGET_NO_SUM_IN_TOC = 0;
1649 target_flags_explicit |= MASK_MINIMAL_TOC;
78f5898b
AH
1650#ifdef TARGET_USES_SYSV4_OPT
1651 /* Note, V.4 no longer uses a normal TOC, so make -mfull-toc, be
1652 just the same as -mminimal-toc. */
1653 target_flags |= MASK_MINIMAL_TOC;
c2dba4ab 1654 target_flags_explicit |= MASK_MINIMAL_TOC;
78f5898b
AH
1655#endif
1656 break;
1657
1658#ifdef TARGET_USES_SYSV4_OPT
1659 case OPT_mtoc:
1660 /* Make -mtoc behave like -mminimal-toc. */
1661 target_flags |= MASK_MINIMAL_TOC;
c2dba4ab 1662 target_flags_explicit |= MASK_MINIMAL_TOC;
78f5898b
AH
1663 break;
1664#endif
1665
1666#ifdef TARGET_USES_AIX64_OPT
1667 case OPT_maix64:
1668#else
1669 case OPT_m64:
1670#endif
2c9c9afd
AM
1671 target_flags |= MASK_POWERPC64 | MASK_POWERPC;
1672 target_flags |= ~target_flags_explicit & MASK_PPC_GFXOPT;
1673 target_flags_explicit |= MASK_POWERPC64 | MASK_POWERPC;
78f5898b
AH
1674 break;
1675
1676#ifdef TARGET_USES_AIX64_OPT
1677 case OPT_maix32:
1678#else
1679 case OPT_m32:
1680#endif
1681 target_flags &= ~MASK_POWERPC64;
c2dba4ab 1682 target_flags_explicit |= MASK_POWERPC64;
78f5898b
AH
1683 break;
1684
1685 case OPT_minsert_sched_nops_:
1686 rs6000_sched_insert_nops_str = arg;
1687 break;
1688
1689 case OPT_mminimal_toc:
1690 if (value == 1)
1691 {
d2894ab5
DE
1692 TARGET_NO_FP_IN_TOC = 0;
1693 TARGET_NO_SUM_IN_TOC = 0;
78f5898b
AH
1694 }
1695 break;
1696
1697 case OPT_mpower:
1698 if (value == 1)
c2dba4ab
AH
1699 {
1700 target_flags |= (MASK_MULTIPLE | MASK_STRING);
1701 target_flags_explicit |= (MASK_MULTIPLE | MASK_STRING);
1702 }
78f5898b
AH
1703 break;
1704
1705 case OPT_mpower2:
1706 if (value == 1)
c2dba4ab
AH
1707 {
1708 target_flags |= (MASK_POWER | MASK_MULTIPLE | MASK_STRING);
1709 target_flags_explicit |= (MASK_POWER | MASK_MULTIPLE | MASK_STRING);
1710 }
78f5898b
AH
1711 break;
1712
1713 case OPT_mpowerpc_gpopt:
1714 case OPT_mpowerpc_gfxopt:
1715 if (value == 1)
c2dba4ab
AH
1716 {
1717 target_flags |= MASK_POWERPC;
1718 target_flags_explicit |= MASK_POWERPC;
1719 }
78f5898b
AH
1720 break;
1721
df01da37
DE
1722 case OPT_maix_struct_return:
1723 case OPT_msvr4_struct_return:
1724 rs6000_explicit_options.aix_struct_ret = true;
1725 break;
1726
78f5898b
AH
1727 case OPT_mvrsave_:
1728 rs6000_parse_yes_no_option ("vrsave", arg, &(TARGET_ALTIVEC_VRSAVE));
1729 break;
78f5898b
AH
1730
1731 case OPT_misel_:
1732 rs6000_explicit_options.isel = true;
1733 rs6000_parse_yes_no_option ("isel", arg, &(rs6000_isel));
1734 break;
1735
1736 case OPT_mspe_:
1737 rs6000_explicit_options.spe = true;
1738 rs6000_parse_yes_no_option ("spe", arg, &(rs6000_spe));
1739 /* No SPE means 64-bit long doubles, even if an E500. */
1740 if (!rs6000_spe)
1741 rs6000_long_double_type_size = 64;
1742 break;
1743
1744 case OPT_mdebug_:
1745 rs6000_debug_name = arg;
1746 break;
1747
1748#ifdef TARGET_USES_SYSV4_OPT
1749 case OPT_mcall_:
1750 rs6000_abi_name = arg;
1751 break;
1752
1753 case OPT_msdata_:
1754 rs6000_sdata_name = arg;
1755 break;
1756
1757 case OPT_mtls_size_:
1758 rs6000_tls_size_string = arg;
1759 break;
1760
1761 case OPT_mrelocatable:
1762 if (value == 1)
c2dba4ab 1763 {
e0bf274f
AM
1764 target_flags |= MASK_MINIMAL_TOC;
1765 target_flags_explicit |= MASK_MINIMAL_TOC;
1766 TARGET_NO_FP_IN_TOC = 1;
c2dba4ab 1767 }
78f5898b
AH
1768 break;
1769
1770 case OPT_mrelocatable_lib:
1771 if (value == 1)
c2dba4ab 1772 {
e0bf274f
AM
1773 target_flags |= MASK_RELOCATABLE | MASK_MINIMAL_TOC;
1774 target_flags_explicit |= MASK_RELOCATABLE | MASK_MINIMAL_TOC;
1775 TARGET_NO_FP_IN_TOC = 1;
c2dba4ab 1776 }
78f5898b 1777 else
c2dba4ab
AH
1778 {
1779 target_flags &= ~MASK_RELOCATABLE;
1780 target_flags_explicit |= MASK_RELOCATABLE;
1781 }
78f5898b
AH
1782 break;
1783#endif
1784
1785 case OPT_mabi_:
78f5898b
AH
1786 if (!strcmp (arg, "altivec"))
1787 {
d3603e8c 1788 rs6000_explicit_options.abi = true;
78f5898b
AH
1789 rs6000_altivec_abi = 1;
1790 rs6000_spe_abi = 0;
1791 }
1792 else if (! strcmp (arg, "no-altivec"))
d3603e8c
AM
1793 {
1794 /* ??? Don't set rs6000_explicit_options.abi here, to allow
1795 the default for rs6000_spe_abi to be chosen later. */
1796 rs6000_altivec_abi = 0;
1797 }
78f5898b
AH
1798 else if (! strcmp (arg, "spe"))
1799 {
d3603e8c 1800 rs6000_explicit_options.abi = true;
78f5898b
AH
1801 rs6000_spe_abi = 1;
1802 rs6000_altivec_abi = 0;
1803 if (!TARGET_SPE_ABI)
1804 error ("not configured for ABI: '%s'", arg);
1805 }
1806 else if (! strcmp (arg, "no-spe"))
d3603e8c
AM
1807 {
1808 rs6000_explicit_options.abi = true;
1809 rs6000_spe_abi = 0;
1810 }
78f5898b
AH
1811
1812 /* These are here for testing during development only, do not
1813 document in the manual please. */
1814 else if (! strcmp (arg, "d64"))
1815 {
1816 rs6000_darwin64_abi = 1;
1817 warning (0, "Using darwin64 ABI");
1818 }
1819 else if (! strcmp (arg, "d32"))
1820 {
1821 rs6000_darwin64_abi = 0;
1822 warning (0, "Using old darwin ABI");
1823 }
1824
602ea4d3
JJ
1825 else if (! strcmp (arg, "ibmlongdouble"))
1826 {
d3603e8c 1827 rs6000_explicit_options.ieee = true;
602ea4d3
JJ
1828 rs6000_ieeequad = 0;
1829 warning (0, "Using IBM extended precision long double");
1830 }
1831 else if (! strcmp (arg, "ieeelongdouble"))
1832 {
d3603e8c 1833 rs6000_explicit_options.ieee = true;
602ea4d3
JJ
1834 rs6000_ieeequad = 1;
1835 warning (0, "Using IEEE extended precision long double");
1836 }
1837
78f5898b
AH
1838 else
1839 {
1840 error ("unknown ABI specified: '%s'", arg);
1841 return false;
1842 }
1843 break;
1844
1845 case OPT_mcpu_:
1846 rs6000_select[1].string = arg;
1847 break;
1848
1849 case OPT_mtune_:
1850 rs6000_select[2].string = arg;
1851 break;
1852
1853 case OPT_mtraceback_:
1854 rs6000_traceback_name = arg;
1855 break;
1856
1857 case OPT_mfloat_gprs_:
1858 rs6000_explicit_options.float_gprs = true;
1859 if (! strcmp (arg, "yes") || ! strcmp (arg, "single"))
1860 rs6000_float_gprs = 1;
1861 else if (! strcmp (arg, "double"))
1862 rs6000_float_gprs = 2;
1863 else if (! strcmp (arg, "no"))
1864 rs6000_float_gprs = 0;
1865 else
1866 {
1867 error ("invalid option for -mfloat-gprs: '%s'", arg);
1868 return false;
1869 }
1870 break;
1871
1872 case OPT_mlong_double_:
1873 rs6000_explicit_options.long_double = true;
1874 rs6000_long_double_type_size = RS6000_DEFAULT_LONG_DOUBLE_SIZE;
1875 if (value != 64 && value != 128)
1876 {
1877 error ("Unknown switch -mlong-double-%s", arg);
1878 rs6000_long_double_type_size = RS6000_DEFAULT_LONG_DOUBLE_SIZE;
1879 return false;
1880 }
1881 else
1882 rs6000_long_double_type_size = value;
1883 break;
1884
1885 case OPT_msched_costly_dep_:
1886 rs6000_sched_costly_dep_str = arg;
1887 break;
1888
1889 case OPT_malign_:
1890 rs6000_explicit_options.alignment = true;
1891 if (! strcmp (arg, "power"))
1892 {
1893 /* On 64-bit Darwin, power alignment is ABI-incompatible with
1894 some C library functions, so warn about it. The flag may be
1895 useful for performance studies from time to time though, so
1896 don't disable it entirely. */
1897 if (DEFAULT_ABI == ABI_DARWIN && TARGET_64BIT)
1898 warning (0, "-malign-power is not supported for 64-bit Darwin;"
1899 " it is incompatible with the installed C and C++ libraries");
1900 rs6000_alignment_flags = MASK_ALIGN_POWER;
1901 }
1902 else if (! strcmp (arg, "natural"))
1903 rs6000_alignment_flags = MASK_ALIGN_NATURAL;
1904 else
1905 {
1906 error ("unknown -malign-XXXXX option specified: '%s'", arg);
1907 return false;
1908 }
1909 break;
1910 }
1911 return true;
1912}
3cfa4909
MM
1913\f
1914/* Do anything needed at the start of the asm file. */
1915
1bc7c5b6 1916static void
863d938c 1917rs6000_file_start (void)
3cfa4909 1918{
c4d38ccb 1919 size_t i;
3cfa4909 1920 char buffer[80];
d330fd93 1921 const char *start = buffer;
3cfa4909 1922 struct rs6000_cpu_select *ptr;
1bc7c5b6
ZW
1923 const char *default_cpu = TARGET_CPU_DEFAULT;
1924 FILE *file = asm_out_file;
1925
1926 default_file_start ();
1927
1928#ifdef TARGET_BI_ARCH
1929 if ((TARGET_DEFAULT ^ target_flags) & MASK_64BIT)
1930 default_cpu = 0;
1931#endif
3cfa4909
MM
1932
1933 if (flag_verbose_asm)
1934 {
1935 sprintf (buffer, "\n%s rs6000/powerpc options:", ASM_COMMENT_START);
1936 rs6000_select[0].string = default_cpu;
1937
b6a1cbae 1938 for (i = 0; i < ARRAY_SIZE (rs6000_select); i++)
3cfa4909
MM
1939 {
1940 ptr = &rs6000_select[i];
1941 if (ptr->string != (char *)0 && ptr->string[0] != '\0')
1942 {
1943 fprintf (file, "%s %s%s", start, ptr->name, ptr->string);
1944 start = "";
1945 }
1946 }
1947
9c6b4ed9 1948 if (PPC405_ERRATUM77)
b0bfee6e 1949 {
9c6b4ed9 1950 fprintf (file, "%s PPC405CR_ERRATUM77", start);
b0bfee6e
DE
1951 start = "";
1952 }
b0bfee6e 1953
b91da81f 1954#ifdef USING_ELFOS_H
3cfa4909
MM
1955 switch (rs6000_sdata)
1956 {
1957 case SDATA_NONE: fprintf (file, "%s -msdata=none", start); start = ""; break;
1958 case SDATA_DATA: fprintf (file, "%s -msdata=data", start); start = ""; break;
1959 case SDATA_SYSV: fprintf (file, "%s -msdata=sysv", start); start = ""; break;
1960 case SDATA_EABI: fprintf (file, "%s -msdata=eabi", start); start = ""; break;
1961 }
1962
1963 if (rs6000_sdata && g_switch_value)
1964 {
307b599c
MK
1965 fprintf (file, "%s -G " HOST_WIDE_INT_PRINT_UNSIGNED, start,
1966 g_switch_value);
3cfa4909
MM
1967 start = "";
1968 }
1969#endif
1970
1971 if (*start == '\0')
949ea356 1972 putc ('\n', file);
3cfa4909 1973 }
b723e82f
JJ
1974
1975 if (DEFAULT_ABI == ABI_AIX || (TARGET_ELF && flag_pic == 2))
1976 {
d6b5193b
RS
1977 switch_to_section (toc_section);
1978 switch_to_section (text_section);
b723e82f 1979 }
3cfa4909 1980}
c4e18b1c 1981
5248c961 1982\f
a0ab749a 1983/* Return nonzero if this function is known to have a null epilogue. */
9878760c
RK
1984
1985int
863d938c 1986direct_return (void)
9878760c 1987{
4697a36c
MM
1988 if (reload_completed)
1989 {
1990 rs6000_stack_t *info = rs6000_stack_info ();
1991
1992 if (info->first_gp_reg_save == 32
1993 && info->first_fp_reg_save == 64
00b960c7 1994 && info->first_altivec_reg_save == LAST_ALTIVEC_REGNO + 1
c81fc13e
DE
1995 && ! info->lr_save_p
1996 && ! info->cr_save_p
00b960c7 1997 && info->vrsave_mask == 0
c81fc13e 1998 && ! info->push_p)
4697a36c
MM
1999 return 1;
2000 }
2001
2002 return 0;
9878760c
RK
2003}
2004
4e74d8ec
MM
2005/* Return the number of instructions it takes to form a constant in an
2006 integer register. */
2007
48d72335 2008int
a2369ed3 2009num_insns_constant_wide (HOST_WIDE_INT value)
4e74d8ec
MM
2010{
2011 /* signed constant loadable with {cal|addi} */
547b216d 2012 if ((unsigned HOST_WIDE_INT) (value + 0x8000) < 0x10000)
0865c631
GK
2013 return 1;
2014
4e74d8ec 2015 /* constant loadable with {cau|addis} */
547b216d
DE
2016 else if ((value & 0xffff) == 0
2017 && (value >> 31 == -1 || value >> 31 == 0))
4e74d8ec
MM
2018 return 1;
2019
5f59ecb7 2020#if HOST_BITS_PER_WIDE_INT == 64
c81fc13e 2021 else if (TARGET_POWERPC64)
4e74d8ec 2022 {
a65c591c
DE
2023 HOST_WIDE_INT low = ((value & 0xffffffff) ^ 0x80000000) - 0x80000000;
2024 HOST_WIDE_INT high = value >> 31;
4e74d8ec 2025
a65c591c 2026 if (high == 0 || high == -1)
4e74d8ec
MM
2027 return 2;
2028
a65c591c 2029 high >>= 1;
4e74d8ec 2030
a65c591c 2031 if (low == 0)
4e74d8ec 2032 return num_insns_constant_wide (high) + 1;
4e74d8ec
MM
2033 else
2034 return (num_insns_constant_wide (high)
e396202a 2035 + num_insns_constant_wide (low) + 1);
4e74d8ec
MM
2036 }
2037#endif
2038
2039 else
2040 return 2;
2041}
2042
2043int
a2369ed3 2044num_insns_constant (rtx op, enum machine_mode mode)
4e74d8ec 2045{
37409796 2046 HOST_WIDE_INT low, high;
bb8df8a6 2047
37409796 2048 switch (GET_CODE (op))
0d30d435 2049 {
37409796 2050 case CONST_INT:
0d30d435 2051#if HOST_BITS_PER_WIDE_INT == 64
4e2c1c44 2052 if ((INTVAL (op) >> 31) != 0 && (INTVAL (op) >> 31) != -1
1990cd79 2053 && mask64_operand (op, mode))
c4ad648e 2054 return 2;
0d30d435
DE
2055 else
2056#endif
2057 return num_insns_constant_wide (INTVAL (op));
4e74d8ec 2058
37409796
NS
2059 case CONST_DOUBLE:
2060 if (mode == SFmode)
2061 {
2062 long l;
2063 REAL_VALUE_TYPE rv;
bb8df8a6 2064
37409796
NS
2065 REAL_VALUE_FROM_CONST_DOUBLE (rv, op);
2066 REAL_VALUE_TO_TARGET_SINGLE (rv, l);
2067 return num_insns_constant_wide ((HOST_WIDE_INT) l);
2068 }
a260abc9 2069
37409796
NS
2070 if (mode == VOIDmode || mode == DImode)
2071 {
2072 high = CONST_DOUBLE_HIGH (op);
2073 low = CONST_DOUBLE_LOW (op);
2074 }
2075 else
2076 {
2077 long l[2];
2078 REAL_VALUE_TYPE rv;
bb8df8a6 2079
37409796
NS
2080 REAL_VALUE_FROM_CONST_DOUBLE (rv, op);
2081 REAL_VALUE_TO_TARGET_DOUBLE (rv, l);
2082 high = l[WORDS_BIG_ENDIAN == 0];
2083 low = l[WORDS_BIG_ENDIAN != 0];
2084 }
47ad8c61 2085
37409796
NS
2086 if (TARGET_32BIT)
2087 return (num_insns_constant_wide (low)
2088 + num_insns_constant_wide (high));
2089 else
2090 {
2091 if ((high == 0 && low >= 0)
2092 || (high == -1 && low < 0))
2093 return num_insns_constant_wide (low);
bb8df8a6 2094
1990cd79 2095 else if (mask64_operand (op, mode))
37409796 2096 return 2;
bb8df8a6 2097
37409796
NS
2098 else if (low == 0)
2099 return num_insns_constant_wide (high) + 1;
bb8df8a6 2100
37409796
NS
2101 else
2102 return (num_insns_constant_wide (high)
2103 + num_insns_constant_wide (low) + 1);
2104 }
bb8df8a6 2105
37409796
NS
2106 default:
2107 gcc_unreachable ();
4e74d8ec 2108 }
4e74d8ec
MM
2109}
2110
452a7d36 2111
77ccdfed 2112/* Return true if OP can be synthesized with a particular vspltisb, vspltish
66180ff3
PB
2113 or vspltisw instruction. OP is a CONST_VECTOR. Which instruction is used
2114 depends on STEP and COPIES, one of which will be 1. If COPIES > 1,
2115 all items are set to the same value and contain COPIES replicas of the
2116 vsplt's operand; if STEP > 1, one in STEP elements is set to the vsplt's
2117 operand and the others are set to the value of the operand's msb. */
2118
2119static bool
2120vspltis_constant (rtx op, unsigned step, unsigned copies)
452a7d36 2121{
66180ff3
PB
2122 enum machine_mode mode = GET_MODE (op);
2123 enum machine_mode inner = GET_MODE_INNER (mode);
2124
2125 unsigned i;
2126 unsigned nunits = GET_MODE_NUNITS (mode);
2127 unsigned bitsize = GET_MODE_BITSIZE (inner);
2128 unsigned mask = GET_MODE_MASK (inner);
2129
2130 rtx last = CONST_VECTOR_ELT (op, nunits - 1);
2131 HOST_WIDE_INT val = INTVAL (last);
2132 HOST_WIDE_INT splat_val = val;
2133 HOST_WIDE_INT msb_val = val > 0 ? 0 : -1;
2134
2135 /* Construct the value to be splatted, if possible. If not, return 0. */
2136 for (i = 2; i <= copies; i *= 2)
452a7d36 2137 {
66180ff3
PB
2138 HOST_WIDE_INT small_val;
2139 bitsize /= 2;
2140 small_val = splat_val >> bitsize;
2141 mask >>= bitsize;
2142 if (splat_val != ((small_val << bitsize) | (small_val & mask)))
2143 return false;
2144 splat_val = small_val;
2145 }
c4ad648e 2146
66180ff3
PB
2147 /* Check if SPLAT_VAL can really be the operand of a vspltis[bhw]. */
2148 if (EASY_VECTOR_15 (splat_val))
2149 ;
2150
2151 /* Also check if we can splat, and then add the result to itself. Do so if
2152 the value is positive, of if the splat instruction is using OP's mode;
2153 for splat_val < 0, the splat and the add should use the same mode. */
2154 else if (EASY_VECTOR_15_ADD_SELF (splat_val)
2155 && (splat_val >= 0 || (step == 1 && copies == 1)))
2156 ;
2157
2158 else
2159 return false;
2160
2161 /* Check if VAL is present in every STEP-th element, and the
2162 other elements are filled with its most significant bit. */
2163 for (i = 0; i < nunits - 1; ++i)
2164 {
2165 HOST_WIDE_INT desired_val;
2166 if (((i + 1) & (step - 1)) == 0)
2167 desired_val = val;
2168 else
2169 desired_val = msb_val;
2170
2171 if (desired_val != INTVAL (CONST_VECTOR_ELT (op, i)))
2172 return false;
452a7d36 2173 }
66180ff3
PB
2174
2175 return true;
452a7d36
HP
2176}
2177
69ef87e2 2178
77ccdfed 2179/* Return true if OP is of the given MODE and can be synthesized
66180ff3
PB
2180 with a vspltisb, vspltish or vspltisw. */
2181
2182bool
2183easy_altivec_constant (rtx op, enum machine_mode mode)
d744e06e 2184{
66180ff3 2185 unsigned step, copies;
d744e06e 2186
66180ff3
PB
2187 if (mode == VOIDmode)
2188 mode = GET_MODE (op);
2189 else if (mode != GET_MODE (op))
2190 return false;
d744e06e 2191
66180ff3
PB
2192 /* Start with a vspltisw. */
2193 step = GET_MODE_NUNITS (mode) / 4;
2194 copies = 1;
2195
2196 if (vspltis_constant (op, step, copies))
2197 return true;
2198
2199 /* Then try with a vspltish. */
2200 if (step == 1)
2201 copies <<= 1;
2202 else
2203 step >>= 1;
2204
2205 if (vspltis_constant (op, step, copies))
2206 return true;
2207
2208 /* And finally a vspltisb. */
2209 if (step == 1)
2210 copies <<= 1;
2211 else
2212 step >>= 1;
2213
2214 if (vspltis_constant (op, step, copies))
2215 return true;
2216
2217 return false;
d744e06e
AH
2218}
2219
66180ff3
PB
2220/* Generate a VEC_DUPLICATE representing a vspltis[bhw] instruction whose
2221 result is OP. Abort if it is not possible. */
d744e06e 2222
f676971a 2223rtx
66180ff3 2224gen_easy_altivec_constant (rtx op)
452a7d36 2225{
66180ff3
PB
2226 enum machine_mode mode = GET_MODE (op);
2227 int nunits = GET_MODE_NUNITS (mode);
2228 rtx last = CONST_VECTOR_ELT (op, nunits - 1);
2229 unsigned step = nunits / 4;
2230 unsigned copies = 1;
2231
2232 /* Start with a vspltisw. */
2233 if (vspltis_constant (op, step, copies))
2234 return gen_rtx_VEC_DUPLICATE (V4SImode, gen_lowpart (SImode, last));
2235
2236 /* Then try with a vspltish. */
2237 if (step == 1)
2238 copies <<= 1;
2239 else
2240 step >>= 1;
2241
2242 if (vspltis_constant (op, step, copies))
2243 return gen_rtx_VEC_DUPLICATE (V8HImode, gen_lowpart (HImode, last));
2244
2245 /* And finally a vspltisb. */
2246 if (step == 1)
2247 copies <<= 1;
2248 else
2249 step >>= 1;
2250
2251 if (vspltis_constant (op, step, copies))
2252 return gen_rtx_VEC_DUPLICATE (V16QImode, gen_lowpart (QImode, last));
2253
2254 gcc_unreachable ();
d744e06e
AH
2255}
2256
2257const char *
a2369ed3 2258output_vec_const_move (rtx *operands)
d744e06e
AH
2259{
2260 int cst, cst2;
2261 enum machine_mode mode;
2262 rtx dest, vec;
2263
2264 dest = operands[0];
2265 vec = operands[1];
d744e06e 2266 mode = GET_MODE (dest);
69ef87e2 2267
d744e06e
AH
2268 if (TARGET_ALTIVEC)
2269 {
66180ff3 2270 rtx splat_vec;
d744e06e
AH
2271 if (zero_constant (vec, mode))
2272 return "vxor %0,%0,%0";
37409796 2273
66180ff3
PB
2274 splat_vec = gen_easy_altivec_constant (vec);
2275 gcc_assert (GET_CODE (splat_vec) == VEC_DUPLICATE);
2276 operands[1] = XEXP (splat_vec, 0);
2277 if (!EASY_VECTOR_15 (INTVAL (operands[1])))
2278 return "#";
bb8df8a6 2279
66180ff3 2280 switch (GET_MODE (splat_vec))
98ef3137 2281 {
37409796 2282 case V4SImode:
66180ff3 2283 return "vspltisw %0,%1";
c4ad648e 2284
37409796 2285 case V8HImode:
66180ff3 2286 return "vspltish %0,%1";
c4ad648e 2287
37409796 2288 case V16QImode:
66180ff3 2289 return "vspltisb %0,%1";
bb8df8a6 2290
37409796
NS
2291 default:
2292 gcc_unreachable ();
98ef3137 2293 }
69ef87e2
AH
2294 }
2295
37409796 2296 gcc_assert (TARGET_SPE);
bb8df8a6 2297
37409796
NS
2298 /* Vector constant 0 is handled as a splitter of V2SI, and in the
2299 pattern of V1DI, V4HI, and V2SF.
2300
2301 FIXME: We should probably return # and add post reload
2302 splitters for these, but this way is so easy ;-). */
e20dcbef
PB
2303 cst = INTVAL (CONST_VECTOR_ELT (vec, 0));
2304 cst2 = INTVAL (CONST_VECTOR_ELT (vec, 1));
2305 operands[1] = CONST_VECTOR_ELT (vec, 0);
2306 operands[2] = CONST_VECTOR_ELT (vec, 1);
37409796
NS
2307 if (cst == cst2)
2308 return "li %0,%1\n\tevmergelo %0,%0,%0";
2309 else
2310 return "li %0,%1\n\tevmergelo %0,%0,%0\n\tli %0,%2";
69ef87e2
AH
2311}
2312
7a4eca66
DE
2313/* Initialize vector TARGET to VALS. */
2314
2315void
2316rs6000_expand_vector_init (rtx target, rtx vals)
2317{
2318 enum machine_mode mode = GET_MODE (target);
2319 enum machine_mode inner_mode = GET_MODE_INNER (mode);
2320 int n_elts = GET_MODE_NUNITS (mode);
2321 int n_var = 0, one_var = -1;
2322 bool all_same = true, all_const_zero = true;
2323 rtx x, mem;
2324 int i;
2325
2326 for (i = 0; i < n_elts; ++i)
2327 {
2328 x = XVECEXP (vals, 0, i);
2329 if (!CONSTANT_P (x))
2330 ++n_var, one_var = i;
2331 else if (x != CONST0_RTX (inner_mode))
2332 all_const_zero = false;
2333
2334 if (i > 0 && !rtx_equal_p (x, XVECEXP (vals, 0, 0)))
2335 all_same = false;
2336 }
2337
2338 if (n_var == 0)
2339 {
2340 if (mode != V4SFmode && all_const_zero)
2341 {
2342 /* Zero register. */
2343 emit_insn (gen_rtx_SET (VOIDmode, target,
2344 gen_rtx_XOR (mode, target, target)));
2345 return;
2346 }
66180ff3 2347 else if (mode != V4SFmode && easy_vector_constant (vals, mode))
7a4eca66
DE
2348 {
2349 /* Splat immediate. */
66180ff3 2350 emit_insn (gen_rtx_SET (VOIDmode, target, vals));
7a4eca66
DE
2351 return;
2352 }
2353 else if (all_same)
2354 ; /* Splat vector element. */
2355 else
2356 {
2357 /* Load from constant pool. */
2358 emit_move_insn (target, gen_rtx_CONST_VECTOR (mode, XVEC (vals, 0)));
2359 return;
2360 }
2361 }
2362
2363 /* Store value to stack temp. Load vector element. Splat. */
2364 if (all_same)
2365 {
2366 mem = assign_stack_temp (mode, GET_MODE_SIZE (inner_mode), 0);
2367 emit_move_insn (adjust_address_nv (mem, inner_mode, 0),
2368 XVECEXP (vals, 0, 0));
2369 x = gen_rtx_UNSPEC (VOIDmode,
2370 gen_rtvec (1, const0_rtx), UNSPEC_LVE);
2371 emit_insn (gen_rtx_PARALLEL (VOIDmode,
2372 gen_rtvec (2,
2373 gen_rtx_SET (VOIDmode,
2374 target, mem),
2375 x)));
2376 x = gen_rtx_VEC_SELECT (inner_mode, target,
2377 gen_rtx_PARALLEL (VOIDmode,
2378 gen_rtvec (1, const0_rtx)));
2379 emit_insn (gen_rtx_SET (VOIDmode, target,
2380 gen_rtx_VEC_DUPLICATE (mode, x)));
2381 return;
2382 }
2383
2384 /* One field is non-constant. Load constant then overwrite
2385 varying field. */
2386 if (n_var == 1)
2387 {
2388 rtx copy = copy_rtx (vals);
2389
57b51d4d 2390 /* Load constant part of vector, substitute neighboring value for
7a4eca66
DE
2391 varying element. */
2392 XVECEXP (copy, 0, one_var) = XVECEXP (vals, 0, (one_var + 1) % n_elts);
2393 rs6000_expand_vector_init (target, copy);
2394
2395 /* Insert variable. */
2396 rs6000_expand_vector_set (target, XVECEXP (vals, 0, one_var), one_var);
2397 return;
2398 }
2399
2400 /* Construct the vector in memory one field at a time
2401 and load the whole vector. */
2402 mem = assign_stack_temp (mode, GET_MODE_SIZE (mode), 0);
2403 for (i = 0; i < n_elts; i++)
2404 emit_move_insn (adjust_address_nv (mem, inner_mode,
2405 i * GET_MODE_SIZE (inner_mode)),
2406 XVECEXP (vals, 0, i));
2407 emit_move_insn (target, mem);
2408}
2409
2410/* Set field ELT of TARGET to VAL. */
2411
2412void
2413rs6000_expand_vector_set (rtx target, rtx val, int elt)
2414{
2415 enum machine_mode mode = GET_MODE (target);
2416 enum machine_mode inner_mode = GET_MODE_INNER (mode);
2417 rtx reg = gen_reg_rtx (mode);
2418 rtx mask, mem, x;
2419 int width = GET_MODE_SIZE (inner_mode);
2420 int i;
2421
2422 /* Load single variable value. */
2423 mem = assign_stack_temp (mode, GET_MODE_SIZE (inner_mode), 0);
2424 emit_move_insn (adjust_address_nv (mem, inner_mode, 0), val);
2425 x = gen_rtx_UNSPEC (VOIDmode,
2426 gen_rtvec (1, const0_rtx), UNSPEC_LVE);
2427 emit_insn (gen_rtx_PARALLEL (VOIDmode,
2428 gen_rtvec (2,
2429 gen_rtx_SET (VOIDmode,
2430 reg, mem),
2431 x)));
2432
2433 /* Linear sequence. */
2434 mask = gen_rtx_PARALLEL (V16QImode, rtvec_alloc (16));
2435 for (i = 0; i < 16; ++i)
2436 XVECEXP (mask, 0, i) = GEN_INT (i);
2437
2438 /* Set permute mask to insert element into target. */
2439 for (i = 0; i < width; ++i)
2440 XVECEXP (mask, 0, elt*width + i)
2441 = GEN_INT (i + 0x10);
2442 x = gen_rtx_CONST_VECTOR (V16QImode, XVEC (mask, 0));
2443 x = gen_rtx_UNSPEC (mode,
2444 gen_rtvec (3, target, reg,
2445 force_reg (V16QImode, x)),
2446 UNSPEC_VPERM);
2447 emit_insn (gen_rtx_SET (VOIDmode, target, x));
2448}
2449
2450/* Extract field ELT from VEC into TARGET. */
2451
2452void
2453rs6000_expand_vector_extract (rtx target, rtx vec, int elt)
2454{
2455 enum machine_mode mode = GET_MODE (vec);
2456 enum machine_mode inner_mode = GET_MODE_INNER (mode);
2457 rtx mem, x;
2458
2459 /* Allocate mode-sized buffer. */
2460 mem = assign_stack_temp (mode, GET_MODE_SIZE (mode), 0);
2461
2462 /* Add offset to field within buffer matching vector element. */
2463 mem = adjust_address_nv (mem, mode, elt * GET_MODE_SIZE (inner_mode));
2464
2465 /* Store single field into mode-sized buffer. */
2466 x = gen_rtx_UNSPEC (VOIDmode,
2467 gen_rtvec (1, const0_rtx), UNSPEC_STVE);
2468 emit_insn (gen_rtx_PARALLEL (VOIDmode,
2469 gen_rtvec (2,
2470 gen_rtx_SET (VOIDmode,
2471 mem, vec),
2472 x)));
2473 emit_move_insn (target, adjust_address_nv (mem, inner_mode, 0));
2474}
2475
0ba1b2ff
AM
2476/* Generates shifts and masks for a pair of rldicl or rldicr insns to
2477 implement ANDing by the mask IN. */
2478void
a2369ed3 2479build_mask64_2_operands (rtx in, rtx *out)
0ba1b2ff
AM
2480{
2481#if HOST_BITS_PER_WIDE_INT >= 64
2482 unsigned HOST_WIDE_INT c, lsb, m1, m2;
2483 int shift;
2484
37409796 2485 gcc_assert (GET_CODE (in) == CONST_INT);
0ba1b2ff
AM
2486
2487 c = INTVAL (in);
2488 if (c & 1)
2489 {
2490 /* Assume c initially something like 0x00fff000000fffff. The idea
2491 is to rotate the word so that the middle ^^^^^^ group of zeros
2492 is at the MS end and can be cleared with an rldicl mask. We then
2493 rotate back and clear off the MS ^^ group of zeros with a
2494 second rldicl. */
2495 c = ~c; /* c == 0xff000ffffff00000 */
2496 lsb = c & -c; /* lsb == 0x0000000000100000 */
2497 m1 = -lsb; /* m1 == 0xfffffffffff00000 */
2498 c = ~c; /* c == 0x00fff000000fffff */
2499 c &= -lsb; /* c == 0x00fff00000000000 */
2500 lsb = c & -c; /* lsb == 0x0000100000000000 */
2501 c = ~c; /* c == 0xff000fffffffffff */
2502 c &= -lsb; /* c == 0xff00000000000000 */
2503 shift = 0;
2504 while ((lsb >>= 1) != 0)
2505 shift++; /* shift == 44 on exit from loop */
2506 m1 <<= 64 - shift; /* m1 == 0xffffff0000000000 */
2507 m1 = ~m1; /* m1 == 0x000000ffffffffff */
2508 m2 = ~c; /* m2 == 0x00ffffffffffffff */
a260abc9
DE
2509 }
2510 else
0ba1b2ff
AM
2511 {
2512 /* Assume c initially something like 0xff000f0000000000. The idea
2513 is to rotate the word so that the ^^^ middle group of zeros
2514 is at the LS end and can be cleared with an rldicr mask. We then
2515 rotate back and clear off the LS group of ^^^^^^^^^^ zeros with
2516 a second rldicr. */
2517 lsb = c & -c; /* lsb == 0x0000010000000000 */
2518 m2 = -lsb; /* m2 == 0xffffff0000000000 */
2519 c = ~c; /* c == 0x00fff0ffffffffff */
2520 c &= -lsb; /* c == 0x00fff00000000000 */
2521 lsb = c & -c; /* lsb == 0x0000100000000000 */
2522 c = ~c; /* c == 0xff000fffffffffff */
2523 c &= -lsb; /* c == 0xff00000000000000 */
2524 shift = 0;
2525 while ((lsb >>= 1) != 0)
2526 shift++; /* shift == 44 on exit from loop */
2527 m1 = ~c; /* m1 == 0x00ffffffffffffff */
2528 m1 >>= shift; /* m1 == 0x0000000000000fff */
2529 m1 = ~m1; /* m1 == 0xfffffffffffff000 */
2530 }
2531
2532 /* Note that when we only have two 0->1 and 1->0 transitions, one of the
2533 masks will be all 1's. We are guaranteed more than one transition. */
2534 out[0] = GEN_INT (64 - shift);
2535 out[1] = GEN_INT (m1);
2536 out[2] = GEN_INT (shift);
2537 out[3] = GEN_INT (m2);
2538#else
045572c7
GK
2539 (void)in;
2540 (void)out;
37409796 2541 gcc_unreachable ();
0ba1b2ff 2542#endif
a260abc9
DE
2543}
2544
54b695e7 2545/* Return TRUE if OP is an invalid SUBREG operation on the e500. */
48d72335
DE
2546
2547bool
54b695e7
AH
2548invalid_e500_subreg (rtx op, enum machine_mode mode)
2549{
2550 /* Reject (subreg:SI (reg:DF)). */
2551 if (GET_CODE (op) == SUBREG
2552 && mode == SImode
2553 && REG_P (SUBREG_REG (op))
2554 && GET_MODE (SUBREG_REG (op)) == DFmode)
2555 return true;
2556
2557 /* Reject (subreg:DF (reg:DI)). */
2558 if (GET_CODE (op) == SUBREG
2559 && mode == DFmode
2560 && REG_P (SUBREG_REG (op))
2561 && GET_MODE (SUBREG_REG (op)) == DImode)
2562 return true;
2563
2564 return false;
2565}
2566
95727fb8
AP
2567/* Darwin, AIX increases natural record alignment to doubleword if the first
2568 field is an FP double while the FP fields remain word aligned. */
2569
19d66194 2570unsigned int
fa5b0972
AM
2571rs6000_special_round_type_align (tree type, unsigned int computed,
2572 unsigned int specified)
95727fb8 2573{
fa5b0972 2574 unsigned int align = MAX (computed, specified);
95727fb8 2575 tree field = TYPE_FIELDS (type);
95727fb8 2576
bb8df8a6 2577 /* Skip all non field decls */
85962ac8 2578 while (field != NULL && TREE_CODE (field) != FIELD_DECL)
95727fb8
AP
2579 field = TREE_CHAIN (field);
2580
fa5b0972
AM
2581 if (field != NULL && field != type)
2582 {
2583 type = TREE_TYPE (field);
2584 while (TREE_CODE (type) == ARRAY_TYPE)
2585 type = TREE_TYPE (type);
2586
2587 if (type != error_mark_node && TYPE_MODE (type) == DFmode)
2588 align = MAX (align, 64);
2589 }
95727fb8 2590
fa5b0972 2591 return align;
95727fb8
AP
2592}
2593
a4f6c312 2594/* Return 1 for an operand in small memory on V.4/eabi. */
7509c759
MM
2595
2596int
f676971a 2597small_data_operand (rtx op ATTRIBUTE_UNUSED,
a2369ed3 2598 enum machine_mode mode ATTRIBUTE_UNUSED)
7509c759 2599{
38c1f2d7 2600#if TARGET_ELF
5f59ecb7 2601 rtx sym_ref;
7509c759 2602
d9407988 2603 if (rs6000_sdata == SDATA_NONE || rs6000_sdata == SDATA_DATA)
a54d04b7 2604 return 0;
a54d04b7 2605
f607bc57 2606 if (DEFAULT_ABI != ABI_V4)
7509c759
MM
2607 return 0;
2608
88228c4b
MM
2609 if (GET_CODE (op) == SYMBOL_REF)
2610 sym_ref = op;
2611
2612 else if (GET_CODE (op) != CONST
2613 || GET_CODE (XEXP (op, 0)) != PLUS
2614 || GET_CODE (XEXP (XEXP (op, 0), 0)) != SYMBOL_REF
2615 || GET_CODE (XEXP (XEXP (op, 0), 1)) != CONST_INT)
7509c759
MM
2616 return 0;
2617
88228c4b 2618 else
dbf55e53
MM
2619 {
2620 rtx sum = XEXP (op, 0);
2621 HOST_WIDE_INT summand;
2622
2623 /* We have to be careful here, because it is the referenced address
c4ad648e 2624 that must be 32k from _SDA_BASE_, not just the symbol. */
dbf55e53 2625 summand = INTVAL (XEXP (sum, 1));
307b599c 2626 if (summand < 0 || (unsigned HOST_WIDE_INT) summand > g_switch_value)
9390387d 2627 return 0;
dbf55e53
MM
2628
2629 sym_ref = XEXP (sum, 0);
2630 }
88228c4b 2631
20bfcd69 2632 return SYMBOL_REF_SMALL_P (sym_ref);
d9407988
MM
2633#else
2634 return 0;
2635#endif
7509c759 2636}
46c07df8 2637
3a1f863f 2638/* Return true if either operand is a general purpose register. */
46c07df8 2639
3a1f863f
DE
2640bool
2641gpr_or_gpr_p (rtx op0, rtx op1)
46c07df8 2642{
3a1f863f
DE
2643 return ((REG_P (op0) && INT_REGNO_P (REGNO (op0)))
2644 || (REG_P (op1) && INT_REGNO_P (REGNO (op1))));
46c07df8
HP
2645}
2646
9ebbca7d 2647\f
4d588c14
RH
2648/* Subroutines of rs6000_legitimize_address and rs6000_legitimate_address. */
2649
f676971a
EC
2650static int
2651constant_pool_expr_1 (rtx op, int *have_sym, int *have_toc)
9ebbca7d 2652{
9390387d 2653 switch (GET_CODE (op))
9ebbca7d
GK
2654 {
2655 case SYMBOL_REF:
c4501e62
JJ
2656 if (RS6000_SYMBOL_REF_TLS_P (op))
2657 return 0;
2658 else if (CONSTANT_POOL_ADDRESS_P (op))
a4f6c312
SS
2659 {
2660 if (ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (get_pool_constant (op), Pmode))
2661 {
2662 *have_sym = 1;
2663 return 1;
2664 }
2665 else
2666 return 0;
2667 }
2668 else if (! strcmp (XSTR (op, 0), toc_label_name))
2669 {
2670 *have_toc = 1;
2671 return 1;
2672 }
2673 else
2674 return 0;
9ebbca7d
GK
2675 case PLUS:
2676 case MINUS:
c1f11548
DE
2677 return (constant_pool_expr_1 (XEXP (op, 0), have_sym, have_toc)
2678 && constant_pool_expr_1 (XEXP (op, 1), have_sym, have_toc));
9ebbca7d 2679 case CONST:
a4f6c312 2680 return constant_pool_expr_1 (XEXP (op, 0), have_sym, have_toc);
9ebbca7d 2681 case CONST_INT:
a4f6c312 2682 return 1;
9ebbca7d 2683 default:
a4f6c312 2684 return 0;
9ebbca7d
GK
2685 }
2686}
2687
4d588c14 2688static bool
a2369ed3 2689constant_pool_expr_p (rtx op)
9ebbca7d
GK
2690{
2691 int have_sym = 0;
2692 int have_toc = 0;
2693 return constant_pool_expr_1 (op, &have_sym, &have_toc) && have_sym;
2694}
2695
48d72335 2696bool
a2369ed3 2697toc_relative_expr_p (rtx op)
9ebbca7d 2698{
4d588c14
RH
2699 int have_sym = 0;
2700 int have_toc = 0;
2701 return constant_pool_expr_1 (op, &have_sym, &have_toc) && have_toc;
2702}
2703
4d588c14 2704bool
a2369ed3 2705legitimate_constant_pool_address_p (rtx x)
4d588c14
RH
2706{
2707 return (TARGET_TOC
2708 && GET_CODE (x) == PLUS
2709 && GET_CODE (XEXP (x, 0)) == REG
2710 && (TARGET_MINIMAL_TOC || REGNO (XEXP (x, 0)) == TOC_REGISTER)
2711 && constant_pool_expr_p (XEXP (x, 1)));
2712}
2713
d04b6e6e
EB
2714static bool
2715legitimate_small_data_p (enum machine_mode mode, rtx x)
4d588c14
RH
2716{
2717 return (DEFAULT_ABI == ABI_V4
2718 && !flag_pic && !TARGET_TOC
2719 && (GET_CODE (x) == SYMBOL_REF || GET_CODE (x) == CONST)
2720 && small_data_operand (x, mode));
2721}
2722
60cdabab
DE
2723/* SPE offset addressing is limited to 5-bits worth of double words. */
2724#define SPE_CONST_OFFSET_OK(x) (((x) & ~0xf8) == 0)
2725
76d2b81d
DJ
2726bool
2727rs6000_legitimate_offset_address_p (enum machine_mode mode, rtx x, int strict)
4d588c14
RH
2728{
2729 unsigned HOST_WIDE_INT offset, extra;
2730
2731 if (GET_CODE (x) != PLUS)
2732 return false;
2733 if (GET_CODE (XEXP (x, 0)) != REG)
2734 return false;
2735 if (!INT_REG_OK_FOR_BASE_P (XEXP (x, 0), strict))
2736 return false;
60cdabab
DE
2737 if (legitimate_constant_pool_address_p (x))
2738 return true;
4d588c14
RH
2739 if (GET_CODE (XEXP (x, 1)) != CONST_INT)
2740 return false;
2741
2742 offset = INTVAL (XEXP (x, 1));
2743 extra = 0;
2744 switch (mode)
2745 {
2746 case V16QImode:
2747 case V8HImode:
2748 case V4SFmode:
2749 case V4SImode:
7a4eca66
DE
2750 /* AltiVec vector modes. Only reg+reg addressing is valid and
2751 constant offset zero should not occur due to canonicalization.
2752 Allow any offset when not strict before reload. */
2753 return !strict;
4d588c14
RH
2754
2755 case V4HImode:
2756 case V2SImode:
2757 case V1DImode:
2758 case V2SFmode:
2759 /* SPE vector modes. */
2760 return SPE_CONST_OFFSET_OK (offset);
2761
2762 case DFmode:
4d4cbc0e
AH
2763 if (TARGET_E500_DOUBLE)
2764 return SPE_CONST_OFFSET_OK (offset);
2765
4d588c14 2766 case DImode:
54b695e7
AH
2767 /* On e500v2, we may have:
2768
2769 (subreg:DF (mem:DI (plus (reg) (const_int))) 0).
2770
2771 Which gets addressed with evldd instructions. */
2772 if (TARGET_E500_DOUBLE)
2773 return SPE_CONST_OFFSET_OK (offset);
2774
3364872d 2775 if (mode == DFmode || !TARGET_POWERPC64)
4d588c14
RH
2776 extra = 4;
2777 else if (offset & 3)
2778 return false;
2779 break;
2780
2781 case TFmode:
2782 case TImode:
3364872d 2783 if (mode == TFmode || !TARGET_POWERPC64)
4d588c14
RH
2784 extra = 12;
2785 else if (offset & 3)
2786 return false;
2787 else
2788 extra = 8;
2789 break;
2790
2791 default:
2792 break;
2793 }
2794
b1917422
AM
2795 offset += 0x8000;
2796 return (offset < 0x10000) && (offset + extra < 0x10000);
4d588c14
RH
2797}
2798
2799static bool
a2369ed3 2800legitimate_indexed_address_p (rtx x, int strict)
4d588c14
RH
2801{
2802 rtx op0, op1;
2803
2804 if (GET_CODE (x) != PLUS)
2805 return false;
850e8d3d 2806
4d588c14
RH
2807 op0 = XEXP (x, 0);
2808 op1 = XEXP (x, 1);
2809
bf00cc0f 2810 /* Recognize the rtl generated by reload which we know will later be
9024f4b8
AM
2811 replaced with proper base and index regs. */
2812 if (!strict
2813 && reload_in_progress
2814 && (REG_P (op0) || GET_CODE (op0) == PLUS)
2815 && REG_P (op1))
2816 return true;
2817
2818 return (REG_P (op0) && REG_P (op1)
2819 && ((INT_REG_OK_FOR_BASE_P (op0, strict)
2820 && INT_REG_OK_FOR_INDEX_P (op1, strict))
2821 || (INT_REG_OK_FOR_BASE_P (op1, strict)
2822 && INT_REG_OK_FOR_INDEX_P (op0, strict))));
9ebbca7d
GK
2823}
2824
48d72335 2825inline bool
a2369ed3 2826legitimate_indirect_address_p (rtx x, int strict)
4d588c14
RH
2827{
2828 return GET_CODE (x) == REG && INT_REG_OK_FOR_BASE_P (x, strict);
2829}
2830
48d72335 2831bool
4c81e946
FJ
2832macho_lo_sum_memory_operand (rtx x, enum machine_mode mode)
2833{
c4ad648e 2834 if (!TARGET_MACHO || !flag_pic
9390387d 2835 || mode != SImode || GET_CODE (x) != MEM)
c4ad648e
AM
2836 return false;
2837 x = XEXP (x, 0);
4c81e946
FJ
2838
2839 if (GET_CODE (x) != LO_SUM)
2840 return false;
2841 if (GET_CODE (XEXP (x, 0)) != REG)
2842 return false;
2843 if (!INT_REG_OK_FOR_BASE_P (XEXP (x, 0), 0))
2844 return false;
2845 x = XEXP (x, 1);
2846
2847 return CONSTANT_P (x);
2848}
2849
4d588c14 2850static bool
a2369ed3 2851legitimate_lo_sum_address_p (enum machine_mode mode, rtx x, int strict)
4d588c14
RH
2852{
2853 if (GET_CODE (x) != LO_SUM)
2854 return false;
2855 if (GET_CODE (XEXP (x, 0)) != REG)
2856 return false;
2857 if (!INT_REG_OK_FOR_BASE_P (XEXP (x, 0), strict))
2858 return false;
54b695e7
AH
2859 /* Restrict addressing for DI because of our SUBREG hackery. */
2860 if (TARGET_E500_DOUBLE && (mode == DFmode || mode == DImode))
f82f556d 2861 return false;
4d588c14
RH
2862 x = XEXP (x, 1);
2863
8622e235 2864 if (TARGET_ELF || TARGET_MACHO)
4d588c14 2865 {
a29077da 2866 if (DEFAULT_ABI != ABI_AIX && DEFAULT_ABI != ABI_DARWIN && flag_pic)
4d588c14
RH
2867 return false;
2868 if (TARGET_TOC)
2869 return false;
2870 if (GET_MODE_NUNITS (mode) != 1)
2871 return false;
5e5f01b9 2872 if (GET_MODE_BITSIZE (mode) > 64
3c028f65
AM
2873 || (GET_MODE_BITSIZE (mode) > 32 && !TARGET_POWERPC64
2874 && !(TARGET_HARD_FLOAT && TARGET_FPRS && mode == DFmode)))
4d588c14
RH
2875 return false;
2876
2877 return CONSTANT_P (x);
2878 }
2879
2880 return false;
2881}
2882
2883
9ebbca7d
GK
2884/* Try machine-dependent ways of modifying an illegitimate address
2885 to be legitimate. If we find one, return the new, valid address.
2886 This is used from only one place: `memory_address' in explow.c.
2887
a4f6c312
SS
2888 OLDX is the address as it was before break_out_memory_refs was
2889 called. In some cases it is useful to look at this to decide what
2890 needs to be done.
9ebbca7d 2891
a4f6c312 2892 MODE is passed so that this function can use GO_IF_LEGITIMATE_ADDRESS.
9ebbca7d 2893
a4f6c312
SS
2894 It is always safe for this function to do nothing. It exists to
2895 recognize opportunities to optimize the output.
9ebbca7d
GK
2896
2897 On RS/6000, first check for the sum of a register with a constant
2898 integer that is out of range. If so, generate code to add the
2899 constant with the low-order 16 bits masked to the register and force
2900 this result into another register (this can be done with `cau').
2901 Then generate an address of REG+(CONST&0xffff), allowing for the
2902 possibility of bit 16 being a one.
2903
2904 Then check for the sum of a register and something not constant, try to
2905 load the other things into a register and return the sum. */
4d588c14 2906
9ebbca7d 2907rtx
a2369ed3
DJ
2908rs6000_legitimize_address (rtx x, rtx oldx ATTRIBUTE_UNUSED,
2909 enum machine_mode mode)
0ac081f6 2910{
c4501e62
JJ
2911 if (GET_CODE (x) == SYMBOL_REF)
2912 {
2913 enum tls_model model = SYMBOL_REF_TLS_MODEL (x);
2914 if (model != 0)
2915 return rs6000_legitimize_tls_address (x, model);
2916 }
2917
f676971a 2918 if (GET_CODE (x) == PLUS
9ebbca7d
GK
2919 && GET_CODE (XEXP (x, 0)) == REG
2920 && GET_CODE (XEXP (x, 1)) == CONST_INT
2921 && (unsigned HOST_WIDE_INT) (INTVAL (XEXP (x, 1)) + 0x8000) >= 0x10000)
f676971a 2922 {
9ebbca7d
GK
2923 HOST_WIDE_INT high_int, low_int;
2924 rtx sum;
a65c591c
DE
2925 low_int = ((INTVAL (XEXP (x, 1)) & 0xffff) ^ 0x8000) - 0x8000;
2926 high_int = INTVAL (XEXP (x, 1)) - low_int;
9ebbca7d
GK
2927 sum = force_operand (gen_rtx_PLUS (Pmode, XEXP (x, 0),
2928 GEN_INT (high_int)), 0);
2929 return gen_rtx_PLUS (Pmode, sum, GEN_INT (low_int));
2930 }
f676971a 2931 else if (GET_CODE (x) == PLUS
9ebbca7d
GK
2932 && GET_CODE (XEXP (x, 0)) == REG
2933 && GET_CODE (XEXP (x, 1)) != CONST_INT
6ac7bf2c 2934 && GET_MODE_NUNITS (mode) == 1
a3170dc6
AH
2935 && ((TARGET_HARD_FLOAT && TARGET_FPRS)
2936 || TARGET_POWERPC64
54b695e7
AH
2937 || (((mode != DImode && mode != DFmode) || TARGET_E500_DOUBLE)
2938 && mode != TFmode))
9ebbca7d
GK
2939 && (TARGET_POWERPC64 || mode != DImode)
2940 && mode != TImode)
2941 {
2942 return gen_rtx_PLUS (Pmode, XEXP (x, 0),
2943 force_reg (Pmode, force_operand (XEXP (x, 1), 0)));
2944 }
0ac081f6
AH
2945 else if (ALTIVEC_VECTOR_MODE (mode))
2946 {
2947 rtx reg;
2948
2949 /* Make sure both operands are registers. */
2950 if (GET_CODE (x) == PLUS)
9f85ed45 2951 return gen_rtx_PLUS (Pmode, force_reg (Pmode, XEXP (x, 0)),
0ac081f6
AH
2952 force_reg (Pmode, XEXP (x, 1)));
2953
2954 reg = force_reg (Pmode, x);
2955 return reg;
2956 }
4d4cbc0e 2957 else if (SPE_VECTOR_MODE (mode)
54b695e7
AH
2958 || (TARGET_E500_DOUBLE && (mode == DFmode
2959 || mode == DImode)))
a3170dc6 2960 {
54b695e7
AH
2961 if (mode == DImode)
2962 return NULL_RTX;
a3170dc6
AH
2963 /* We accept [reg + reg] and [reg + OFFSET]. */
2964
2965 if (GET_CODE (x) == PLUS)
c4ad648e
AM
2966 {
2967 rtx op1 = XEXP (x, 0);
2968 rtx op2 = XEXP (x, 1);
a3170dc6 2969
c4ad648e 2970 op1 = force_reg (Pmode, op1);
a3170dc6 2971
c4ad648e
AM
2972 if (GET_CODE (op2) != REG
2973 && (GET_CODE (op2) != CONST_INT
2974 || !SPE_CONST_OFFSET_OK (INTVAL (op2))))
2975 op2 = force_reg (Pmode, op2);
a3170dc6 2976
c4ad648e
AM
2977 return gen_rtx_PLUS (Pmode, op1, op2);
2978 }
a3170dc6
AH
2979
2980 return force_reg (Pmode, x);
2981 }
f1384257
AM
2982 else if (TARGET_ELF
2983 && TARGET_32BIT
2984 && TARGET_NO_TOC
2985 && ! flag_pic
9ebbca7d 2986 && GET_CODE (x) != CONST_INT
f676971a 2987 && GET_CODE (x) != CONST_DOUBLE
9ebbca7d 2988 && CONSTANT_P (x)
6ac7bf2c
GK
2989 && GET_MODE_NUNITS (mode) == 1
2990 && (GET_MODE_BITSIZE (mode) <= 32
a3170dc6 2991 || ((TARGET_HARD_FLOAT && TARGET_FPRS) && mode == DFmode)))
9ebbca7d
GK
2992 {
2993 rtx reg = gen_reg_rtx (Pmode);
8a1977f3
GK
2994 emit_insn (gen_elf_high (reg, x));
2995 return gen_rtx_LO_SUM (Pmode, reg, x);
9ebbca7d 2996 }
ee890fe2
SS
2997 else if (TARGET_MACHO && TARGET_32BIT && TARGET_NO_TOC
2998 && ! flag_pic
ab82a49f
AP
2999#if TARGET_MACHO
3000 && ! MACHO_DYNAMIC_NO_PIC_P
3001#endif
ee890fe2 3002 && GET_CODE (x) != CONST_INT
f676971a 3003 && GET_CODE (x) != CONST_DOUBLE
ee890fe2 3004 && CONSTANT_P (x)
f82f556d 3005 && ((TARGET_HARD_FLOAT && TARGET_FPRS) || mode != DFmode)
f676971a 3006 && mode != DImode
ee890fe2
SS
3007 && mode != TImode)
3008 {
3009 rtx reg = gen_reg_rtx (Pmode);
8a1977f3
GK
3010 emit_insn (gen_macho_high (reg, x));
3011 return gen_rtx_LO_SUM (Pmode, reg, x);
ee890fe2 3012 }
f676971a 3013 else if (TARGET_TOC
4d588c14 3014 && constant_pool_expr_p (x)
a9098fd0 3015 && ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (get_pool_constant (x), Pmode))
9ebbca7d
GK
3016 {
3017 return create_TOC_reference (x);
3018 }
3019 else
3020 return NULL_RTX;
3021}
258bfae2 3022
fdbe66f2 3023/* This is called from dwarf2out.c via TARGET_ASM_OUTPUT_DWARF_DTPREL.
c973d557
JJ
3024 We need to emit DTP-relative relocations. */
3025
fdbe66f2 3026static void
c973d557
JJ
3027rs6000_output_dwarf_dtprel (FILE *file, int size, rtx x)
3028{
3029 switch (size)
3030 {
3031 case 4:
3032 fputs ("\t.long\t", file);
3033 break;
3034 case 8:
3035 fputs (DOUBLE_INT_ASM_OP, file);
3036 break;
3037 default:
37409796 3038 gcc_unreachable ();
c973d557
JJ
3039 }
3040 output_addr_const (file, x);
3041 fputs ("@dtprel+0x8000", file);
3042}
3043
c4501e62
JJ
3044/* Construct the SYMBOL_REF for the tls_get_addr function. */
3045
3046static GTY(()) rtx rs6000_tls_symbol;
3047static rtx
863d938c 3048rs6000_tls_get_addr (void)
c4501e62
JJ
3049{
3050 if (!rs6000_tls_symbol)
3051 rs6000_tls_symbol = init_one_libfunc ("__tls_get_addr");
3052
3053 return rs6000_tls_symbol;
3054}
3055
3056/* Construct the SYMBOL_REF for TLS GOT references. */
3057
3058static GTY(()) rtx rs6000_got_symbol;
3059static rtx
863d938c 3060rs6000_got_sym (void)
c4501e62
JJ
3061{
3062 if (!rs6000_got_symbol)
3063 {
3064 rs6000_got_symbol = gen_rtx_SYMBOL_REF (Pmode, "_GLOBAL_OFFSET_TABLE_");
3065 SYMBOL_REF_FLAGS (rs6000_got_symbol) |= SYMBOL_FLAG_LOCAL;
3066 SYMBOL_REF_FLAGS (rs6000_got_symbol) |= SYMBOL_FLAG_EXTERNAL;
f676971a 3067 }
c4501e62
JJ
3068
3069 return rs6000_got_symbol;
3070}
3071
3072/* ADDR contains a thread-local SYMBOL_REF. Generate code to compute
3073 this (thread-local) address. */
3074
3075static rtx
a2369ed3 3076rs6000_legitimize_tls_address (rtx addr, enum tls_model model)
c4501e62
JJ
3077{
3078 rtx dest, insn;
3079
3080 dest = gen_reg_rtx (Pmode);
3081 if (model == TLS_MODEL_LOCAL_EXEC && rs6000_tls_size == 16)
3082 {
3083 rtx tlsreg;
3084
3085 if (TARGET_64BIT)
3086 {
3087 tlsreg = gen_rtx_REG (Pmode, 13);
3088 insn = gen_tls_tprel_64 (dest, tlsreg, addr);
3089 }
3090 else
3091 {
3092 tlsreg = gen_rtx_REG (Pmode, 2);
3093 insn = gen_tls_tprel_32 (dest, tlsreg, addr);
3094 }
3095 emit_insn (insn);
3096 }
3097 else if (model == TLS_MODEL_LOCAL_EXEC && rs6000_tls_size == 32)
3098 {
3099 rtx tlsreg, tmp;
3100
3101 tmp = gen_reg_rtx (Pmode);
3102 if (TARGET_64BIT)
3103 {
3104 tlsreg = gen_rtx_REG (Pmode, 13);
3105 insn = gen_tls_tprel_ha_64 (tmp, tlsreg, addr);
3106 }
3107 else
3108 {
3109 tlsreg = gen_rtx_REG (Pmode, 2);
3110 insn = gen_tls_tprel_ha_32 (tmp, tlsreg, addr);
3111 }
3112 emit_insn (insn);
3113 if (TARGET_64BIT)
3114 insn = gen_tls_tprel_lo_64 (dest, tmp, addr);
3115 else
3116 insn = gen_tls_tprel_lo_32 (dest, tmp, addr);
3117 emit_insn (insn);
3118 }
3119 else
3120 {
3121 rtx r3, got, tga, tmp1, tmp2, eqv;
3122
4fed8f8f
AM
3123 /* We currently use relocations like @got@tlsgd for tls, which
3124 means the linker will handle allocation of tls entries, placing
3125 them in the .got section. So use a pointer to the .got section,
3126 not one to secondary TOC sections used by 64-bit -mminimal-toc,
3127 or to secondary GOT sections used by 32-bit -fPIC. */
c4501e62 3128 if (TARGET_64BIT)
972f427b 3129 got = gen_rtx_REG (Pmode, 2);
c4501e62
JJ
3130 else
3131 {
3132 if (flag_pic == 1)
3133 got = gen_rtx_REG (Pmode, RS6000_PIC_OFFSET_TABLE_REGNUM);
3134 else
3135 {
3136 rtx gsym = rs6000_got_sym ();
3137 got = gen_reg_rtx (Pmode);
3138 if (flag_pic == 0)
3139 rs6000_emit_move (got, gsym, Pmode);
3140 else
3141 {
ccbca5e4 3142 rtx tempLR, tmp3, mem;
c4501e62
JJ
3143 rtx first, last;
3144
c4501e62
JJ
3145 tempLR = gen_reg_rtx (Pmode);
3146 tmp1 = gen_reg_rtx (Pmode);
3147 tmp2 = gen_reg_rtx (Pmode);
3148 tmp3 = gen_reg_rtx (Pmode);
542a8afa 3149 mem = gen_const_mem (Pmode, tmp1);
c4501e62 3150
ccbca5e4 3151 first = emit_insn (gen_load_toc_v4_PIC_1b (tempLR, gsym));
c4501e62
JJ
3152 emit_move_insn (tmp1, tempLR);
3153 emit_move_insn (tmp2, mem);
3154 emit_insn (gen_addsi3 (tmp3, tmp1, tmp2));
3155 last = emit_move_insn (got, tmp3);
3156 REG_NOTES (last) = gen_rtx_EXPR_LIST (REG_EQUAL, gsym,
3157 REG_NOTES (last));
3158 REG_NOTES (first) = gen_rtx_INSN_LIST (REG_LIBCALL, last,
3159 REG_NOTES (first));
3160 REG_NOTES (last) = gen_rtx_INSN_LIST (REG_RETVAL, first,
3161 REG_NOTES (last));
3162 }
3163 }
3164 }
3165
3166 if (model == TLS_MODEL_GLOBAL_DYNAMIC)
3167 {
3168 r3 = gen_rtx_REG (Pmode, 3);
3169 if (TARGET_64BIT)
3170 insn = gen_tls_gd_64 (r3, got, addr);
3171 else
3172 insn = gen_tls_gd_32 (r3, got, addr);
3173 start_sequence ();
3174 emit_insn (insn);
3175 tga = gen_rtx_MEM (Pmode, rs6000_tls_get_addr ());
3176 insn = gen_call_value (r3, tga, const0_rtx, const0_rtx);
3177 insn = emit_call_insn (insn);
3178 CONST_OR_PURE_CALL_P (insn) = 1;
3179 use_reg (&CALL_INSN_FUNCTION_USAGE (insn), r3);
3180 insn = get_insns ();
3181 end_sequence ();
3182 emit_libcall_block (insn, dest, r3, addr);
3183 }
3184 else if (model == TLS_MODEL_LOCAL_DYNAMIC)
3185 {
3186 r3 = gen_rtx_REG (Pmode, 3);
3187 if (TARGET_64BIT)
3188 insn = gen_tls_ld_64 (r3, got);
3189 else
3190 insn = gen_tls_ld_32 (r3, got);
3191 start_sequence ();
3192 emit_insn (insn);
3193 tga = gen_rtx_MEM (Pmode, rs6000_tls_get_addr ());
3194 insn = gen_call_value (r3, tga, const0_rtx, const0_rtx);
3195 insn = emit_call_insn (insn);
3196 CONST_OR_PURE_CALL_P (insn) = 1;
3197 use_reg (&CALL_INSN_FUNCTION_USAGE (insn), r3);
3198 insn = get_insns ();
3199 end_sequence ();
3200 tmp1 = gen_reg_rtx (Pmode);
3201 eqv = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, const0_rtx),
3202 UNSPEC_TLSLD);
3203 emit_libcall_block (insn, tmp1, r3, eqv);
3204 if (rs6000_tls_size == 16)
3205 {
3206 if (TARGET_64BIT)
3207 insn = gen_tls_dtprel_64 (dest, tmp1, addr);
3208 else
3209 insn = gen_tls_dtprel_32 (dest, tmp1, addr);
3210 }
3211 else if (rs6000_tls_size == 32)
3212 {
3213 tmp2 = gen_reg_rtx (Pmode);
3214 if (TARGET_64BIT)
3215 insn = gen_tls_dtprel_ha_64 (tmp2, tmp1, addr);
3216 else
3217 insn = gen_tls_dtprel_ha_32 (tmp2, tmp1, addr);
3218 emit_insn (insn);
3219 if (TARGET_64BIT)
3220 insn = gen_tls_dtprel_lo_64 (dest, tmp2, addr);
3221 else
3222 insn = gen_tls_dtprel_lo_32 (dest, tmp2, addr);
3223 }
3224 else
3225 {
3226 tmp2 = gen_reg_rtx (Pmode);
3227 if (TARGET_64BIT)
3228 insn = gen_tls_got_dtprel_64 (tmp2, got, addr);
3229 else
3230 insn = gen_tls_got_dtprel_32 (tmp2, got, addr);
3231 emit_insn (insn);
3232 insn = gen_rtx_SET (Pmode, dest,
3233 gen_rtx_PLUS (Pmode, tmp2, tmp1));
3234 }
3235 emit_insn (insn);
3236 }
3237 else
3238 {
3239 /* IE, or 64 bit offset LE. */
3240 tmp2 = gen_reg_rtx (Pmode);
3241 if (TARGET_64BIT)
3242 insn = gen_tls_got_tprel_64 (tmp2, got, addr);
3243 else
3244 insn = gen_tls_got_tprel_32 (tmp2, got, addr);
3245 emit_insn (insn);
3246 if (TARGET_64BIT)
3247 insn = gen_tls_tls_64 (dest, tmp2, addr);
3248 else
3249 insn = gen_tls_tls_32 (dest, tmp2, addr);
3250 emit_insn (insn);
3251 }
3252 }
3253
3254 return dest;
3255}
3256
c4501e62
JJ
3257/* Return 1 if X contains a thread-local symbol. */
3258
3259bool
a2369ed3 3260rs6000_tls_referenced_p (rtx x)
c4501e62 3261{
cd413cab
AP
3262 if (! TARGET_HAVE_TLS)
3263 return false;
3264
c4501e62
JJ
3265 return for_each_rtx (&x, &rs6000_tls_symbol_ref_1, 0);
3266}
3267
3268/* Return 1 if *X is a thread-local symbol. This is the same as
3269 rs6000_tls_symbol_ref except for the type of the unused argument. */
3270
9390387d 3271static int
a2369ed3 3272rs6000_tls_symbol_ref_1 (rtx *x, void *data ATTRIBUTE_UNUSED)
c4501e62
JJ
3273{
3274 return RS6000_SYMBOL_REF_TLS_P (*x);
3275}
3276
24ea750e
DJ
3277/* The convention appears to be to define this wherever it is used.
3278 With legitimize_reload_address now defined here, REG_MODE_OK_FOR_BASE_P
3279 is now used here. */
3280#ifndef REG_MODE_OK_FOR_BASE_P
3281#define REG_MODE_OK_FOR_BASE_P(REGNO, MODE) REG_OK_FOR_BASE_P (REGNO)
3282#endif
3283
3284/* Our implementation of LEGITIMIZE_RELOAD_ADDRESS. Returns a value to
3285 replace the input X, or the original X if no replacement is called for.
3286 The output parameter *WIN is 1 if the calling macro should goto WIN,
3287 0 if it should not.
3288
3289 For RS/6000, we wish to handle large displacements off a base
3290 register by splitting the addend across an addiu/addis and the mem insn.
3291 This cuts number of extra insns needed from 3 to 1.
3292
3293 On Darwin, we use this to generate code for floating point constants.
3294 A movsf_low is generated so we wind up with 2 instructions rather than 3.
3295 The Darwin code is inside #if TARGET_MACHO because only then is
3296 machopic_function_base_name() defined. */
3297rtx
f676971a 3298rs6000_legitimize_reload_address (rtx x, enum machine_mode mode,
c4ad648e
AM
3299 int opnum, int type,
3300 int ind_levels ATTRIBUTE_UNUSED, int *win)
24ea750e 3301{
f676971a 3302 /* We must recognize output that we have already generated ourselves. */
24ea750e
DJ
3303 if (GET_CODE (x) == PLUS
3304 && GET_CODE (XEXP (x, 0)) == PLUS
3305 && GET_CODE (XEXP (XEXP (x, 0), 0)) == REG
3306 && GET_CODE (XEXP (XEXP (x, 0), 1)) == CONST_INT
3307 && GET_CODE (XEXP (x, 1)) == CONST_INT)
3308 {
3309 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
c4ad648e
AM
3310 BASE_REG_CLASS, GET_MODE (x), VOIDmode, 0, 0,
3311 opnum, (enum reload_type)type);
24ea750e
DJ
3312 *win = 1;
3313 return x;
3314 }
3deb2758 3315
24ea750e
DJ
3316#if TARGET_MACHO
3317 if (DEFAULT_ABI == ABI_DARWIN && flag_pic
3318 && GET_CODE (x) == LO_SUM
3319 && GET_CODE (XEXP (x, 0)) == PLUS
3320 && XEXP (XEXP (x, 0), 0) == pic_offset_table_rtx
3321 && GET_CODE (XEXP (XEXP (x, 0), 1)) == HIGH
3322 && GET_CODE (XEXP (XEXP (XEXP (x, 0), 1), 0)) == CONST
3323 && XEXP (XEXP (XEXP (x, 0), 1), 0) == XEXP (x, 1)
3324 && GET_CODE (XEXP (XEXP (x, 1), 0)) == MINUS
3325 && GET_CODE (XEXP (XEXP (XEXP (x, 1), 0), 0)) == SYMBOL_REF
3326 && GET_CODE (XEXP (XEXP (XEXP (x, 1), 0), 1)) == SYMBOL_REF)
3327 {
3328 /* Result of previous invocation of this function on Darwin
6f317ef3 3329 floating point constant. */
24ea750e 3330 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
c4ad648e
AM
3331 BASE_REG_CLASS, Pmode, VOIDmode, 0, 0,
3332 opnum, (enum reload_type)type);
24ea750e
DJ
3333 *win = 1;
3334 return x;
3335 }
3336#endif
4937d02d
DE
3337
3338 /* Force ld/std non-word aligned offset into base register by wrapping
3339 in offset 0. */
3340 if (GET_CODE (x) == PLUS
3341 && GET_CODE (XEXP (x, 0)) == REG
3342 && REGNO (XEXP (x, 0)) < 32
3343 && REG_MODE_OK_FOR_BASE_P (XEXP (x, 0), mode)
3344 && GET_CODE (XEXP (x, 1)) == CONST_INT
3345 && (INTVAL (XEXP (x, 1)) & 3) != 0
78796ad5 3346 && !ALTIVEC_VECTOR_MODE (mode)
4937d02d
DE
3347 && GET_MODE_SIZE (mode) >= UNITS_PER_WORD
3348 && TARGET_POWERPC64)
3349 {
3350 x = gen_rtx_PLUS (GET_MODE (x), x, GEN_INT (0));
3351 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
3352 BASE_REG_CLASS, GET_MODE (x), VOIDmode, 0, 0,
3353 opnum, (enum reload_type) type);
3354 *win = 1;
3355 return x;
3356 }
3357
24ea750e
DJ
3358 if (GET_CODE (x) == PLUS
3359 && GET_CODE (XEXP (x, 0)) == REG
3360 && REGNO (XEXP (x, 0)) < FIRST_PSEUDO_REGISTER
3361 && REG_MODE_OK_FOR_BASE_P (XEXP (x, 0), mode)
78c875e8 3362 && GET_CODE (XEXP (x, 1)) == CONST_INT
93638d7a 3363 && !SPE_VECTOR_MODE (mode)
54b695e7
AH
3364 && !(TARGET_E500_DOUBLE && (mode == DFmode
3365 || mode == DImode))
78c875e8 3366 && !ALTIVEC_VECTOR_MODE (mode))
24ea750e
DJ
3367 {
3368 HOST_WIDE_INT val = INTVAL (XEXP (x, 1));
3369 HOST_WIDE_INT low = ((val & 0xffff) ^ 0x8000) - 0x8000;
3370 HOST_WIDE_INT high
c4ad648e 3371 = (((val - low) & 0xffffffff) ^ 0x80000000) - 0x80000000;
24ea750e
DJ
3372
3373 /* Check for 32-bit overflow. */
3374 if (high + low != val)
c4ad648e 3375 {
24ea750e
DJ
3376 *win = 0;
3377 return x;
3378 }
3379
3380 /* Reload the high part into a base reg; leave the low part
c4ad648e 3381 in the mem directly. */
24ea750e
DJ
3382
3383 x = gen_rtx_PLUS (GET_MODE (x),
c4ad648e
AM
3384 gen_rtx_PLUS (GET_MODE (x), XEXP (x, 0),
3385 GEN_INT (high)),
3386 GEN_INT (low));
24ea750e
DJ
3387
3388 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
c4ad648e
AM
3389 BASE_REG_CLASS, GET_MODE (x), VOIDmode, 0, 0,
3390 opnum, (enum reload_type)type);
24ea750e
DJ
3391 *win = 1;
3392 return x;
3393 }
4937d02d 3394
24ea750e 3395 if (GET_CODE (x) == SYMBOL_REF
69ef87e2 3396 && !ALTIVEC_VECTOR_MODE (mode)
8308679f
DE
3397#if TARGET_MACHO
3398 && DEFAULT_ABI == ABI_DARWIN
a29077da 3399 && (flag_pic || MACHO_DYNAMIC_NO_PIC_P)
8308679f
DE
3400#else
3401 && DEFAULT_ABI == ABI_V4
3402 && !flag_pic
3403#endif
0d8c1c97 3404 /* Don't do this for TFmode, since the result isn't offsettable.
7b5d92b2
AM
3405 The same goes for DImode without 64-bit gprs and DFmode
3406 without fprs. */
0d8c1c97 3407 && mode != TFmode
7b5d92b2
AM
3408 && (mode != DImode || TARGET_POWERPC64)
3409 && (mode != DFmode || TARGET_POWERPC64
3410 || (TARGET_FPRS && TARGET_HARD_FLOAT)))
24ea750e 3411 {
8308679f 3412#if TARGET_MACHO
a29077da
GK
3413 if (flag_pic)
3414 {
3415 rtx offset = gen_rtx_CONST (Pmode,
3416 gen_rtx_MINUS (Pmode, x,
11abc112 3417 machopic_function_base_sym ()));
a29077da
GK
3418 x = gen_rtx_LO_SUM (GET_MODE (x),
3419 gen_rtx_PLUS (Pmode, pic_offset_table_rtx,
3420 gen_rtx_HIGH (Pmode, offset)), offset);
3421 }
3422 else
8308679f 3423#endif
a29077da 3424 x = gen_rtx_LO_SUM (GET_MODE (x),
c4ad648e 3425 gen_rtx_HIGH (Pmode, x), x);
a29077da 3426
24ea750e 3427 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
a29077da
GK
3428 BASE_REG_CLASS, Pmode, VOIDmode, 0, 0,
3429 opnum, (enum reload_type)type);
24ea750e
DJ
3430 *win = 1;
3431 return x;
3432 }
4937d02d 3433
dec1f3aa
DE
3434 /* Reload an offset address wrapped by an AND that represents the
3435 masking of the lower bits. Strip the outer AND and let reload
3436 convert the offset address into an indirect address. */
3437 if (TARGET_ALTIVEC
3438 && ALTIVEC_VECTOR_MODE (mode)
3439 && GET_CODE (x) == AND
3440 && GET_CODE (XEXP (x, 0)) == PLUS
3441 && GET_CODE (XEXP (XEXP (x, 0), 0)) == REG
3442 && GET_CODE (XEXP (XEXP (x, 0), 1)) == CONST_INT
3443 && GET_CODE (XEXP (x, 1)) == CONST_INT
3444 && INTVAL (XEXP (x, 1)) == -16)
3445 {
3446 x = XEXP (x, 0);
3447 *win = 1;
3448 return x;
3449 }
3450
24ea750e 3451 if (TARGET_TOC
4d588c14 3452 && constant_pool_expr_p (x)
c1f11548 3453 && ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (get_pool_constant (x), mode))
24ea750e
DJ
3454 {
3455 (x) = create_TOC_reference (x);
3456 *win = 1;
3457 return x;
3458 }
3459 *win = 0;
3460 return x;
f676971a 3461}
24ea750e 3462
258bfae2
FS
3463/* GO_IF_LEGITIMATE_ADDRESS recognizes an RTL expression
3464 that is a valid memory address for an instruction.
3465 The MODE argument is the machine mode for the MEM expression
3466 that wants to use this address.
3467
3468 On the RS/6000, there are four valid address: a SYMBOL_REF that
3469 refers to a constant pool entry of an address (or the sum of it
3470 plus a constant), a short (16-bit signed) constant plus a register,
3471 the sum of two registers, or a register indirect, possibly with an
5bdc5878 3472 auto-increment. For DFmode and DImode with a constant plus register,
258bfae2
FS
3473 we must ensure that both words are addressable or PowerPC64 with offset
3474 word aligned.
3475
3476 For modes spanning multiple registers (DFmode in 32-bit GPRs,
76d2b81d 3477 32-bit DImode, TImode, TFmode), indexed addressing cannot be used because
258bfae2
FS
3478 adjacent memory cells are accessed by adding word-sized offsets
3479 during assembly output. */
3480int
a2369ed3 3481rs6000_legitimate_address (enum machine_mode mode, rtx x, int reg_ok_strict)
258bfae2 3482{
850e8d3d
DN
3483 /* If this is an unaligned stvx/ldvx type address, discard the outer AND. */
3484 if (TARGET_ALTIVEC
3485 && ALTIVEC_VECTOR_MODE (mode)
3486 && GET_CODE (x) == AND
3487 && GET_CODE (XEXP (x, 1)) == CONST_INT
3488 && INTVAL (XEXP (x, 1)) == -16)
3489 x = XEXP (x, 0);
3490
c4501e62
JJ
3491 if (RS6000_SYMBOL_REF_TLS_P (x))
3492 return 0;
4d588c14 3493 if (legitimate_indirect_address_p (x, reg_ok_strict))
258bfae2
FS
3494 return 1;
3495 if ((GET_CODE (x) == PRE_INC || GET_CODE (x) == PRE_DEC)
0d6d6892 3496 && !ALTIVEC_VECTOR_MODE (mode)
a3170dc6 3497 && !SPE_VECTOR_MODE (mode)
54b695e7
AH
3498 /* Restrict addressing for DI because of our SUBREG hackery. */
3499 && !(TARGET_E500_DOUBLE && (mode == DFmode || mode == DImode))
258bfae2 3500 && TARGET_UPDATE
4d588c14 3501 && legitimate_indirect_address_p (XEXP (x, 0), reg_ok_strict))
258bfae2 3502 return 1;
d04b6e6e 3503 if (legitimate_small_data_p (mode, x))
258bfae2 3504 return 1;
4d588c14 3505 if (legitimate_constant_pool_address_p (x))
258bfae2
FS
3506 return 1;
3507 /* If not REG_OK_STRICT (before reload) let pass any stack offset. */
3508 if (! reg_ok_strict
3509 && GET_CODE (x) == PLUS
3510 && GET_CODE (XEXP (x, 0)) == REG
708d2456 3511 && (XEXP (x, 0) == virtual_stack_vars_rtx
c4ad648e 3512 || XEXP (x, 0) == arg_pointer_rtx)
258bfae2
FS
3513 && GET_CODE (XEXP (x, 1)) == CONST_INT)
3514 return 1;
76d2b81d 3515 if (rs6000_legitimate_offset_address_p (mode, x, reg_ok_strict))
258bfae2
FS
3516 return 1;
3517 if (mode != TImode
76d2b81d 3518 && mode != TFmode
a3170dc6
AH
3519 && ((TARGET_HARD_FLOAT && TARGET_FPRS)
3520 || TARGET_POWERPC64
4d4cbc0e 3521 || ((mode != DFmode || TARGET_E500_DOUBLE) && mode != TFmode))
258bfae2 3522 && (TARGET_POWERPC64 || mode != DImode)
4d588c14 3523 && legitimate_indexed_address_p (x, reg_ok_strict))
258bfae2 3524 return 1;
4d588c14 3525 if (legitimate_lo_sum_address_p (mode, x, reg_ok_strict))
258bfae2
FS
3526 return 1;
3527 return 0;
3528}
4d588c14
RH
3529
3530/* Go to LABEL if ADDR (a legitimate address expression)
3531 has an effect that depends on the machine mode it is used for.
3532
3533 On the RS/6000 this is true of all integral offsets (since AltiVec
3534 modes don't allow them) or is a pre-increment or decrement.
3535
3536 ??? Except that due to conceptual problems in offsettable_address_p
3537 we can't really report the problems of integral offsets. So leave
f676971a 3538 this assuming that the adjustable offset must be valid for the
4d588c14
RH
3539 sub-words of a TFmode operand, which is what we had before. */
3540
3541bool
a2369ed3 3542rs6000_mode_dependent_address (rtx addr)
4d588c14
RH
3543{
3544 switch (GET_CODE (addr))
3545 {
3546 case PLUS:
3547 if (GET_CODE (XEXP (addr, 1)) == CONST_INT)
3548 {
3549 unsigned HOST_WIDE_INT val = INTVAL (XEXP (addr, 1));
3550 return val + 12 + 0x8000 >= 0x10000;
3551 }
3552 break;
3553
3554 case LO_SUM:
3555 return true;
3556
3557 case PRE_INC:
3558 case PRE_DEC:
3559 return TARGET_UPDATE;
3560
3561 default:
3562 break;
3563 }
3564
3565 return false;
3566}
d8ecbcdb 3567
d04b6e6e
EB
3568/* More elaborate version of recog's offsettable_memref_p predicate
3569 that works around the ??? note of rs6000_mode_dependent_address.
3570 In particular it accepts
3571
3572 (mem:DI (plus:SI (reg/f:SI 31 31) (const_int 32760 [0x7ff8])))
3573
3574 in 32-bit mode, that the recog predicate rejects. */
3575
3576bool
3577rs6000_offsettable_memref_p (rtx op)
3578{
3579 if (!MEM_P (op))
3580 return false;
3581
3582 /* First mimic offsettable_memref_p. */
3583 if (offsettable_address_p (1, GET_MODE (op), XEXP (op, 0)))
3584 return true;
3585
3586 /* offsettable_address_p invokes rs6000_mode_dependent_address, but
3587 the latter predicate knows nothing about the mode of the memory
3588 reference and, therefore, assumes that it is the largest supported
3589 mode (TFmode). As a consequence, legitimate offsettable memory
3590 references are rejected. rs6000_legitimate_offset_address_p contains
3591 the correct logic for the PLUS case of rs6000_mode_dependent_address. */
3592 return rs6000_legitimate_offset_address_p (GET_MODE (op), XEXP (op, 0), 1);
3593}
3594
d8ecbcdb
AH
3595/* Return number of consecutive hard regs needed starting at reg REGNO
3596 to hold something of mode MODE.
3597 This is ordinarily the length in words of a value of mode MODE
3598 but can be less for certain modes in special long registers.
3599
3600 For the SPE, GPRs are 64 bits but only 32 bits are visible in
3601 scalar instructions. The upper 32 bits are only available to the
3602 SIMD instructions.
3603
3604 POWER and PowerPC GPRs hold 32 bits worth;
3605 PowerPC64 GPRs and FPRs point register holds 64 bits worth. */
3606
3607int
3608rs6000_hard_regno_nregs (int regno, enum machine_mode mode)
3609{
3610 if (FP_REGNO_P (regno))
3611 return (GET_MODE_SIZE (mode) + UNITS_PER_FP_WORD - 1) / UNITS_PER_FP_WORD;
3612
4d4cbc0e
AH
3613 if (TARGET_E500_DOUBLE && mode == DFmode)
3614 return 1;
3615
d8ecbcdb
AH
3616 if (SPE_SIMD_REGNO_P (regno) && TARGET_SPE && SPE_VECTOR_MODE (mode))
3617 return (GET_MODE_SIZE (mode) + UNITS_PER_SPE_WORD - 1) / UNITS_PER_SPE_WORD;
3618
3619 if (ALTIVEC_REGNO_P (regno))
3620 return
3621 (GET_MODE_SIZE (mode) + UNITS_PER_ALTIVEC_WORD - 1) / UNITS_PER_ALTIVEC_WORD;
3622
3623 return (GET_MODE_SIZE (mode) + UNITS_PER_WORD - 1) / UNITS_PER_WORD;
3624}
2aa4498c
AH
3625
3626/* Change register usage conditional on target flags. */
3627void
3628rs6000_conditional_register_usage (void)
3629{
3630 int i;
3631
3632 /* Set MQ register fixed (already call_used) if not POWER
3633 architecture (RIOS1, RIOS2, RSC, and PPC601) so that it will not
3634 be allocated. */
3635 if (! TARGET_POWER)
3636 fixed_regs[64] = 1;
3637
7c9ac5c0 3638 /* 64-bit AIX and Linux reserve GPR13 for thread-private data. */
2aa4498c
AH
3639 if (TARGET_64BIT)
3640 fixed_regs[13] = call_used_regs[13]
3641 = call_really_used_regs[13] = 1;
3642
3643 /* Conditionally disable FPRs. */
3644 if (TARGET_SOFT_FLOAT || !TARGET_FPRS)
3645 for (i = 32; i < 64; i++)
3646 fixed_regs[i] = call_used_regs[i]
c4ad648e 3647 = call_really_used_regs[i] = 1;
2aa4498c 3648
7c9ac5c0
PH
3649 /* The TOC register is not killed across calls in a way that is
3650 visible to the compiler. */
3651 if (DEFAULT_ABI == ABI_AIX)
3652 call_really_used_regs[2] = 0;
3653
2aa4498c
AH
3654 if (DEFAULT_ABI == ABI_V4
3655 && PIC_OFFSET_TABLE_REGNUM != INVALID_REGNUM
3656 && flag_pic == 2)
3657 fixed_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] = 1;
3658
3659 if (DEFAULT_ABI == ABI_V4
3660 && PIC_OFFSET_TABLE_REGNUM != INVALID_REGNUM
3661 && flag_pic == 1)
3662 fixed_regs[RS6000_PIC_OFFSET_TABLE_REGNUM]
3663 = call_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM]
3664 = call_really_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] = 1;
3665
3666 if (DEFAULT_ABI == ABI_DARWIN
3667 && PIC_OFFSET_TABLE_REGNUM != INVALID_REGNUM)
6d0a8091 3668 fixed_regs[RS6000_PIC_OFFSET_TABLE_REGNUM]
2aa4498c
AH
3669 = call_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM]
3670 = call_really_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] = 1;
3671
b4db40bf
JJ
3672 if (TARGET_TOC && TARGET_MINIMAL_TOC)
3673 fixed_regs[RS6000_PIC_OFFSET_TABLE_REGNUM]
3674 = call_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] = 1;
3675
2aa4498c
AH
3676 if (TARGET_ALTIVEC)
3677 global_regs[VSCR_REGNO] = 1;
3678
3679 if (TARGET_SPE)
3680 {
3681 global_regs[SPEFSCR_REGNO] = 1;
3682 fixed_regs[FIXED_SCRATCH]
c4ad648e 3683 = call_used_regs[FIXED_SCRATCH]
2aa4498c
AH
3684 = call_really_used_regs[FIXED_SCRATCH] = 1;
3685 }
3686
3687 if (! TARGET_ALTIVEC)
3688 {
3689 for (i = FIRST_ALTIVEC_REGNO; i <= LAST_ALTIVEC_REGNO; ++i)
3690 fixed_regs[i] = call_used_regs[i] = call_really_used_regs[i] = 1;
3691 call_really_used_regs[VRSAVE_REGNO] = 1;
3692 }
3693
3694 if (TARGET_ALTIVEC_ABI)
3695 for (i = FIRST_ALTIVEC_REGNO; i < FIRST_ALTIVEC_REGNO + 20; ++i)
3696 call_used_regs[i] = call_really_used_regs[i] = 1;
3697}
fb4d4348 3698\f
a4f6c312
SS
3699/* Try to output insns to set TARGET equal to the constant C if it can
3700 be done in less than N insns. Do all computations in MODE.
3701 Returns the place where the output has been placed if it can be
3702 done and the insns have been emitted. If it would take more than N
3703 insns, zero is returned and no insns and emitted. */
2bfcf297
DB
3704
3705rtx
f676971a 3706rs6000_emit_set_const (rtx dest, enum machine_mode mode,
a2369ed3 3707 rtx source, int n ATTRIBUTE_UNUSED)
2bfcf297 3708{
af8cb5c5 3709 rtx result, insn, set;
2bfcf297
DB
3710 HOST_WIDE_INT c0, c1;
3711
37409796 3712 switch (mode)
2bfcf297 3713 {
37409796
NS
3714 case QImode:
3715 case HImode:
2bfcf297 3716 if (dest == NULL)
c4ad648e 3717 dest = gen_reg_rtx (mode);
2bfcf297
DB
3718 emit_insn (gen_rtx_SET (VOIDmode, dest, source));
3719 return dest;
bb8df8a6 3720
37409796 3721 case SImode:
af8cb5c5 3722 result = no_new_pseudos ? dest : gen_reg_rtx (SImode);
bb8df8a6 3723
af8cb5c5
DE
3724 emit_insn (gen_rtx_SET (VOIDmode, result,
3725 GEN_INT (INTVAL (source)
3726 & (~ (HOST_WIDE_INT) 0xffff))));
3727 emit_insn (gen_rtx_SET (VOIDmode, dest,
3728 gen_rtx_IOR (SImode, result,
3729 GEN_INT (INTVAL (source) & 0xffff))));
3730 result = dest;
37409796
NS
3731 break;
3732
3733 case DImode:
3734 switch (GET_CODE (source))
af8cb5c5 3735 {
37409796 3736 case CONST_INT:
af8cb5c5
DE
3737 c0 = INTVAL (source);
3738 c1 = -(c0 < 0);
37409796 3739 break;
bb8df8a6 3740
37409796 3741 case CONST_DOUBLE:
2bfcf297 3742#if HOST_BITS_PER_WIDE_INT >= 64
af8cb5c5
DE
3743 c0 = CONST_DOUBLE_LOW (source);
3744 c1 = -(c0 < 0);
2bfcf297 3745#else
af8cb5c5
DE
3746 c0 = CONST_DOUBLE_LOW (source);
3747 c1 = CONST_DOUBLE_HIGH (source);
2bfcf297 3748#endif
37409796
NS
3749 break;
3750
3751 default:
3752 gcc_unreachable ();
af8cb5c5 3753 }
af8cb5c5
DE
3754
3755 result = rs6000_emit_set_long_const (dest, c0, c1);
37409796
NS
3756 break;
3757
3758 default:
3759 gcc_unreachable ();
2bfcf297 3760 }
2bfcf297 3761
af8cb5c5
DE
3762 insn = get_last_insn ();
3763 set = single_set (insn);
3764 if (! CONSTANT_P (SET_SRC (set)))
3765 set_unique_reg_note (insn, REG_EQUAL, source);
3766
3767 return result;
2bfcf297
DB
3768}
3769
3770/* Having failed to find a 3 insn sequence in rs6000_emit_set_const,
3771 fall back to a straight forward decomposition. We do this to avoid
3772 exponential run times encountered when looking for longer sequences
3773 with rs6000_emit_set_const. */
3774static rtx
a2369ed3 3775rs6000_emit_set_long_const (rtx dest, HOST_WIDE_INT c1, HOST_WIDE_INT c2)
2bfcf297
DB
3776{
3777 if (!TARGET_POWERPC64)
3778 {
3779 rtx operand1, operand2;
3780
3781 operand1 = operand_subword_force (dest, WORDS_BIG_ENDIAN == 0,
3782 DImode);
3783 operand2 = operand_subword_force (dest, WORDS_BIG_ENDIAN != 0,
3784 DImode);
3785 emit_move_insn (operand1, GEN_INT (c1));
3786 emit_move_insn (operand2, GEN_INT (c2));
3787 }
3788 else
3789 {
bc06712d 3790 HOST_WIDE_INT ud1, ud2, ud3, ud4;
252b88f7 3791
bc06712d 3792 ud1 = c1 & 0xffff;
f921c9c9 3793 ud2 = (c1 & 0xffff0000) >> 16;
2bfcf297 3794#if HOST_BITS_PER_WIDE_INT >= 64
bc06712d 3795 c2 = c1 >> 32;
2bfcf297 3796#endif
bc06712d 3797 ud3 = c2 & 0xffff;
f921c9c9 3798 ud4 = (c2 & 0xffff0000) >> 16;
2bfcf297 3799
f676971a 3800 if ((ud4 == 0xffff && ud3 == 0xffff && ud2 == 0xffff && (ud1 & 0x8000))
bc06712d 3801 || (ud4 == 0 && ud3 == 0 && ud2 == 0 && ! (ud1 & 0x8000)))
2bfcf297 3802 {
bc06712d 3803 if (ud1 & 0x8000)
b78d48dd 3804 emit_move_insn (dest, GEN_INT (((ud1 ^ 0x8000) - 0x8000)));
bc06712d
TR
3805 else
3806 emit_move_insn (dest, GEN_INT (ud1));
2bfcf297 3807 }
2bfcf297 3808
f676971a 3809 else if ((ud4 == 0xffff && ud3 == 0xffff && (ud2 & 0x8000))
bc06712d 3810 || (ud4 == 0 && ud3 == 0 && ! (ud2 & 0x8000)))
252b88f7 3811 {
bc06712d 3812 if (ud2 & 0x8000)
f676971a 3813 emit_move_insn (dest, GEN_INT (((ud2 << 16) ^ 0x80000000)
bc06712d 3814 - 0x80000000));
252b88f7 3815 else
bc06712d
TR
3816 emit_move_insn (dest, GEN_INT (ud2 << 16));
3817 if (ud1 != 0)
3818 emit_move_insn (dest, gen_rtx_IOR (DImode, dest, GEN_INT (ud1)));
252b88f7 3819 }
f676971a 3820 else if ((ud4 == 0xffff && (ud3 & 0x8000))
bc06712d
TR
3821 || (ud4 == 0 && ! (ud3 & 0x8000)))
3822 {
3823 if (ud3 & 0x8000)
f676971a 3824 emit_move_insn (dest, GEN_INT (((ud3 << 16) ^ 0x80000000)
bc06712d
TR
3825 - 0x80000000));
3826 else
3827 emit_move_insn (dest, GEN_INT (ud3 << 16));
3828
3829 if (ud2 != 0)
3830 emit_move_insn (dest, gen_rtx_IOR (DImode, dest, GEN_INT (ud2)));
3831 emit_move_insn (dest, gen_rtx_ASHIFT (DImode, dest, GEN_INT (16)));
3832 if (ud1 != 0)
3833 emit_move_insn (dest, gen_rtx_IOR (DImode, dest, GEN_INT (ud1)));
3834 }
f676971a 3835 else
bc06712d
TR
3836 {
3837 if (ud4 & 0x8000)
f676971a 3838 emit_move_insn (dest, GEN_INT (((ud4 << 16) ^ 0x80000000)
bc06712d
TR
3839 - 0x80000000));
3840 else
3841 emit_move_insn (dest, GEN_INT (ud4 << 16));
3842
3843 if (ud3 != 0)
3844 emit_move_insn (dest, gen_rtx_IOR (DImode, dest, GEN_INT (ud3)));
2bfcf297 3845
bc06712d
TR
3846 emit_move_insn (dest, gen_rtx_ASHIFT (DImode, dest, GEN_INT (32)));
3847 if (ud2 != 0)
f676971a
EC
3848 emit_move_insn (dest, gen_rtx_IOR (DImode, dest,
3849 GEN_INT (ud2 << 16)));
bc06712d
TR
3850 if (ud1 != 0)
3851 emit_move_insn (dest, gen_rtx_IOR (DImode, dest, GEN_INT (ud1)));
3852 }
3853 }
2bfcf297
DB
3854 return dest;
3855}
3856
76d2b81d
DJ
3857/* Helper for the following. Get rid of [r+r] memory refs
3858 in cases where it won't work (TImode, TFmode). */
3859
3860static void
3861rs6000_eliminate_indexed_memrefs (rtx operands[2])
3862{
3863 if (GET_CODE (operands[0]) == MEM
3864 && GET_CODE (XEXP (operands[0], 0)) != REG
55aa0757 3865 && ! legitimate_constant_pool_address_p (XEXP (operands[0], 0))
76d2b81d
DJ
3866 && ! reload_in_progress)
3867 operands[0]
3868 = replace_equiv_address (operands[0],
3869 copy_addr_to_reg (XEXP (operands[0], 0)));
3870
3871 if (GET_CODE (operands[1]) == MEM
3872 && GET_CODE (XEXP (operands[1], 0)) != REG
55aa0757 3873 && ! legitimate_constant_pool_address_p (XEXP (operands[1], 0))
76d2b81d
DJ
3874 && ! reload_in_progress)
3875 operands[1]
3876 = replace_equiv_address (operands[1],
3877 copy_addr_to_reg (XEXP (operands[1], 0)));
3878}
3879
fb4d4348
GK
3880/* Emit a move from SOURCE to DEST in mode MODE. */
3881void
a2369ed3 3882rs6000_emit_move (rtx dest, rtx source, enum machine_mode mode)
fb4d4348
GK
3883{
3884 rtx operands[2];
3885 operands[0] = dest;
3886 operands[1] = source;
f676971a 3887
fb4d4348
GK
3888 /* Sanity checks. Check that we get CONST_DOUBLE only when we should. */
3889 if (GET_CODE (operands[1]) == CONST_DOUBLE
3890 && ! FLOAT_MODE_P (mode)
3891 && GET_MODE_BITSIZE (mode) <= HOST_BITS_PER_WIDE_INT)
3892 {
3893 /* FIXME. This should never happen. */
3894 /* Since it seems that it does, do the safe thing and convert
3895 to a CONST_INT. */
2496c7bd 3896 operands[1] = gen_int_mode (CONST_DOUBLE_LOW (operands[1]), mode);
fb4d4348 3897 }
37409796
NS
3898 gcc_assert (GET_CODE (operands[1]) != CONST_DOUBLE
3899 || FLOAT_MODE_P (mode)
3900 || ((CONST_DOUBLE_HIGH (operands[1]) != 0
3901 || CONST_DOUBLE_LOW (operands[1]) < 0)
3902 && (CONST_DOUBLE_HIGH (operands[1]) != -1
3903 || CONST_DOUBLE_LOW (operands[1]) >= 0)));
bb8df8a6 3904
c9e8cb32
DD
3905 /* Check if GCC is setting up a block move that will end up using FP
3906 registers as temporaries. We must make sure this is acceptable. */
3907 if (GET_CODE (operands[0]) == MEM
3908 && GET_CODE (operands[1]) == MEM
3909 && mode == DImode
41543739
GK
3910 && (SLOW_UNALIGNED_ACCESS (DImode, MEM_ALIGN (operands[0]))
3911 || SLOW_UNALIGNED_ACCESS (DImode, MEM_ALIGN (operands[1])))
3912 && ! (SLOW_UNALIGNED_ACCESS (SImode, (MEM_ALIGN (operands[0]) > 32
3913 ? 32 : MEM_ALIGN (operands[0])))
3914 || SLOW_UNALIGNED_ACCESS (SImode, (MEM_ALIGN (operands[1]) > 32
f676971a 3915 ? 32
41543739
GK
3916 : MEM_ALIGN (operands[1]))))
3917 && ! MEM_VOLATILE_P (operands [0])
3918 && ! MEM_VOLATILE_P (operands [1]))
c9e8cb32 3919 {
41543739
GK
3920 emit_move_insn (adjust_address (operands[0], SImode, 0),
3921 adjust_address (operands[1], SImode, 0));
3922 emit_move_insn (adjust_address (operands[0], SImode, 4),
3923 adjust_address (operands[1], SImode, 4));
c9e8cb32
DD
3924 return;
3925 }
630d42a0 3926
55aa0757 3927 if (!no_new_pseudos && GET_CODE (operands[0]) == MEM
c9dbf840 3928 && !gpc_reg_operand (operands[1], mode))
f6219a5e 3929 operands[1] = force_reg (mode, operands[1]);
a9098fd0 3930
a3170dc6
AH
3931 if (mode == SFmode && ! TARGET_POWERPC
3932 && TARGET_HARD_FLOAT && TARGET_FPRS
ffc14f31 3933 && GET_CODE (operands[0]) == MEM)
fb4d4348 3934 {
ffc14f31
GK
3935 int regnum;
3936
3937 if (reload_in_progress || reload_completed)
3938 regnum = true_regnum (operands[1]);
3939 else if (GET_CODE (operands[1]) == REG)
3940 regnum = REGNO (operands[1]);
3941 else
3942 regnum = -1;
f676971a 3943
fb4d4348
GK
3944 /* If operands[1] is a register, on POWER it may have
3945 double-precision data in it, so truncate it to single
3946 precision. */
3947 if (FP_REGNO_P (regnum) || regnum >= FIRST_PSEUDO_REGISTER)
3948 {
3949 rtx newreg;
3950 newreg = (no_new_pseudos ? operands[1] : gen_reg_rtx (mode));
3951 emit_insn (gen_aux_truncdfsf2 (newreg, operands[1]));
3952 operands[1] = newreg;
3953 }
3954 }
3955
c4501e62
JJ
3956 /* Recognize the case where operand[1] is a reference to thread-local
3957 data and load its address to a register. */
84f52ebd 3958 if (rs6000_tls_referenced_p (operands[1]))
c4501e62 3959 {
84f52ebd
RH
3960 enum tls_model model;
3961 rtx tmp = operands[1];
3962 rtx addend = NULL;
3963
3964 if (GET_CODE (tmp) == CONST && GET_CODE (XEXP (tmp, 0)) == PLUS)
3965 {
3966 addend = XEXP (XEXP (tmp, 0), 1);
3967 tmp = XEXP (XEXP (tmp, 0), 0);
3968 }
3969
3970 gcc_assert (GET_CODE (tmp) == SYMBOL_REF);
3971 model = SYMBOL_REF_TLS_MODEL (tmp);
3972 gcc_assert (model != 0);
3973
3974 tmp = rs6000_legitimize_tls_address (tmp, model);
3975 if (addend)
3976 {
3977 tmp = gen_rtx_PLUS (mode, tmp, addend);
3978 tmp = force_operand (tmp, operands[0]);
3979 }
3980 operands[1] = tmp;
c4501e62
JJ
3981 }
3982
8f4e6caf
RH
3983 /* Handle the case where reload calls us with an invalid address. */
3984 if (reload_in_progress && mode == Pmode
69ef87e2 3985 && (! general_operand (operands[1], mode)
8f4e6caf
RH
3986 || ! nonimmediate_operand (operands[0], mode)))
3987 goto emit_set;
3988
a9baceb1
GK
3989 /* 128-bit constant floating-point values on Darwin should really be
3990 loaded as two parts. */
602ea4d3 3991 if (!TARGET_IEEEQUAD
a9baceb1
GK
3992 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128
3993 && mode == TFmode && GET_CODE (operands[1]) == CONST_DOUBLE)
3994 {
3995 /* DImode is used, not DFmode, because simplify_gen_subreg doesn't
3996 know how to get a DFmode SUBREG of a TFmode. */
3997 rs6000_emit_move (simplify_gen_subreg (DImode, operands[0], mode, 0),
3998 simplify_gen_subreg (DImode, operands[1], mode, 0),
3999 DImode);
4000 rs6000_emit_move (simplify_gen_subreg (DImode, operands[0], mode,
4001 GET_MODE_SIZE (DImode)),
4002 simplify_gen_subreg (DImode, operands[1], mode,
4003 GET_MODE_SIZE (DImode)),
4004 DImode);
4005 return;
4006 }
4007
fb4d4348
GK
4008 /* FIXME: In the long term, this switch statement should go away
4009 and be replaced by a sequence of tests based on things like
4010 mode == Pmode. */
4011 switch (mode)
4012 {
4013 case HImode:
4014 case QImode:
4015 if (CONSTANT_P (operands[1])
4016 && GET_CODE (operands[1]) != CONST_INT)
a9098fd0 4017 operands[1] = force_const_mem (mode, operands[1]);
fb4d4348
GK
4018 break;
4019
06f4e019 4020 case TFmode:
76d2b81d
DJ
4021 rs6000_eliminate_indexed_memrefs (operands);
4022 /* fall through */
4023
fb4d4348
GK
4024 case DFmode:
4025 case SFmode:
f676971a 4026 if (CONSTANT_P (operands[1])
fb4d4348 4027 && ! easy_fp_constant (operands[1], mode))
a9098fd0 4028 operands[1] = force_const_mem (mode, operands[1]);
fb4d4348 4029 break;
f676971a 4030
0ac081f6
AH
4031 case V16QImode:
4032 case V8HImode:
4033 case V4SFmode:
4034 case V4SImode:
a3170dc6
AH
4035 case V4HImode:
4036 case V2SFmode:
4037 case V2SImode:
00a892b8 4038 case V1DImode:
69ef87e2 4039 if (CONSTANT_P (operands[1])
d744e06e 4040 && !easy_vector_constant (operands[1], mode))
0ac081f6
AH
4041 operands[1] = force_const_mem (mode, operands[1]);
4042 break;
f676971a 4043
fb4d4348 4044 case SImode:
a9098fd0 4045 case DImode:
fb4d4348
GK
4046 /* Use default pattern for address of ELF small data */
4047 if (TARGET_ELF
a9098fd0 4048 && mode == Pmode
f607bc57 4049 && DEFAULT_ABI == ABI_V4
f676971a 4050 && (GET_CODE (operands[1]) == SYMBOL_REF
a9098fd0
GK
4051 || GET_CODE (operands[1]) == CONST)
4052 && small_data_operand (operands[1], mode))
fb4d4348
GK
4053 {
4054 emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
4055 return;
4056 }
4057
f607bc57 4058 if (DEFAULT_ABI == ABI_V4
a9098fd0
GK
4059 && mode == Pmode && mode == SImode
4060 && flag_pic == 1 && got_operand (operands[1], mode))
fb4d4348
GK
4061 {
4062 emit_insn (gen_movsi_got (operands[0], operands[1]));
4063 return;
4064 }
4065
ee890fe2 4066 if ((TARGET_ELF || DEFAULT_ABI == ABI_DARWIN)
f1384257
AM
4067 && TARGET_NO_TOC
4068 && ! flag_pic
a9098fd0 4069 && mode == Pmode
fb4d4348
GK
4070 && CONSTANT_P (operands[1])
4071 && GET_CODE (operands[1]) != HIGH
4072 && GET_CODE (operands[1]) != CONST_INT)
4073 {
a9098fd0 4074 rtx target = (no_new_pseudos ? operands[0] : gen_reg_rtx (mode));
fb4d4348
GK
4075
4076 /* If this is a function address on -mcall-aixdesc,
4077 convert it to the address of the descriptor. */
4078 if (DEFAULT_ABI == ABI_AIX
4079 && GET_CODE (operands[1]) == SYMBOL_REF
4080 && XSTR (operands[1], 0)[0] == '.')
4081 {
4082 const char *name = XSTR (operands[1], 0);
4083 rtx new_ref;
4084 while (*name == '.')
4085 name++;
4086 new_ref = gen_rtx_SYMBOL_REF (Pmode, name);
4087 CONSTANT_POOL_ADDRESS_P (new_ref)
4088 = CONSTANT_POOL_ADDRESS_P (operands[1]);
d1908feb 4089 SYMBOL_REF_FLAGS (new_ref) = SYMBOL_REF_FLAGS (operands[1]);
fb4d4348 4090 SYMBOL_REF_USED (new_ref) = SYMBOL_REF_USED (operands[1]);
c185c797 4091 SYMBOL_REF_DATA (new_ref) = SYMBOL_REF_DATA (operands[1]);
fb4d4348
GK
4092 operands[1] = new_ref;
4093 }
7509c759 4094
ee890fe2
SS
4095 if (DEFAULT_ABI == ABI_DARWIN)
4096 {
ab82a49f
AP
4097#if TARGET_MACHO
4098 if (MACHO_DYNAMIC_NO_PIC_P)
4099 {
4100 /* Take care of any required data indirection. */
4101 operands[1] = rs6000_machopic_legitimize_pic_address (
4102 operands[1], mode, operands[0]);
4103 if (operands[0] != operands[1])
4104 emit_insn (gen_rtx_SET (VOIDmode,
c4ad648e 4105 operands[0], operands[1]));
ab82a49f
AP
4106 return;
4107 }
4108#endif
b8a55285
AP
4109 emit_insn (gen_macho_high (target, operands[1]));
4110 emit_insn (gen_macho_low (operands[0], target, operands[1]));
ee890fe2
SS
4111 return;
4112 }
4113
fb4d4348
GK
4114 emit_insn (gen_elf_high (target, operands[1]));
4115 emit_insn (gen_elf_low (operands[0], target, operands[1]));
4116 return;
4117 }
4118
a9098fd0
GK
4119 /* If this is a SYMBOL_REF that refers to a constant pool entry,
4120 and we have put it in the TOC, we just need to make a TOC-relative
4121 reference to it. */
4122 if (TARGET_TOC
4123 && GET_CODE (operands[1]) == SYMBOL_REF
4d588c14 4124 && constant_pool_expr_p (operands[1])
a9098fd0
GK
4125 && ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (get_pool_constant (operands[1]),
4126 get_pool_mode (operands[1])))
fb4d4348 4127 {
a9098fd0 4128 operands[1] = create_TOC_reference (operands[1]);
fb4d4348 4129 }
a9098fd0
GK
4130 else if (mode == Pmode
4131 && CONSTANT_P (operands[1])
38886f37
AO
4132 && ((GET_CODE (operands[1]) != CONST_INT
4133 && ! easy_fp_constant (operands[1], mode))
4134 || (GET_CODE (operands[1]) == CONST_INT
4135 && num_insns_constant (operands[1], mode) > 2)
4136 || (GET_CODE (operands[0]) == REG
4137 && FP_REGNO_P (REGNO (operands[0]))))
a9098fd0 4138 && GET_CODE (operands[1]) != HIGH
4d588c14
RH
4139 && ! legitimate_constant_pool_address_p (operands[1])
4140 && ! toc_relative_expr_p (operands[1]))
fb4d4348
GK
4141 {
4142 /* Emit a USE operation so that the constant isn't deleted if
4143 expensive optimizations are turned on because nobody
4144 references it. This should only be done for operands that
4145 contain SYMBOL_REFs with CONSTANT_POOL_ADDRESS_P set.
4146 This should not be done for operands that contain LABEL_REFs.
4147 For now, we just handle the obvious case. */
4148 if (GET_CODE (operands[1]) != LABEL_REF)
4149 emit_insn (gen_rtx_USE (VOIDmode, operands[1]));
4150
c859cda6 4151#if TARGET_MACHO
ee890fe2 4152 /* Darwin uses a special PIC legitimizer. */
ab82a49f 4153 if (DEFAULT_ABI == ABI_DARWIN && MACHOPIC_INDIRECT)
ee890fe2 4154 {
ee890fe2
SS
4155 operands[1] =
4156 rs6000_machopic_legitimize_pic_address (operands[1], mode,
c859cda6
DJ
4157 operands[0]);
4158 if (operands[0] != operands[1])
4159 emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
ee890fe2
SS
4160 return;
4161 }
c859cda6 4162#endif
ee890fe2 4163
fb4d4348
GK
4164 /* If we are to limit the number of things we put in the TOC and
4165 this is a symbol plus a constant we can add in one insn,
4166 just put the symbol in the TOC and add the constant. Don't do
4167 this if reload is in progress. */
4168 if (GET_CODE (operands[1]) == CONST
4169 && TARGET_NO_SUM_IN_TOC && ! reload_in_progress
4170 && GET_CODE (XEXP (operands[1], 0)) == PLUS
a9098fd0 4171 && add_operand (XEXP (XEXP (operands[1], 0), 1), mode)
fb4d4348
GK
4172 && (GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == LABEL_REF
4173 || GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == SYMBOL_REF)
4174 && ! side_effects_p (operands[0]))
4175 {
a4f6c312
SS
4176 rtx sym =
4177 force_const_mem (mode, XEXP (XEXP (operands[1], 0), 0));
fb4d4348
GK
4178 rtx other = XEXP (XEXP (operands[1], 0), 1);
4179
a9098fd0
GK
4180 sym = force_reg (mode, sym);
4181 if (mode == SImode)
4182 emit_insn (gen_addsi3 (operands[0], sym, other));
4183 else
4184 emit_insn (gen_adddi3 (operands[0], sym, other));
fb4d4348
GK
4185 return;
4186 }
4187
a9098fd0 4188 operands[1] = force_const_mem (mode, operands[1]);
fb4d4348 4189
f676971a 4190 if (TARGET_TOC
4d588c14 4191 && constant_pool_expr_p (XEXP (operands[1], 0))
d34c5b80
DE
4192 && ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (
4193 get_pool_constant (XEXP (operands[1], 0)),
4194 get_pool_mode (XEXP (operands[1], 0))))
a9098fd0 4195 {
ba4828e0 4196 operands[1]
542a8afa 4197 = gen_const_mem (mode,
c4ad648e 4198 create_TOC_reference (XEXP (operands[1], 0)));
ba4828e0 4199 set_mem_alias_set (operands[1], get_TOC_alias_set ());
a9098fd0 4200 }
fb4d4348
GK
4201 }
4202 break;
a9098fd0 4203
fb4d4348 4204 case TImode:
76d2b81d
DJ
4205 rs6000_eliminate_indexed_memrefs (operands);
4206
27dc0551
DE
4207 if (TARGET_POWER)
4208 {
4209 emit_insn (gen_rtx_PARALLEL (VOIDmode,
4210 gen_rtvec (2,
4211 gen_rtx_SET (VOIDmode,
4212 operands[0], operands[1]),
4213 gen_rtx_CLOBBER (VOIDmode,
4214 gen_rtx_SCRATCH (SImode)))));
4215 return;
4216 }
fb4d4348
GK
4217 break;
4218
4219 default:
37409796 4220 gcc_unreachable ();
fb4d4348
GK
4221 }
4222
a9098fd0
GK
4223 /* Above, we may have called force_const_mem which may have returned
4224 an invalid address. If we can, fix this up; otherwise, reload will
4225 have to deal with it. */
8f4e6caf
RH
4226 if (GET_CODE (operands[1]) == MEM && ! reload_in_progress)
4227 operands[1] = validize_mem (operands[1]);
a9098fd0 4228
8f4e6caf 4229 emit_set:
fb4d4348
GK
4230 emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
4231}
4697a36c 4232\f
2858f73a
GK
4233/* Nonzero if we can use a floating-point register to pass this arg. */
4234#define USE_FP_FOR_ARG_P(CUM,MODE,TYPE) \
ebb109ad 4235 (SCALAR_FLOAT_MODE_P (MODE) \
00b79d54 4236 && !DECIMAL_FLOAT_MODE_P (MODE) \
2858f73a
GK
4237 && (CUM)->fregno <= FP_ARG_MAX_REG \
4238 && TARGET_HARD_FLOAT && TARGET_FPRS)
4239
4240/* Nonzero if we can use an AltiVec register to pass this arg. */
4241#define USE_ALTIVEC_FOR_ARG_P(CUM,MODE,TYPE,NAMED) \
4242 (ALTIVEC_VECTOR_MODE (MODE) \
4243 && (CUM)->vregno <= ALTIVEC_ARG_MAX_REG \
4244 && TARGET_ALTIVEC_ABI \
83953138 4245 && (NAMED))
2858f73a 4246
c6e8c921
GK
4247/* Return a nonzero value to say to return the function value in
4248 memory, just as large structures are always returned. TYPE will be
4249 the data type of the value, and FNTYPE will be the type of the
4250 function doing the returning, or @code{NULL} for libcalls.
4251
4252 The AIX ABI for the RS/6000 specifies that all structures are
4253 returned in memory. The Darwin ABI does the same. The SVR4 ABI
4254 specifies that structures <= 8 bytes are returned in r3/r4, but a
4255 draft put them in memory, and GCC used to implement the draft
df01da37 4256 instead of the final standard. Therefore, aix_struct_return
c6e8c921
GK
4257 controls this instead of DEFAULT_ABI; V.4 targets needing backward
4258 compatibility can change DRAFT_V4_STRUCT_RET to override the
4259 default, and -m switches get the final word. See
4260 rs6000_override_options for more details.
4261
4262 The PPC32 SVR4 ABI uses IEEE double extended for long double, if 128-bit
4263 long double support is enabled. These values are returned in memory.
4264
4265 int_size_in_bytes returns -1 for variable size objects, which go in
4266 memory always. The cast to unsigned makes -1 > 8. */
4267
4268static bool
4269rs6000_return_in_memory (tree type, tree fntype ATTRIBUTE_UNUSED)
4270{
594a51fe
SS
4271 /* In the darwin64 abi, try to use registers for larger structs
4272 if possible. */
0b5383eb 4273 if (rs6000_darwin64_abi
594a51fe 4274 && TREE_CODE (type) == RECORD_TYPE
0b5383eb
DJ
4275 && int_size_in_bytes (type) > 0)
4276 {
4277 CUMULATIVE_ARGS valcum;
4278 rtx valret;
4279
4280 valcum.words = 0;
4281 valcum.fregno = FP_ARG_MIN_REG;
4282 valcum.vregno = ALTIVEC_ARG_MIN_REG;
4283 /* Do a trial code generation as if this were going to be passed
4284 as an argument; if any part goes in memory, we return NULL. */
4285 valret = rs6000_darwin64_record_arg (&valcum, type, 1, true);
4286 if (valret)
4287 return false;
4288 /* Otherwise fall through to more conventional ABI rules. */
4289 }
594a51fe 4290
c6e8c921 4291 if (AGGREGATE_TYPE_P (type)
df01da37 4292 && (aix_struct_return
c6e8c921
GK
4293 || (unsigned HOST_WIDE_INT) int_size_in_bytes (type) > 8))
4294 return true;
b693336b 4295
bada2eb8
DE
4296 /* Allow -maltivec -mabi=no-altivec without warning. Altivec vector
4297 modes only exist for GCC vector types if -maltivec. */
4298 if (TARGET_32BIT && !TARGET_ALTIVEC_ABI
4299 && ALTIVEC_VECTOR_MODE (TYPE_MODE (type)))
4300 return false;
4301
b693336b
PB
4302 /* Return synthetic vectors in memory. */
4303 if (TREE_CODE (type) == VECTOR_TYPE
ad630bef 4304 && int_size_in_bytes (type) > (TARGET_ALTIVEC_ABI ? 16 : 8))
b693336b
PB
4305 {
4306 static bool warned_for_return_big_vectors = false;
4307 if (!warned_for_return_big_vectors)
4308 {
d4ee4d25 4309 warning (0, "GCC vector returned by reference: "
b693336b
PB
4310 "non-standard ABI extension with no compatibility guarantee");
4311 warned_for_return_big_vectors = true;
4312 }
4313 return true;
4314 }
4315
602ea4d3 4316 if (DEFAULT_ABI == ABI_V4 && TARGET_IEEEQUAD && TYPE_MODE (type) == TFmode)
c6e8c921 4317 return true;
ad630bef 4318
c6e8c921
GK
4319 return false;
4320}
4321
4697a36c
MM
4322/* Initialize a variable CUM of type CUMULATIVE_ARGS
4323 for a call to a function whose data type is FNTYPE.
4324 For a library call, FNTYPE is 0.
4325
4326 For incoming args we set the number of arguments in the prototype large
1c20ae99 4327 so we never return a PARALLEL. */
4697a36c
MM
4328
4329void
f676971a 4330init_cumulative_args (CUMULATIVE_ARGS *cum, tree fntype,
0f6937fe
AM
4331 rtx libname ATTRIBUTE_UNUSED, int incoming,
4332 int libcall, int n_named_args)
4697a36c
MM
4333{
4334 static CUMULATIVE_ARGS zero_cumulative;
4335
4336 *cum = zero_cumulative;
4337 cum->words = 0;
4338 cum->fregno = FP_ARG_MIN_REG;
0ac081f6 4339 cum->vregno = ALTIVEC_ARG_MIN_REG;
4697a36c 4340 cum->prototype = (fntype && TYPE_ARG_TYPES (fntype));
ddcc8263
DE
4341 cum->call_cookie = ((DEFAULT_ABI == ABI_V4 && libcall)
4342 ? CALL_LIBCALL : CALL_NORMAL);
4cc833b7 4343 cum->sysv_gregno = GP_ARG_MIN_REG;
a6c9bed4
AH
4344 cum->stdarg = fntype
4345 && (TYPE_ARG_TYPES (fntype) != 0
4346 && (TREE_VALUE (tree_last (TYPE_ARG_TYPES (fntype)))
4347 != void_type_node));
4697a36c 4348
0f6937fe
AM
4349 cum->nargs_prototype = 0;
4350 if (incoming || cum->prototype)
4351 cum->nargs_prototype = n_named_args;
4697a36c 4352
a5c76ee6 4353 /* Check for a longcall attribute. */
3eb4e360
AM
4354 if ((!fntype && rs6000_default_long_calls)
4355 || (fntype
4356 && lookup_attribute ("longcall", TYPE_ATTRIBUTES (fntype))
4357 && !lookup_attribute ("shortcall", TYPE_ATTRIBUTES (fntype))))
4358 cum->call_cookie |= CALL_LONG;
6a4cee5f 4359
4697a36c
MM
4360 if (TARGET_DEBUG_ARG)
4361 {
4362 fprintf (stderr, "\ninit_cumulative_args:");
4363 if (fntype)
4364 {
4365 tree ret_type = TREE_TYPE (fntype);
4366 fprintf (stderr, " ret code = %s,",
4367 tree_code_name[ (int)TREE_CODE (ret_type) ]);
4368 }
4369
6a4cee5f
MM
4370 if (cum->call_cookie & CALL_LONG)
4371 fprintf (stderr, " longcall,");
4372
4697a36c
MM
4373 fprintf (stderr, " proto = %d, nargs = %d\n",
4374 cum->prototype, cum->nargs_prototype);
4375 }
f676971a 4376
c4ad648e
AM
4377 if (fntype
4378 && !TARGET_ALTIVEC
4379 && TARGET_ALTIVEC_ABI
4380 && ALTIVEC_VECTOR_MODE (TYPE_MODE (TREE_TYPE (fntype))))
4381 {
c85ce869 4382 error ("cannot return value in vector register because"
c4ad648e 4383 " altivec instructions are disabled, use -maltivec"
c85ce869 4384 " to enable them");
c4ad648e 4385 }
4697a36c
MM
4386}
4387\f
fe984136
RH
4388/* Return true if TYPE must be passed on the stack and not in registers. */
4389
4390static bool
4391rs6000_must_pass_in_stack (enum machine_mode mode, tree type)
4392{
4393 if (DEFAULT_ABI == ABI_AIX || TARGET_64BIT)
4394 return must_pass_in_stack_var_size (mode, type);
4395 else
4396 return must_pass_in_stack_var_size_or_pad (mode, type);
4397}
4398
c229cba9
DE
4399/* If defined, a C expression which determines whether, and in which
4400 direction, to pad out an argument with extra space. The value
4401 should be of type `enum direction': either `upward' to pad above
4402 the argument, `downward' to pad below, or `none' to inhibit
4403 padding.
4404
4405 For the AIX ABI structs are always stored left shifted in their
4406 argument slot. */
4407
9ebbca7d 4408enum direction
a2369ed3 4409function_arg_padding (enum machine_mode mode, tree type)
c229cba9 4410{
6e985040
AM
4411#ifndef AGGREGATE_PADDING_FIXED
4412#define AGGREGATE_PADDING_FIXED 0
4413#endif
4414#ifndef AGGREGATES_PAD_UPWARD_ALWAYS
4415#define AGGREGATES_PAD_UPWARD_ALWAYS 0
4416#endif
4417
4418 if (!AGGREGATE_PADDING_FIXED)
4419 {
4420 /* GCC used to pass structures of the same size as integer types as
4421 if they were in fact integers, ignoring FUNCTION_ARG_PADDING.
19525b57 4422 i.e. Structures of size 1 or 2 (or 4 when TARGET_64BIT) were
6e985040
AM
4423 passed padded downward, except that -mstrict-align further
4424 muddied the water in that multi-component structures of 2 and 4
4425 bytes in size were passed padded upward.
4426
4427 The following arranges for best compatibility with previous
4428 versions of gcc, but removes the -mstrict-align dependency. */
4429 if (BYTES_BIG_ENDIAN)
4430 {
4431 HOST_WIDE_INT size = 0;
4432
4433 if (mode == BLKmode)
4434 {
4435 if (type && TREE_CODE (TYPE_SIZE (type)) == INTEGER_CST)
4436 size = int_size_in_bytes (type);
4437 }
4438 else
4439 size = GET_MODE_SIZE (mode);
4440
4441 if (size == 1 || size == 2 || size == 4)
4442 return downward;
4443 }
4444 return upward;
4445 }
4446
4447 if (AGGREGATES_PAD_UPWARD_ALWAYS)
4448 {
4449 if (type != 0 && AGGREGATE_TYPE_P (type))
4450 return upward;
4451 }
c229cba9 4452
d3704c46
KH
4453 /* Fall back to the default. */
4454 return DEFAULT_FUNCTION_ARG_PADDING (mode, type);
c229cba9
DE
4455}
4456
b6c9286a 4457/* If defined, a C expression that gives the alignment boundary, in bits,
f676971a 4458 of an argument with the specified mode and type. If it is not defined,
b6c9286a 4459 PARM_BOUNDARY is used for all arguments.
f676971a 4460
b693336b
PB
4461 V.4 wants long longs to be double word aligned.
4462 Doubleword align SPE vectors.
4463 Quadword align Altivec vectors.
4464 Quadword align large synthetic vector types. */
b6c9286a
MM
4465
4466int
b693336b 4467function_arg_boundary (enum machine_mode mode, tree type)
b6c9286a 4468{
4ed78545
AM
4469 if (DEFAULT_ABI == ABI_V4 && GET_MODE_SIZE (mode) == 8)
4470 return 64;
ad630bef
DE
4471 else if (SPE_VECTOR_MODE (mode)
4472 || (type && TREE_CODE (type) == VECTOR_TYPE
4473 && int_size_in_bytes (type) >= 8
4474 && int_size_in_bytes (type) < 16))
e1f83b4d 4475 return 64;
ad630bef
DE
4476 else if (ALTIVEC_VECTOR_MODE (mode)
4477 || (type && TREE_CODE (type) == VECTOR_TYPE
4478 && int_size_in_bytes (type) >= 16))
0ac081f6 4479 return 128;
0b5383eb
DJ
4480 else if (rs6000_darwin64_abi && mode == BLKmode
4481 && type && TYPE_ALIGN (type) > 64)
4482 return 128;
9ebbca7d 4483 else
b6c9286a 4484 return PARM_BOUNDARY;
b6c9286a 4485}
c53bdcf5 4486
294bd182
AM
4487/* For a function parm of MODE and TYPE, return the starting word in
4488 the parameter area. NWORDS of the parameter area are already used. */
4489
4490static unsigned int
4491rs6000_parm_start (enum machine_mode mode, tree type, unsigned int nwords)
4492{
4493 unsigned int align;
4494 unsigned int parm_offset;
4495
4496 align = function_arg_boundary (mode, type) / PARM_BOUNDARY - 1;
4497 parm_offset = DEFAULT_ABI == ABI_V4 ? 2 : 6;
4498 return nwords + (-(parm_offset + nwords) & align);
4499}
4500
c53bdcf5
AM
4501/* Compute the size (in words) of a function argument. */
4502
4503static unsigned long
4504rs6000_arg_size (enum machine_mode mode, tree type)
4505{
4506 unsigned long size;
4507
4508 if (mode != BLKmode)
4509 size = GET_MODE_SIZE (mode);
4510 else
4511 size = int_size_in_bytes (type);
4512
4513 if (TARGET_32BIT)
4514 return (size + 3) >> 2;
4515 else
4516 return (size + 7) >> 3;
4517}
b6c9286a 4518\f
0b5383eb 4519/* Use this to flush pending int fields. */
594a51fe
SS
4520
4521static void
0b5383eb
DJ
4522rs6000_darwin64_record_arg_advance_flush (CUMULATIVE_ARGS *cum,
4523 HOST_WIDE_INT bitpos)
594a51fe 4524{
0b5383eb
DJ
4525 unsigned int startbit, endbit;
4526 int intregs, intoffset;
4527 enum machine_mode mode;
594a51fe 4528
0b5383eb
DJ
4529 if (cum->intoffset == -1)
4530 return;
594a51fe 4531
0b5383eb
DJ
4532 intoffset = cum->intoffset;
4533 cum->intoffset = -1;
4534
4535 if (intoffset % BITS_PER_WORD != 0)
4536 {
4537 mode = mode_for_size (BITS_PER_WORD - intoffset % BITS_PER_WORD,
4538 MODE_INT, 0);
4539 if (mode == BLKmode)
594a51fe 4540 {
0b5383eb
DJ
4541 /* We couldn't find an appropriate mode, which happens,
4542 e.g., in packed structs when there are 3 bytes to load.
4543 Back intoffset back to the beginning of the word in this
4544 case. */
4545 intoffset = intoffset & -BITS_PER_WORD;
594a51fe 4546 }
594a51fe 4547 }
0b5383eb
DJ
4548
4549 startbit = intoffset & -BITS_PER_WORD;
4550 endbit = (bitpos + BITS_PER_WORD - 1) & -BITS_PER_WORD;
4551 intregs = (endbit - startbit) / BITS_PER_WORD;
4552 cum->words += intregs;
4553}
4554
4555/* The darwin64 ABI calls for us to recurse down through structs,
4556 looking for elements passed in registers. Unfortunately, we have
4557 to track int register count here also because of misalignments
4558 in powerpc alignment mode. */
4559
4560static void
4561rs6000_darwin64_record_arg_advance_recurse (CUMULATIVE_ARGS *cum,
4562 tree type,
4563 HOST_WIDE_INT startbitpos)
4564{
4565 tree f;
4566
4567 for (f = TYPE_FIELDS (type); f ; f = TREE_CHAIN (f))
4568 if (TREE_CODE (f) == FIELD_DECL)
4569 {
4570 HOST_WIDE_INT bitpos = startbitpos;
4571 tree ftype = TREE_TYPE (f);
4572 enum machine_mode mode = TYPE_MODE (ftype);
4573
4574 if (DECL_SIZE (f) != 0
4575 && host_integerp (bit_position (f), 1))
4576 bitpos += int_bit_position (f);
4577
4578 /* ??? FIXME: else assume zero offset. */
4579
4580 if (TREE_CODE (ftype) == RECORD_TYPE)
4581 rs6000_darwin64_record_arg_advance_recurse (cum, ftype, bitpos);
4582 else if (USE_FP_FOR_ARG_P (cum, mode, ftype))
4583 {
4584 rs6000_darwin64_record_arg_advance_flush (cum, bitpos);
4585 cum->fregno += (GET_MODE_SIZE (mode) + 7) >> 3;
4586 cum->words += (GET_MODE_SIZE (mode) + 7) >> 3;
4587 }
4588 else if (USE_ALTIVEC_FOR_ARG_P (cum, mode, type, 1))
4589 {
4590 rs6000_darwin64_record_arg_advance_flush (cum, bitpos);
4591 cum->vregno++;
4592 cum->words += 2;
4593 }
4594 else if (cum->intoffset == -1)
4595 cum->intoffset = bitpos;
4596 }
594a51fe
SS
4597}
4598
4697a36c
MM
4599/* Update the data in CUM to advance over an argument
4600 of mode MODE and data type TYPE.
b2d04ecf
AM
4601 (TYPE is null for libcalls where that information may not be available.)
4602
4603 Note that for args passed by reference, function_arg will be called
4604 with MODE and TYPE set to that of the pointer to the arg, not the arg
4605 itself. */
4697a36c
MM
4606
4607void
f676971a 4608function_arg_advance (CUMULATIVE_ARGS *cum, enum machine_mode mode,
594a51fe 4609 tree type, int named, int depth)
4697a36c 4610{
0b5383eb
DJ
4611 int size;
4612
594a51fe
SS
4613 /* Only tick off an argument if we're not recursing. */
4614 if (depth == 0)
4615 cum->nargs_prototype--;
4697a36c 4616
ad630bef
DE
4617 if (TARGET_ALTIVEC_ABI
4618 && (ALTIVEC_VECTOR_MODE (mode)
4619 || (type && TREE_CODE (type) == VECTOR_TYPE
4620 && int_size_in_bytes (type) == 16)))
0ac081f6 4621 {
4ed78545
AM
4622 bool stack = false;
4623
2858f73a 4624 if (USE_ALTIVEC_FOR_ARG_P (cum, mode, type, named))
c4ad648e 4625 {
6d0ef01e
HP
4626 cum->vregno++;
4627 if (!TARGET_ALTIVEC)
c85ce869 4628 error ("cannot pass argument in vector register because"
6d0ef01e 4629 " altivec instructions are disabled, use -maltivec"
c85ce869 4630 " to enable them");
4ed78545
AM
4631
4632 /* PowerPC64 Linux and AIX allocate GPRs for a vector argument
f676971a 4633 even if it is going to be passed in a vector register.
4ed78545
AM
4634 Darwin does the same for variable-argument functions. */
4635 if ((DEFAULT_ABI == ABI_AIX && TARGET_64BIT)
4636 || (cum->stdarg && DEFAULT_ABI != ABI_V4))
4637 stack = true;
6d0ef01e 4638 }
4ed78545
AM
4639 else
4640 stack = true;
4641
4642 if (stack)
c4ad648e 4643 {
a594a19c 4644 int align;
f676971a 4645
2858f73a
GK
4646 /* Vector parameters must be 16-byte aligned. This places
4647 them at 2 mod 4 in terms of words in 32-bit mode, since
4648 the parameter save area starts at offset 24 from the
4649 stack. In 64-bit mode, they just have to start on an
4650 even word, since the parameter save area is 16-byte
4651 aligned. Space for GPRs is reserved even if the argument
4652 will be passed in memory. */
4653 if (TARGET_32BIT)
4ed78545 4654 align = (2 - cum->words) & 3;
2858f73a
GK
4655 else
4656 align = cum->words & 1;
c53bdcf5 4657 cum->words += align + rs6000_arg_size (mode, type);
f676971a 4658
a594a19c
GK
4659 if (TARGET_DEBUG_ARG)
4660 {
f676971a 4661 fprintf (stderr, "function_adv: words = %2d, align=%d, ",
a594a19c
GK
4662 cum->words, align);
4663 fprintf (stderr, "nargs = %4d, proto = %d, mode = %4s\n",
f676971a 4664 cum->nargs_prototype, cum->prototype,
2858f73a 4665 GET_MODE_NAME (mode));
a594a19c
GK
4666 }
4667 }
0ac081f6 4668 }
a4b0320c 4669 else if (TARGET_SPE_ABI && TARGET_SPE && SPE_VECTOR_MODE (mode)
a6c9bed4
AH
4670 && !cum->stdarg
4671 && cum->sysv_gregno <= GP_ARG_MAX_REG)
a4b0320c 4672 cum->sysv_gregno++;
594a51fe
SS
4673
4674 else if (rs6000_darwin64_abi
4675 && mode == BLKmode
0b5383eb
DJ
4676 && TREE_CODE (type) == RECORD_TYPE
4677 && (size = int_size_in_bytes (type)) > 0)
4678 {
4679 /* Variable sized types have size == -1 and are
4680 treated as if consisting entirely of ints.
4681 Pad to 16 byte boundary if needed. */
4682 if (TYPE_ALIGN (type) >= 2 * BITS_PER_WORD
4683 && (cum->words % 2) != 0)
4684 cum->words++;
4685 /* For varargs, we can just go up by the size of the struct. */
4686 if (!named)
4687 cum->words += (size + 7) / 8;
4688 else
4689 {
4690 /* It is tempting to say int register count just goes up by
4691 sizeof(type)/8, but this is wrong in a case such as
4692 { int; double; int; } [powerpc alignment]. We have to
4693 grovel through the fields for these too. */
4694 cum->intoffset = 0;
4695 rs6000_darwin64_record_arg_advance_recurse (cum, type, 0);
bb8df8a6 4696 rs6000_darwin64_record_arg_advance_flush (cum,
0b5383eb
DJ
4697 size * BITS_PER_UNIT);
4698 }
4699 }
f607bc57 4700 else if (DEFAULT_ABI == ABI_V4)
4697a36c 4701 {
a3170dc6 4702 if (TARGET_HARD_FLOAT && TARGET_FPRS
602ea4d3
JJ
4703 && (mode == SFmode || mode == DFmode
4704 || (mode == TFmode && !TARGET_IEEEQUAD)))
4697a36c 4705 {
602ea4d3
JJ
4706 if (cum->fregno + (mode == TFmode ? 1 : 0) <= FP_ARG_V4_MAX_REG)
4707 cum->fregno += (GET_MODE_SIZE (mode) + 7) >> 3;
4cc833b7
RH
4708 else
4709 {
602ea4d3
JJ
4710 cum->fregno = FP_ARG_V4_MAX_REG + 1;
4711 if (mode == DFmode || mode == TFmode)
c4ad648e 4712 cum->words += cum->words & 1;
c53bdcf5 4713 cum->words += rs6000_arg_size (mode, type);
4cc833b7 4714 }
4697a36c 4715 }
4cc833b7
RH
4716 else
4717 {
b2d04ecf 4718 int n_words = rs6000_arg_size (mode, type);
4cc833b7
RH
4719 int gregno = cum->sysv_gregno;
4720
4ed78545
AM
4721 /* Long long and SPE vectors are put in (r3,r4), (r5,r6),
4722 (r7,r8) or (r9,r10). As does any other 2 word item such
4723 as complex int due to a historical mistake. */
4724 if (n_words == 2)
4725 gregno += (1 - gregno) & 1;
4cc833b7 4726
4ed78545 4727 /* Multi-reg args are not split between registers and stack. */
4cc833b7
RH
4728 if (gregno + n_words - 1 > GP_ARG_MAX_REG)
4729 {
4ed78545
AM
4730 /* Long long and SPE vectors are aligned on the stack.
4731 So are other 2 word items such as complex int due to
4732 a historical mistake. */
4cc833b7
RH
4733 if (n_words == 2)
4734 cum->words += cum->words & 1;
4735 cum->words += n_words;
4736 }
4697a36c 4737
4cc833b7
RH
4738 /* Note: continuing to accumulate gregno past when we've started
4739 spilling to the stack indicates the fact that we've started
4740 spilling to the stack to expand_builtin_saveregs. */
4741 cum->sysv_gregno = gregno + n_words;
4742 }
4697a36c 4743
4cc833b7
RH
4744 if (TARGET_DEBUG_ARG)
4745 {
4746 fprintf (stderr, "function_adv: words = %2d, fregno = %2d, ",
4747 cum->words, cum->fregno);
4748 fprintf (stderr, "gregno = %2d, nargs = %4d, proto = %d, ",
4749 cum->sysv_gregno, cum->nargs_prototype, cum->prototype);
4750 fprintf (stderr, "mode = %4s, named = %d\n",
4751 GET_MODE_NAME (mode), named);
4752 }
4697a36c
MM
4753 }
4754 else
4cc833b7 4755 {
b2d04ecf 4756 int n_words = rs6000_arg_size (mode, type);
294bd182
AM
4757 int start_words = cum->words;
4758 int align_words = rs6000_parm_start (mode, type, start_words);
a4f6c312 4759
294bd182 4760 cum->words = align_words + n_words;
4697a36c 4761
ebb109ad 4762 if (SCALAR_FLOAT_MODE_P (mode)
00b79d54 4763 && !DECIMAL_FLOAT_MODE_P (mode)
a3170dc6 4764 && TARGET_HARD_FLOAT && TARGET_FPRS)
c53bdcf5 4765 cum->fregno += (GET_MODE_SIZE (mode) + 7) >> 3;
4cc833b7
RH
4766
4767 if (TARGET_DEBUG_ARG)
4768 {
4769 fprintf (stderr, "function_adv: words = %2d, fregno = %2d, ",
4770 cum->words, cum->fregno);
4771 fprintf (stderr, "nargs = %4d, proto = %d, mode = %4s, ",
4772 cum->nargs_prototype, cum->prototype, GET_MODE_NAME (mode));
594a51fe 4773 fprintf (stderr, "named = %d, align = %d, depth = %d\n",
294bd182 4774 named, align_words - start_words, depth);
4cc833b7
RH
4775 }
4776 }
4697a36c 4777}
a6c9bed4 4778
f82f556d
AH
4779static rtx
4780spe_build_register_parallel (enum machine_mode mode, int gregno)
4781{
54b695e7 4782 rtx r1, r3;
f82f556d 4783
37409796 4784 switch (mode)
f82f556d 4785 {
37409796 4786 case DFmode:
54b695e7
AH
4787 r1 = gen_rtx_REG (DImode, gregno);
4788 r1 = gen_rtx_EXPR_LIST (VOIDmode, r1, const0_rtx);
4789 return gen_rtx_PARALLEL (mode, gen_rtvec (1, r1));
37409796
NS
4790
4791 case DCmode:
54b695e7
AH
4792 r1 = gen_rtx_REG (DImode, gregno);
4793 r1 = gen_rtx_EXPR_LIST (VOIDmode, r1, const0_rtx);
4794 r3 = gen_rtx_REG (DImode, gregno + 2);
4795 r3 = gen_rtx_EXPR_LIST (VOIDmode, r3, GEN_INT (8));
4796 return gen_rtx_PARALLEL (mode, gen_rtvec (2, r1, r3));
37409796
NS
4797
4798 default:
4799 gcc_unreachable ();
f82f556d 4800 }
f82f556d 4801}
b78d48dd 4802
f82f556d 4803/* Determine where to put a SIMD argument on the SPE. */
a6c9bed4 4804static rtx
f676971a 4805rs6000_spe_function_arg (CUMULATIVE_ARGS *cum, enum machine_mode mode,
a2369ed3 4806 tree type)
a6c9bed4 4807{
f82f556d
AH
4808 int gregno = cum->sysv_gregno;
4809
4810 /* On E500 v2, double arithmetic is done on the full 64-bit GPR, but
600e1f95 4811 are passed and returned in a pair of GPRs for ABI compatibility. */
18f63bfa 4812 if (TARGET_E500_DOUBLE && (mode == DFmode || mode == DCmode))
f82f556d 4813 {
b5870bee
AH
4814 int n_words = rs6000_arg_size (mode, type);
4815
f82f556d 4816 /* Doubles go in an odd/even register pair (r5/r6, etc). */
b5870bee
AH
4817 if (mode == DFmode)
4818 gregno += (1 - gregno) & 1;
f82f556d 4819
b5870bee
AH
4820 /* Multi-reg args are not split between registers and stack. */
4821 if (gregno + n_words - 1 > GP_ARG_MAX_REG)
f82f556d
AH
4822 return NULL_RTX;
4823
4824 return spe_build_register_parallel (mode, gregno);
4825 }
a6c9bed4
AH
4826 if (cum->stdarg)
4827 {
c53bdcf5 4828 int n_words = rs6000_arg_size (mode, type);
a6c9bed4
AH
4829
4830 /* SPE vectors are put in odd registers. */
4831 if (n_words == 2 && (gregno & 1) == 0)
4832 gregno += 1;
4833
4834 if (gregno + n_words - 1 <= GP_ARG_MAX_REG)
4835 {
4836 rtx r1, r2;
4837 enum machine_mode m = SImode;
4838
4839 r1 = gen_rtx_REG (m, gregno);
4840 r1 = gen_rtx_EXPR_LIST (m, r1, const0_rtx);
4841 r2 = gen_rtx_REG (m, gregno + 1);
4842 r2 = gen_rtx_EXPR_LIST (m, r2, GEN_INT (4));
4843 return gen_rtx_PARALLEL (mode, gen_rtvec (2, r1, r2));
4844 }
4845 else
b78d48dd 4846 return NULL_RTX;
a6c9bed4
AH
4847 }
4848 else
4849 {
f82f556d
AH
4850 if (gregno <= GP_ARG_MAX_REG)
4851 return gen_rtx_REG (mode, gregno);
a6c9bed4 4852 else
b78d48dd 4853 return NULL_RTX;
a6c9bed4
AH
4854 }
4855}
4856
0b5383eb
DJ
4857/* A subroutine of rs6000_darwin64_record_arg. Assign the bits of the
4858 structure between cum->intoffset and bitpos to integer registers. */
594a51fe 4859
0b5383eb 4860static void
bb8df8a6 4861rs6000_darwin64_record_arg_flush (CUMULATIVE_ARGS *cum,
0b5383eb 4862 HOST_WIDE_INT bitpos, rtx rvec[], int *k)
594a51fe 4863{
0b5383eb
DJ
4864 enum machine_mode mode;
4865 unsigned int regno;
4866 unsigned int startbit, endbit;
4867 int this_regno, intregs, intoffset;
4868 rtx reg;
594a51fe 4869
0b5383eb
DJ
4870 if (cum->intoffset == -1)
4871 return;
4872
4873 intoffset = cum->intoffset;
4874 cum->intoffset = -1;
4875
4876 /* If this is the trailing part of a word, try to only load that
4877 much into the register. Otherwise load the whole register. Note
4878 that in the latter case we may pick up unwanted bits. It's not a
4879 problem at the moment but may wish to revisit. */
4880
4881 if (intoffset % BITS_PER_WORD != 0)
594a51fe 4882 {
0b5383eb
DJ
4883 mode = mode_for_size (BITS_PER_WORD - intoffset % BITS_PER_WORD,
4884 MODE_INT, 0);
4885 if (mode == BLKmode)
4886 {
4887 /* We couldn't find an appropriate mode, which happens,
4888 e.g., in packed structs when there are 3 bytes to load.
4889 Back intoffset back to the beginning of the word in this
4890 case. */
4891 intoffset = intoffset & -BITS_PER_WORD;
4892 mode = word_mode;
4893 }
4894 }
4895 else
4896 mode = word_mode;
4897
4898 startbit = intoffset & -BITS_PER_WORD;
4899 endbit = (bitpos + BITS_PER_WORD - 1) & -BITS_PER_WORD;
4900 intregs = (endbit - startbit) / BITS_PER_WORD;
4901 this_regno = cum->words + intoffset / BITS_PER_WORD;
4902
4903 if (intregs > 0 && intregs > GP_ARG_NUM_REG - this_regno)
4904 cum->use_stack = 1;
bb8df8a6 4905
0b5383eb
DJ
4906 intregs = MIN (intregs, GP_ARG_NUM_REG - this_regno);
4907 if (intregs <= 0)
4908 return;
4909
4910 intoffset /= BITS_PER_UNIT;
4911 do
4912 {
4913 regno = GP_ARG_MIN_REG + this_regno;
4914 reg = gen_rtx_REG (mode, regno);
4915 rvec[(*k)++] =
4916 gen_rtx_EXPR_LIST (VOIDmode, reg, GEN_INT (intoffset));
4917
4918 this_regno += 1;
4919 intoffset = (intoffset | (UNITS_PER_WORD-1)) + 1;
4920 mode = word_mode;
4921 intregs -= 1;
4922 }
4923 while (intregs > 0);
4924}
4925
4926/* Recursive workhorse for the following. */
4927
4928static void
bb8df8a6 4929rs6000_darwin64_record_arg_recurse (CUMULATIVE_ARGS *cum, tree type,
0b5383eb
DJ
4930 HOST_WIDE_INT startbitpos, rtx rvec[],
4931 int *k)
4932{
4933 tree f;
4934
4935 for (f = TYPE_FIELDS (type); f ; f = TREE_CHAIN (f))
4936 if (TREE_CODE (f) == FIELD_DECL)
4937 {
4938 HOST_WIDE_INT bitpos = startbitpos;
4939 tree ftype = TREE_TYPE (f);
4940 enum machine_mode mode = TYPE_MODE (ftype);
4941
4942 if (DECL_SIZE (f) != 0
4943 && host_integerp (bit_position (f), 1))
4944 bitpos += int_bit_position (f);
4945
4946 /* ??? FIXME: else assume zero offset. */
4947
4948 if (TREE_CODE (ftype) == RECORD_TYPE)
4949 rs6000_darwin64_record_arg_recurse (cum, ftype, bitpos, rvec, k);
4950 else if (cum->named && USE_FP_FOR_ARG_P (cum, mode, ftype))
594a51fe 4951 {
0b5383eb
DJ
4952#if 0
4953 switch (mode)
594a51fe 4954 {
0b5383eb
DJ
4955 case SCmode: mode = SFmode; break;
4956 case DCmode: mode = DFmode; break;
4957 case TCmode: mode = TFmode; break;
4958 default: break;
594a51fe 4959 }
0b5383eb
DJ
4960#endif
4961 rs6000_darwin64_record_arg_flush (cum, bitpos, rvec, k);
4962 rvec[(*k)++]
bb8df8a6 4963 = gen_rtx_EXPR_LIST (VOIDmode,
0b5383eb
DJ
4964 gen_rtx_REG (mode, cum->fregno++),
4965 GEN_INT (bitpos / BITS_PER_UNIT));
4966 if (mode == TFmode)
4967 cum->fregno++;
594a51fe 4968 }
0b5383eb
DJ
4969 else if (cum->named && USE_ALTIVEC_FOR_ARG_P (cum, mode, ftype, 1))
4970 {
4971 rs6000_darwin64_record_arg_flush (cum, bitpos, rvec, k);
4972 rvec[(*k)++]
bb8df8a6
EC
4973 = gen_rtx_EXPR_LIST (VOIDmode,
4974 gen_rtx_REG (mode, cum->vregno++),
0b5383eb
DJ
4975 GEN_INT (bitpos / BITS_PER_UNIT));
4976 }
4977 else if (cum->intoffset == -1)
4978 cum->intoffset = bitpos;
4979 }
4980}
594a51fe 4981
0b5383eb
DJ
4982/* For the darwin64 ABI, we want to construct a PARALLEL consisting of
4983 the register(s) to be used for each field and subfield of a struct
4984 being passed by value, along with the offset of where the
4985 register's value may be found in the block. FP fields go in FP
4986 register, vector fields go in vector registers, and everything
bb8df8a6 4987 else goes in int registers, packed as in memory.
8ff40a74 4988
0b5383eb
DJ
4989 This code is also used for function return values. RETVAL indicates
4990 whether this is the case.
8ff40a74 4991
a4d05547 4992 Much of this is taken from the SPARC V9 port, which has a similar
0b5383eb 4993 calling convention. */
594a51fe 4994
0b5383eb
DJ
4995static rtx
4996rs6000_darwin64_record_arg (CUMULATIVE_ARGS *orig_cum, tree type,
4997 int named, bool retval)
4998{
4999 rtx rvec[FIRST_PSEUDO_REGISTER];
5000 int k = 1, kbase = 1;
5001 HOST_WIDE_INT typesize = int_size_in_bytes (type);
5002 /* This is a copy; modifications are not visible to our caller. */
5003 CUMULATIVE_ARGS copy_cum = *orig_cum;
5004 CUMULATIVE_ARGS *cum = &copy_cum;
5005
5006 /* Pad to 16 byte boundary if needed. */
5007 if (!retval && TYPE_ALIGN (type) >= 2 * BITS_PER_WORD
5008 && (cum->words % 2) != 0)
5009 cum->words++;
5010
5011 cum->intoffset = 0;
5012 cum->use_stack = 0;
5013 cum->named = named;
5014
5015 /* Put entries into rvec[] for individual FP and vector fields, and
5016 for the chunks of memory that go in int regs. Note we start at
5017 element 1; 0 is reserved for an indication of using memory, and
5018 may or may not be filled in below. */
5019 rs6000_darwin64_record_arg_recurse (cum, type, 0, rvec, &k);
5020 rs6000_darwin64_record_arg_flush (cum, typesize * BITS_PER_UNIT, rvec, &k);
5021
5022 /* If any part of the struct went on the stack put all of it there.
5023 This hack is because the generic code for
5024 FUNCTION_ARG_PARTIAL_NREGS cannot handle cases where the register
5025 parts of the struct are not at the beginning. */
5026 if (cum->use_stack)
5027 {
5028 if (retval)
5029 return NULL_RTX; /* doesn't go in registers at all */
5030 kbase = 0;
5031 rvec[0] = gen_rtx_EXPR_LIST (VOIDmode, NULL_RTX, const0_rtx);
5032 }
5033 if (k > 1 || cum->use_stack)
5034 return gen_rtx_PARALLEL (BLKmode, gen_rtvec_v (k - kbase, &rvec[kbase]));
594a51fe
SS
5035 else
5036 return NULL_RTX;
5037}
5038
b78d48dd
FJ
5039/* Determine where to place an argument in 64-bit mode with 32-bit ABI. */
5040
5041static rtx
ec6376ab 5042rs6000_mixed_function_arg (enum machine_mode mode, tree type, int align_words)
b78d48dd 5043{
ec6376ab
AM
5044 int n_units;
5045 int i, k;
5046 rtx rvec[GP_ARG_NUM_REG + 1];
5047
5048 if (align_words >= GP_ARG_NUM_REG)
5049 return NULL_RTX;
5050
5051 n_units = rs6000_arg_size (mode, type);
5052
5053 /* Optimize the simple case where the arg fits in one gpr, except in
5054 the case of BLKmode due to assign_parms assuming that registers are
5055 BITS_PER_WORD wide. */
5056 if (n_units == 0
5057 || (n_units == 1 && mode != BLKmode))
5058 return gen_rtx_REG (mode, GP_ARG_MIN_REG + align_words);
5059
5060 k = 0;
5061 if (align_words + n_units > GP_ARG_NUM_REG)
5062 /* Not all of the arg fits in gprs. Say that it goes in memory too,
5063 using a magic NULL_RTX component.
79773478
AM
5064 This is not strictly correct. Only some of the arg belongs in
5065 memory, not all of it. However, the normal scheme using
5066 function_arg_partial_nregs can result in unusual subregs, eg.
5067 (subreg:SI (reg:DF) 4), which are not handled well. The code to
5068 store the whole arg to memory is often more efficient than code
5069 to store pieces, and we know that space is available in the right
5070 place for the whole arg. */
ec6376ab
AM
5071 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, NULL_RTX, const0_rtx);
5072
5073 i = 0;
5074 do
36a454e1 5075 {
ec6376ab
AM
5076 rtx r = gen_rtx_REG (SImode, GP_ARG_MIN_REG + align_words);
5077 rtx off = GEN_INT (i++ * 4);
5078 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, r, off);
36a454e1 5079 }
ec6376ab
AM
5080 while (++align_words < GP_ARG_NUM_REG && --n_units != 0);
5081
5082 return gen_rtx_PARALLEL (mode, gen_rtvec_v (k, rvec));
b78d48dd
FJ
5083}
5084
4697a36c
MM
5085/* Determine where to put an argument to a function.
5086 Value is zero to push the argument on the stack,
5087 or a hard register in which to store the argument.
5088
5089 MODE is the argument's machine mode.
5090 TYPE is the data type of the argument (as a tree).
5091 This is null for libcalls where that information may
5092 not be available.
5093 CUM is a variable of type CUMULATIVE_ARGS which gives info about
0b5383eb
DJ
5094 the preceding args and about the function being called. It is
5095 not modified in this routine.
4697a36c
MM
5096 NAMED is nonzero if this argument is a named parameter
5097 (otherwise it is an extra parameter matching an ellipsis).
5098
5099 On RS/6000 the first eight words of non-FP are normally in registers
5100 and the rest are pushed. Under AIX, the first 13 FP args are in registers.
5101 Under V.4, the first 8 FP args are in registers.
5102
5103 If this is floating-point and no prototype is specified, we use
5104 both an FP and integer register (or possibly FP reg and stack). Library
b9599e46 5105 functions (when CALL_LIBCALL is set) always have the proper types for args,
4697a36c 5106 so we can pass the FP value just in one register. emit_library_function
b2d04ecf
AM
5107 doesn't support PARALLEL anyway.
5108
5109 Note that for args passed by reference, function_arg will be called
5110 with MODE and TYPE set to that of the pointer to the arg, not the arg
5111 itself. */
4697a36c 5112
9390387d 5113rtx
f676971a 5114function_arg (CUMULATIVE_ARGS *cum, enum machine_mode mode,
a2369ed3 5115 tree type, int named)
4697a36c 5116{
4cc833b7 5117 enum rs6000_abi abi = DEFAULT_ABI;
4697a36c 5118
a4f6c312
SS
5119 /* Return a marker to indicate whether CR1 needs to set or clear the
5120 bit that V.4 uses to say fp args were passed in registers.
5121 Assume that we don't need the marker for software floating point,
5122 or compiler generated library calls. */
4697a36c
MM
5123 if (mode == VOIDmode)
5124 {
f607bc57 5125 if (abi == ABI_V4
b9599e46 5126 && (cum->call_cookie & CALL_LIBCALL) == 0
c1fa753e
AM
5127 && (cum->stdarg
5128 || (cum->nargs_prototype < 0
5129 && (cum->prototype || TARGET_NO_PROTOTYPE))))
7509c759 5130 {
a3170dc6
AH
5131 /* For the SPE, we need to crxor CR6 always. */
5132 if (TARGET_SPE_ABI)
5133 return GEN_INT (cum->call_cookie | CALL_V4_SET_FP_ARGS);
5134 else if (TARGET_HARD_FLOAT && TARGET_FPRS)
5135 return GEN_INT (cum->call_cookie
5136 | ((cum->fregno == FP_ARG_MIN_REG)
5137 ? CALL_V4_SET_FP_ARGS
5138 : CALL_V4_CLEAR_FP_ARGS));
7509c759 5139 }
4697a36c 5140
7509c759 5141 return GEN_INT (cum->call_cookie);
4697a36c
MM
5142 }
5143
0b5383eb
DJ
5144 if (rs6000_darwin64_abi && mode == BLKmode
5145 && TREE_CODE (type) == RECORD_TYPE)
8ff40a74 5146 {
0b5383eb 5147 rtx rslt = rs6000_darwin64_record_arg (cum, type, named, false);
8ff40a74
SS
5148 if (rslt != NULL_RTX)
5149 return rslt;
5150 /* Else fall through to usual handling. */
5151 }
5152
2858f73a 5153 if (USE_ALTIVEC_FOR_ARG_P (cum, mode, type, named))
c72d6c26
HP
5154 if (TARGET_64BIT && ! cum->prototype)
5155 {
c4ad648e
AM
5156 /* Vector parameters get passed in vector register
5157 and also in GPRs or memory, in absence of prototype. */
5158 int align_words;
5159 rtx slot;
5160 align_words = (cum->words + 1) & ~1;
5161
5162 if (align_words >= GP_ARG_NUM_REG)
5163 {
5164 slot = NULL_RTX;
5165 }
5166 else
5167 {
5168 slot = gen_rtx_REG (mode, GP_ARG_MIN_REG + align_words);
5169 }
5170 return gen_rtx_PARALLEL (mode,
5171 gen_rtvec (2,
5172 gen_rtx_EXPR_LIST (VOIDmode,
5173 slot, const0_rtx),
5174 gen_rtx_EXPR_LIST (VOIDmode,
5175 gen_rtx_REG (mode, cum->vregno),
5176 const0_rtx)));
c72d6c26
HP
5177 }
5178 else
5179 return gen_rtx_REG (mode, cum->vregno);
ad630bef
DE
5180 else if (TARGET_ALTIVEC_ABI
5181 && (ALTIVEC_VECTOR_MODE (mode)
5182 || (type && TREE_CODE (type) == VECTOR_TYPE
5183 && int_size_in_bytes (type) == 16)))
0ac081f6 5184 {
2858f73a 5185 if (named || abi == ABI_V4)
a594a19c 5186 return NULL_RTX;
0ac081f6 5187 else
a594a19c
GK
5188 {
5189 /* Vector parameters to varargs functions under AIX or Darwin
5190 get passed in memory and possibly also in GPRs. */
ec6376ab
AM
5191 int align, align_words, n_words;
5192 enum machine_mode part_mode;
a594a19c
GK
5193
5194 /* Vector parameters must be 16-byte aligned. This places them at
2858f73a
GK
5195 2 mod 4 in terms of words in 32-bit mode, since the parameter
5196 save area starts at offset 24 from the stack. In 64-bit mode,
5197 they just have to start on an even word, since the parameter
5198 save area is 16-byte aligned. */
5199 if (TARGET_32BIT)
4ed78545 5200 align = (2 - cum->words) & 3;
2858f73a
GK
5201 else
5202 align = cum->words & 1;
a594a19c
GK
5203 align_words = cum->words + align;
5204
5205 /* Out of registers? Memory, then. */
5206 if (align_words >= GP_ARG_NUM_REG)
5207 return NULL_RTX;
ec6376ab
AM
5208
5209 if (TARGET_32BIT && TARGET_POWERPC64)
5210 return rs6000_mixed_function_arg (mode, type, align_words);
5211
2858f73a
GK
5212 /* The vector value goes in GPRs. Only the part of the
5213 value in GPRs is reported here. */
ec6376ab
AM
5214 part_mode = mode;
5215 n_words = rs6000_arg_size (mode, type);
5216 if (align_words + n_words > GP_ARG_NUM_REG)
839a4992 5217 /* Fortunately, there are only two possibilities, the value
2858f73a
GK
5218 is either wholly in GPRs or half in GPRs and half not. */
5219 part_mode = DImode;
ec6376ab
AM
5220
5221 return gen_rtx_REG (part_mode, GP_ARG_MIN_REG + align_words);
a594a19c 5222 }
0ac081f6 5223 }
f82f556d
AH
5224 else if (TARGET_SPE_ABI && TARGET_SPE
5225 && (SPE_VECTOR_MODE (mode)
18f63bfa
AH
5226 || (TARGET_E500_DOUBLE && (mode == DFmode
5227 || mode == DCmode))))
a6c9bed4 5228 return rs6000_spe_function_arg (cum, mode, type);
594a51fe 5229
f607bc57 5230 else if (abi == ABI_V4)
4697a36c 5231 {
a3170dc6 5232 if (TARGET_HARD_FLOAT && TARGET_FPRS
602ea4d3
JJ
5233 && (mode == SFmode || mode == DFmode
5234 || (mode == TFmode && !TARGET_IEEEQUAD)))
4cc833b7 5235 {
602ea4d3 5236 if (cum->fregno + (mode == TFmode ? 1 : 0) <= FP_ARG_V4_MAX_REG)
4cc833b7
RH
5237 return gen_rtx_REG (mode, cum->fregno);
5238 else
b78d48dd 5239 return NULL_RTX;
4cc833b7
RH
5240 }
5241 else
5242 {
b2d04ecf 5243 int n_words = rs6000_arg_size (mode, type);
4cc833b7
RH
5244 int gregno = cum->sysv_gregno;
5245
4ed78545
AM
5246 /* Long long and SPE vectors are put in (r3,r4), (r5,r6),
5247 (r7,r8) or (r9,r10). As does any other 2 word item such
5248 as complex int due to a historical mistake. */
5249 if (n_words == 2)
5250 gregno += (1 - gregno) & 1;
4cc833b7 5251
4ed78545 5252 /* Multi-reg args are not split between registers and stack. */
ec6376ab 5253 if (gregno + n_words - 1 > GP_ARG_MAX_REG)
b78d48dd 5254 return NULL_RTX;
ec6376ab
AM
5255
5256 if (TARGET_32BIT && TARGET_POWERPC64)
5257 return rs6000_mixed_function_arg (mode, type,
5258 gregno - GP_ARG_MIN_REG);
5259 return gen_rtx_REG (mode, gregno);
4cc833b7 5260 }
4697a36c 5261 }
4cc833b7
RH
5262 else
5263 {
294bd182 5264 int align_words = rs6000_parm_start (mode, type, cum->words);
b78d48dd 5265
2858f73a 5266 if (USE_FP_FOR_ARG_P (cum, mode, type))
4cc833b7 5267 {
ec6376ab
AM
5268 rtx rvec[GP_ARG_NUM_REG + 1];
5269 rtx r;
5270 int k;
c53bdcf5
AM
5271 bool needs_psave;
5272 enum machine_mode fmode = mode;
c53bdcf5
AM
5273 unsigned long n_fpreg = (GET_MODE_SIZE (mode) + 7) >> 3;
5274
5275 if (cum->fregno + n_fpreg > FP_ARG_MAX_REG + 1)
5276 {
c53bdcf5
AM
5277 /* Currently, we only ever need one reg here because complex
5278 doubles are split. */
37409796 5279 gcc_assert (cum->fregno == FP_ARG_MAX_REG && fmode == TFmode);
ec6376ab
AM
5280
5281 /* Long double split over regs and memory. */
5282 fmode = DFmode;
c53bdcf5 5283 }
c53bdcf5
AM
5284
5285 /* Do we also need to pass this arg in the parameter save
5286 area? */
5287 needs_psave = (type
5288 && (cum->nargs_prototype <= 0
5289 || (DEFAULT_ABI == ABI_AIX
de17c25f 5290 && TARGET_XL_COMPAT
c53bdcf5
AM
5291 && align_words >= GP_ARG_NUM_REG)));
5292
5293 if (!needs_psave && mode == fmode)
ec6376ab 5294 return gen_rtx_REG (fmode, cum->fregno);
c53bdcf5 5295
ec6376ab 5296 k = 0;
c53bdcf5
AM
5297 if (needs_psave)
5298 {
ec6376ab 5299 /* Describe the part that goes in gprs or the stack.
c53bdcf5 5300 This piece must come first, before the fprs. */
c53bdcf5
AM
5301 if (align_words < GP_ARG_NUM_REG)
5302 {
5303 unsigned long n_words = rs6000_arg_size (mode, type);
ec6376ab
AM
5304
5305 if (align_words + n_words > GP_ARG_NUM_REG
5306 || (TARGET_32BIT && TARGET_POWERPC64))
5307 {
5308 /* If this is partially on the stack, then we only
5309 include the portion actually in registers here. */
5310 enum machine_mode rmode = TARGET_32BIT ? SImode : DImode;
5311 rtx off;
79773478
AM
5312 int i = 0;
5313 if (align_words + n_words > GP_ARG_NUM_REG)
c4ad648e
AM
5314 /* Not all of the arg fits in gprs. Say that it
5315 goes in memory too, using a magic NULL_RTX
5316 component. Also see comment in
5317 rs6000_mixed_function_arg for why the normal
5318 function_arg_partial_nregs scheme doesn't work
5319 in this case. */
5320 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, NULL_RTX,
5321 const0_rtx);
ec6376ab
AM
5322 do
5323 {
5324 r = gen_rtx_REG (rmode,
5325 GP_ARG_MIN_REG + align_words);
2e6c9641 5326 off = GEN_INT (i++ * GET_MODE_SIZE (rmode));
ec6376ab
AM
5327 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, r, off);
5328 }
5329 while (++align_words < GP_ARG_NUM_REG && --n_words != 0);
5330 }
5331 else
5332 {
5333 /* The whole arg fits in gprs. */
5334 r = gen_rtx_REG (mode, GP_ARG_MIN_REG + align_words);
5335 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, r, const0_rtx);
5336 }
c53bdcf5 5337 }
ec6376ab
AM
5338 else
5339 /* It's entirely in memory. */
5340 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, NULL_RTX, const0_rtx);
c53bdcf5
AM
5341 }
5342
ec6376ab
AM
5343 /* Describe where this piece goes in the fprs. */
5344 r = gen_rtx_REG (fmode, cum->fregno);
5345 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, r, const0_rtx);
5346
5347 return gen_rtx_PARALLEL (mode, gen_rtvec_v (k, rvec));
4cc833b7
RH
5348 }
5349 else if (align_words < GP_ARG_NUM_REG)
b2d04ecf 5350 {
ec6376ab
AM
5351 if (TARGET_32BIT && TARGET_POWERPC64)
5352 return rs6000_mixed_function_arg (mode, type, align_words);
b2d04ecf 5353
4eeca74f
AM
5354 if (mode == BLKmode)
5355 mode = Pmode;
5356
b2d04ecf
AM
5357 return gen_rtx_REG (mode, GP_ARG_MIN_REG + align_words);
5358 }
4cc833b7
RH
5359 else
5360 return NULL_RTX;
4697a36c 5361 }
4697a36c
MM
5362}
5363\f
ec6376ab 5364/* For an arg passed partly in registers and partly in memory, this is
fb63c729
AM
5365 the number of bytes passed in registers. For args passed entirely in
5366 registers or entirely in memory, zero. When an arg is described by a
5367 PARALLEL, perhaps using more than one register type, this function
5368 returns the number of bytes used by the first element of the PARALLEL. */
4697a36c 5369
78a52f11
RH
5370static int
5371rs6000_arg_partial_bytes (CUMULATIVE_ARGS *cum, enum machine_mode mode,
5372 tree type, bool named)
4697a36c 5373{
c53bdcf5 5374 int ret = 0;
ec6376ab 5375 int align_words;
c53bdcf5 5376
f607bc57 5377 if (DEFAULT_ABI == ABI_V4)
4697a36c 5378 return 0;
4697a36c 5379
c53bdcf5
AM
5380 if (USE_ALTIVEC_FOR_ARG_P (cum, mode, type, named)
5381 && cum->nargs_prototype >= 0)
5382 return 0;
5383
0b5383eb
DJ
5384 /* In this complicated case we just disable the partial_nregs code. */
5385 if (rs6000_darwin64_abi && mode == BLKmode
5386 && TREE_CODE (type) == RECORD_TYPE
5387 && int_size_in_bytes (type) > 0)
5388 return 0;
5389
294bd182 5390 align_words = rs6000_parm_start (mode, type, cum->words);
ec6376ab 5391
79773478
AM
5392 if (USE_FP_FOR_ARG_P (cum, mode, type))
5393 {
fb63c729
AM
5394 /* If we are passing this arg in the fixed parameter save area
5395 (gprs or memory) as well as fprs, then this function should
79773478
AM
5396 return the number of partial bytes passed in the parameter
5397 save area rather than partial bytes passed in fprs. */
5398 if (type
5399 && (cum->nargs_prototype <= 0
5400 || (DEFAULT_ABI == ABI_AIX
5401 && TARGET_XL_COMPAT
5402 && align_words >= GP_ARG_NUM_REG)))
5403 return 0;
5404 else if (cum->fregno + ((GET_MODE_SIZE (mode) + 7) >> 3)
5405 > FP_ARG_MAX_REG + 1)
ac7e839c 5406 ret = (FP_ARG_MAX_REG + 1 - cum->fregno) * 8;
c53bdcf5 5407 else if (cum->nargs_prototype >= 0)
4697a36c
MM
5408 return 0;
5409 }
5410
ec6376ab
AM
5411 if (align_words < GP_ARG_NUM_REG
5412 && GP_ARG_NUM_REG < align_words + rs6000_arg_size (mode, type))
ac7e839c 5413 ret = (GP_ARG_NUM_REG - align_words) * (TARGET_32BIT ? 4 : 8);
78a52f11 5414
c53bdcf5 5415 if (ret != 0 && TARGET_DEBUG_ARG)
78a52f11 5416 fprintf (stderr, "rs6000_arg_partial_bytes: %d\n", ret);
4697a36c 5417
c53bdcf5 5418 return ret;
4697a36c
MM
5419}
5420\f
5421/* A C expression that indicates when an argument must be passed by
5422 reference. If nonzero for an argument, a copy of that argument is
5423 made in memory and a pointer to the argument is passed instead of
5424 the argument itself. The pointer is passed in whatever way is
5425 appropriate for passing a pointer to that type.
5426
b2d04ecf
AM
5427 Under V.4, aggregates and long double are passed by reference.
5428
5429 As an extension to all 32-bit ABIs, AltiVec vectors are passed by
5430 reference unless the AltiVec vector extension ABI is in force.
c8c99a68
DE
5431
5432 As an extension to all ABIs, variable sized types are passed by
5433 reference. */
4697a36c 5434
8cd5a4e0 5435static bool
f676971a 5436rs6000_pass_by_reference (CUMULATIVE_ARGS *cum ATTRIBUTE_UNUSED,
bada2eb8
DE
5437 enum machine_mode mode, tree type,
5438 bool named ATTRIBUTE_UNUSED)
4697a36c 5439{
602ea4d3 5440 if (DEFAULT_ABI == ABI_V4 && TARGET_IEEEQUAD && mode == TFmode)
4697a36c
MM
5441 {
5442 if (TARGET_DEBUG_ARG)
bada2eb8
DE
5443 fprintf (stderr, "function_arg_pass_by_reference: V4 long double\n");
5444 return 1;
5445 }
5446
5447 if (!type)
5448 return 0;
4697a36c 5449
bada2eb8
DE
5450 if (DEFAULT_ABI == ABI_V4 && AGGREGATE_TYPE_P (type))
5451 {
5452 if (TARGET_DEBUG_ARG)
5453 fprintf (stderr, "function_arg_pass_by_reference: V4 aggregate\n");
5454 return 1;
5455 }
5456
5457 if (int_size_in_bytes (type) < 0)
5458 {
5459 if (TARGET_DEBUG_ARG)
5460 fprintf (stderr, "function_arg_pass_by_reference: variable size\n");
5461 return 1;
5462 }
5463
5464 /* Allow -maltivec -mabi=no-altivec without warning. Altivec vector
5465 modes only exist for GCC vector types if -maltivec. */
5466 if (TARGET_32BIT && !TARGET_ALTIVEC_ABI && ALTIVEC_VECTOR_MODE (mode))
5467 {
5468 if (TARGET_DEBUG_ARG)
5469 fprintf (stderr, "function_arg_pass_by_reference: AltiVec\n");
4697a36c
MM
5470 return 1;
5471 }
b693336b
PB
5472
5473 /* Pass synthetic vectors in memory. */
bada2eb8 5474 if (TREE_CODE (type) == VECTOR_TYPE
ad630bef 5475 && int_size_in_bytes (type) > (TARGET_ALTIVEC_ABI ? 16 : 8))
b693336b
PB
5476 {
5477 static bool warned_for_pass_big_vectors = false;
5478 if (TARGET_DEBUG_ARG)
5479 fprintf (stderr, "function_arg_pass_by_reference: synthetic vector\n");
5480 if (!warned_for_pass_big_vectors)
5481 {
d4ee4d25 5482 warning (0, "GCC vector passed by reference: "
b693336b
PB
5483 "non-standard ABI extension with no compatibility guarantee");
5484 warned_for_pass_big_vectors = true;
5485 }
5486 return 1;
5487 }
5488
b2d04ecf 5489 return 0;
4697a36c 5490}
5985c7a6
FJ
5491
5492static void
2d9db8eb 5493rs6000_move_block_from_reg (int regno, rtx x, int nregs)
5985c7a6
FJ
5494{
5495 int i;
5496 enum machine_mode reg_mode = TARGET_32BIT ? SImode : DImode;
5497
5498 if (nregs == 0)
5499 return;
5500
c4ad648e 5501 for (i = 0; i < nregs; i++)
5985c7a6 5502 {
9390387d 5503 rtx tem = adjust_address_nv (x, reg_mode, i * GET_MODE_SIZE (reg_mode));
5985c7a6 5504 if (reload_completed)
c4ad648e
AM
5505 {
5506 if (! strict_memory_address_p (reg_mode, XEXP (tem, 0)))
5507 tem = NULL_RTX;
5508 else
5509 tem = simplify_gen_subreg (reg_mode, x, BLKmode,
9390387d 5510 i * GET_MODE_SIZE (reg_mode));
c4ad648e 5511 }
5985c7a6
FJ
5512 else
5513 tem = replace_equiv_address (tem, XEXP (tem, 0));
5514
37409796 5515 gcc_assert (tem);
5985c7a6
FJ
5516
5517 emit_move_insn (tem, gen_rtx_REG (reg_mode, regno + i));
5518 }
5519}
4697a36c
MM
5520\f
5521/* Perform any needed actions needed for a function that is receiving a
f676971a 5522 variable number of arguments.
4697a36c
MM
5523
5524 CUM is as above.
5525
5526 MODE and TYPE are the mode and type of the current parameter.
5527
5528 PRETEND_SIZE is a variable that should be set to the amount of stack
5529 that must be pushed by the prolog to pretend that our caller pushed
5530 it.
5531
5532 Normally, this macro will push all remaining incoming registers on the
5533 stack and set PRETEND_SIZE to the length of the registers pushed. */
5534
c6e8c921 5535static void
f676971a 5536setup_incoming_varargs (CUMULATIVE_ARGS *cum, enum machine_mode mode,
c4ad648e
AM
5537 tree type, int *pretend_size ATTRIBUTE_UNUSED,
5538 int no_rtl)
4697a36c 5539{
4cc833b7
RH
5540 CUMULATIVE_ARGS next_cum;
5541 int reg_size = TARGET_32BIT ? 4 : 8;
ca5adc63 5542 rtx save_area = NULL_RTX, mem;
dfafc897 5543 int first_reg_offset, set;
4697a36c 5544
f31bf321 5545 /* Skip the last named argument. */
d34c5b80 5546 next_cum = *cum;
594a51fe 5547 function_arg_advance (&next_cum, mode, type, 1, 0);
4cc833b7 5548
f607bc57 5549 if (DEFAULT_ABI == ABI_V4)
d34c5b80 5550 {
5b667039
JJ
5551 first_reg_offset = next_cum.sysv_gregno - GP_ARG_MIN_REG;
5552
60e2d0ca 5553 if (! no_rtl)
5b667039
JJ
5554 {
5555 int gpr_reg_num = 0, gpr_size = 0, fpr_size = 0;
5556 HOST_WIDE_INT offset = 0;
5557
5558 /* Try to optimize the size of the varargs save area.
5559 The ABI requires that ap.reg_save_area is doubleword
5560 aligned, but we don't need to allocate space for all
5561 the bytes, only those to which we actually will save
5562 anything. */
5563 if (cfun->va_list_gpr_size && first_reg_offset < GP_ARG_NUM_REG)
5564 gpr_reg_num = GP_ARG_NUM_REG - first_reg_offset;
5565 if (TARGET_HARD_FLOAT && TARGET_FPRS
5566 && next_cum.fregno <= FP_ARG_V4_MAX_REG
5567 && cfun->va_list_fpr_size)
5568 {
5569 if (gpr_reg_num)
5570 fpr_size = (next_cum.fregno - FP_ARG_MIN_REG)
5571 * UNITS_PER_FP_WORD;
5572 if (cfun->va_list_fpr_size
5573 < FP_ARG_V4_MAX_REG + 1 - next_cum.fregno)
5574 fpr_size += cfun->va_list_fpr_size * UNITS_PER_FP_WORD;
5575 else
5576 fpr_size += (FP_ARG_V4_MAX_REG + 1 - next_cum.fregno)
5577 * UNITS_PER_FP_WORD;
5578 }
5579 if (gpr_reg_num)
5580 {
5581 offset = -((first_reg_offset * reg_size) & ~7);
5582 if (!fpr_size && gpr_reg_num > cfun->va_list_gpr_size)
5583 {
5584 gpr_reg_num = cfun->va_list_gpr_size;
5585 if (reg_size == 4 && (first_reg_offset & 1))
5586 gpr_reg_num++;
5587 }
5588 gpr_size = (gpr_reg_num * reg_size + 7) & ~7;
5589 }
5590 else if (fpr_size)
5591 offset = - (int) (next_cum.fregno - FP_ARG_MIN_REG)
5592 * UNITS_PER_FP_WORD
5593 - (int) (GP_ARG_NUM_REG * reg_size);
4cc833b7 5594
5b667039
JJ
5595 if (gpr_size + fpr_size)
5596 {
5597 rtx reg_save_area
5598 = assign_stack_local (BLKmode, gpr_size + fpr_size, 64);
5599 gcc_assert (GET_CODE (reg_save_area) == MEM);
5600 reg_save_area = XEXP (reg_save_area, 0);
5601 if (GET_CODE (reg_save_area) == PLUS)
5602 {
5603 gcc_assert (XEXP (reg_save_area, 0)
5604 == virtual_stack_vars_rtx);
5605 gcc_assert (GET_CODE (XEXP (reg_save_area, 1)) == CONST_INT);
5606 offset += INTVAL (XEXP (reg_save_area, 1));
5607 }
5608 else
5609 gcc_assert (reg_save_area == virtual_stack_vars_rtx);
5610 }
5611
5612 cfun->machine->varargs_save_offset = offset;
5613 save_area = plus_constant (virtual_stack_vars_rtx, offset);
5614 }
4697a36c 5615 }
60e2d0ca 5616 else
4697a36c 5617 {
d34c5b80 5618 first_reg_offset = next_cum.words;
4cc833b7 5619 save_area = virtual_incoming_args_rtx;
4697a36c 5620
fe984136 5621 if (targetm.calls.must_pass_in_stack (mode, type))
c53bdcf5 5622 first_reg_offset += rs6000_arg_size (TYPE_MODE (type), type);
4cc833b7 5623 }
4697a36c 5624
dfafc897 5625 set = get_varargs_alias_set ();
9d30f3c1
JJ
5626 if (! no_rtl && first_reg_offset < GP_ARG_NUM_REG
5627 && cfun->va_list_gpr_size)
4cc833b7 5628 {
9d30f3c1
JJ
5629 int nregs = GP_ARG_NUM_REG - first_reg_offset;
5630
5631 if (va_list_gpr_counter_field)
5632 {
5633 /* V4 va_list_gpr_size counts number of registers needed. */
5634 if (nregs > cfun->va_list_gpr_size)
5635 nregs = cfun->va_list_gpr_size;
5636 }
5637 else
5638 {
5639 /* char * va_list instead counts number of bytes needed. */
5640 if (nregs > cfun->va_list_gpr_size / reg_size)
5641 nregs = cfun->va_list_gpr_size / reg_size;
5642 }
5643
dfafc897 5644 mem = gen_rtx_MEM (BLKmode,
c4ad648e 5645 plus_constant (save_area,
13e2e16e
DE
5646 first_reg_offset * reg_size));
5647 MEM_NOTRAP_P (mem) = 1;
ba4828e0 5648 set_mem_alias_set (mem, set);
8ac61af7 5649 set_mem_align (mem, BITS_PER_WORD);
dfafc897 5650
f676971a 5651 rs6000_move_block_from_reg (GP_ARG_MIN_REG + first_reg_offset, mem,
9d30f3c1 5652 nregs);
4697a36c
MM
5653 }
5654
4697a36c 5655 /* Save FP registers if needed. */
f607bc57 5656 if (DEFAULT_ABI == ABI_V4
a3170dc6
AH
5657 && TARGET_HARD_FLOAT && TARGET_FPRS
5658 && ! no_rtl
9d30f3c1
JJ
5659 && next_cum.fregno <= FP_ARG_V4_MAX_REG
5660 && cfun->va_list_fpr_size)
4697a36c 5661 {
9d30f3c1 5662 int fregno = next_cum.fregno, nregs;
9ebbca7d 5663 rtx cr1 = gen_rtx_REG (CCmode, CR1_REGNO);
4cc833b7 5664 rtx lab = gen_label_rtx ();
5b667039
JJ
5665 int off = (GP_ARG_NUM_REG * reg_size) + ((fregno - FP_ARG_MIN_REG)
5666 * UNITS_PER_FP_WORD);
4697a36c 5667
c4ad648e
AM
5668 emit_jump_insn
5669 (gen_rtx_SET (VOIDmode,
5670 pc_rtx,
5671 gen_rtx_IF_THEN_ELSE (VOIDmode,
4cc833b7 5672 gen_rtx_NE (VOIDmode, cr1,
c4ad648e 5673 const0_rtx),
39403d82 5674 gen_rtx_LABEL_REF (VOIDmode, lab),
4697a36c
MM
5675 pc_rtx)));
5676
9d30f3c1
JJ
5677 for (nregs = 0;
5678 fregno <= FP_ARG_V4_MAX_REG && nregs < cfun->va_list_fpr_size;
5b667039 5679 fregno++, off += UNITS_PER_FP_WORD, nregs++)
4cc833b7 5680 {
5496b36f 5681 mem = gen_rtx_MEM (DFmode, plus_constant (save_area, off));
13e2e16e 5682 MEM_NOTRAP_P (mem) = 1;
c4ad648e 5683 set_mem_alias_set (mem, set);
94ff898d 5684 set_mem_align (mem, GET_MODE_ALIGNMENT (DFmode));
dfafc897 5685 emit_move_insn (mem, gen_rtx_REG (DFmode, fregno));
4697a36c 5686 }
4cc833b7
RH
5687
5688 emit_label (lab);
4697a36c 5689 }
4697a36c 5690}
4697a36c 5691
dfafc897 5692/* Create the va_list data type. */
2c4974b7 5693
c35d187f
RH
5694static tree
5695rs6000_build_builtin_va_list (void)
dfafc897 5696{
64c2816f 5697 tree f_gpr, f_fpr, f_res, f_ovf, f_sav, record, type_decl;
4697a36c 5698
9ebbca7d
GK
5699 /* For AIX, prefer 'char *' because that's what the system
5700 header files like. */
f607bc57 5701 if (DEFAULT_ABI != ABI_V4)
9ebbca7d 5702 return build_pointer_type (char_type_node);
dfafc897 5703
f1e639b1 5704 record = (*lang_hooks.types.make_type) (RECORD_TYPE);
bab45a51 5705 type_decl = build_decl (TYPE_DECL, get_identifier ("__va_list_tag"), record);
0f4fd75d 5706
f676971a 5707 f_gpr = build_decl (FIELD_DECL, get_identifier ("gpr"),
9ebbca7d 5708 unsigned_char_type_node);
f676971a 5709 f_fpr = build_decl (FIELD_DECL, get_identifier ("fpr"),
9ebbca7d 5710 unsigned_char_type_node);
64c2816f
DT
5711 /* Give the two bytes of padding a name, so that -Wpadded won't warn on
5712 every user file. */
5713 f_res = build_decl (FIELD_DECL, get_identifier ("reserved"),
5714 short_unsigned_type_node);
dfafc897
FS
5715 f_ovf = build_decl (FIELD_DECL, get_identifier ("overflow_arg_area"),
5716 ptr_type_node);
5717 f_sav = build_decl (FIELD_DECL, get_identifier ("reg_save_area"),
5718 ptr_type_node);
5719
9d30f3c1
JJ
5720 va_list_gpr_counter_field = f_gpr;
5721 va_list_fpr_counter_field = f_fpr;
5722
dfafc897
FS
5723 DECL_FIELD_CONTEXT (f_gpr) = record;
5724 DECL_FIELD_CONTEXT (f_fpr) = record;
64c2816f 5725 DECL_FIELD_CONTEXT (f_res) = record;
dfafc897
FS
5726 DECL_FIELD_CONTEXT (f_ovf) = record;
5727 DECL_FIELD_CONTEXT (f_sav) = record;
5728
bab45a51
FS
5729 TREE_CHAIN (record) = type_decl;
5730 TYPE_NAME (record) = type_decl;
dfafc897
FS
5731 TYPE_FIELDS (record) = f_gpr;
5732 TREE_CHAIN (f_gpr) = f_fpr;
64c2816f
DT
5733 TREE_CHAIN (f_fpr) = f_res;
5734 TREE_CHAIN (f_res) = f_ovf;
dfafc897
FS
5735 TREE_CHAIN (f_ovf) = f_sav;
5736
5737 layout_type (record);
5738
5739 /* The correct type is an array type of one element. */
5740 return build_array_type (record, build_index_type (size_zero_node));
5741}
5742
5743/* Implement va_start. */
5744
5745void
a2369ed3 5746rs6000_va_start (tree valist, rtx nextarg)
4697a36c 5747{
dfafc897 5748 HOST_WIDE_INT words, n_gpr, n_fpr;
c566f9bd 5749 tree f_gpr, f_fpr, f_res, f_ovf, f_sav;
dfafc897 5750 tree gpr, fpr, ovf, sav, t;
2c4974b7 5751
dfafc897 5752 /* Only SVR4 needs something special. */
f607bc57 5753 if (DEFAULT_ABI != ABI_V4)
dfafc897 5754 {
e5faf155 5755 std_expand_builtin_va_start (valist, nextarg);
dfafc897
FS
5756 return;
5757 }
5758
973a648b 5759 f_gpr = TYPE_FIELDS (TREE_TYPE (va_list_type_node));
dfafc897 5760 f_fpr = TREE_CHAIN (f_gpr);
c566f9bd
DT
5761 f_res = TREE_CHAIN (f_fpr);
5762 f_ovf = TREE_CHAIN (f_res);
dfafc897
FS
5763 f_sav = TREE_CHAIN (f_ovf);
5764
872a65b5 5765 valist = build_va_arg_indirect_ref (valist);
47a25a46
RG
5766 gpr = build3 (COMPONENT_REF, TREE_TYPE (f_gpr), valist, f_gpr, NULL_TREE);
5767 fpr = build3 (COMPONENT_REF, TREE_TYPE (f_fpr), valist, f_fpr, NULL_TREE);
5768 ovf = build3 (COMPONENT_REF, TREE_TYPE (f_ovf), valist, f_ovf, NULL_TREE);
5769 sav = build3 (COMPONENT_REF, TREE_TYPE (f_sav), valist, f_sav, NULL_TREE);
dfafc897
FS
5770
5771 /* Count number of gp and fp argument registers used. */
4cc833b7 5772 words = current_function_args_info.words;
987732e0
DE
5773 n_gpr = MIN (current_function_args_info.sysv_gregno - GP_ARG_MIN_REG,
5774 GP_ARG_NUM_REG);
5775 n_fpr = MIN (current_function_args_info.fregno - FP_ARG_MIN_REG,
5776 FP_ARG_NUM_REG);
dfafc897
FS
5777
5778 if (TARGET_DEBUG_ARG)
4a0a75dd
KG
5779 fprintf (stderr, "va_start: words = "HOST_WIDE_INT_PRINT_DEC", n_gpr = "
5780 HOST_WIDE_INT_PRINT_DEC", n_fpr = "HOST_WIDE_INT_PRINT_DEC"\n",
5781 words, n_gpr, n_fpr);
dfafc897 5782
9d30f3c1
JJ
5783 if (cfun->va_list_gpr_size)
5784 {
47a25a46
RG
5785 t = build2 (MODIFY_EXPR, TREE_TYPE (gpr), gpr,
5786 build_int_cst (NULL_TREE, n_gpr));
9d30f3c1
JJ
5787 TREE_SIDE_EFFECTS (t) = 1;
5788 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
5789 }
58c8adc1 5790
9d30f3c1
JJ
5791 if (cfun->va_list_fpr_size)
5792 {
47a25a46
RG
5793 t = build2 (MODIFY_EXPR, TREE_TYPE (fpr), fpr,
5794 build_int_cst (NULL_TREE, n_fpr));
9d30f3c1
JJ
5795 TREE_SIDE_EFFECTS (t) = 1;
5796 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
5797 }
dfafc897
FS
5798
5799 /* Find the overflow area. */
5800 t = make_tree (TREE_TYPE (ovf), virtual_incoming_args_rtx);
5801 if (words != 0)
47a25a46
RG
5802 t = build2 (PLUS_EXPR, TREE_TYPE (ovf), t,
5803 build_int_cst (NULL_TREE, words * UNITS_PER_WORD));
5804 t = build2 (MODIFY_EXPR, TREE_TYPE (ovf), ovf, t);
dfafc897
FS
5805 TREE_SIDE_EFFECTS (t) = 1;
5806 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
5807
9d30f3c1
JJ
5808 /* If there were no va_arg invocations, don't set up the register
5809 save area. */
5810 if (!cfun->va_list_gpr_size
5811 && !cfun->va_list_fpr_size
5812 && n_gpr < GP_ARG_NUM_REG
5813 && n_fpr < FP_ARG_V4_MAX_REG)
5814 return;
5815
dfafc897
FS
5816 /* Find the register save area. */
5817 t = make_tree (TREE_TYPE (sav), virtual_stack_vars_rtx);
5b667039 5818 if (cfun->machine->varargs_save_offset)
47a25a46
RG
5819 t = build2 (PLUS_EXPR, TREE_TYPE (sav), t,
5820 build_int_cst (NULL_TREE, cfun->machine->varargs_save_offset));
5821 t = build2 (MODIFY_EXPR, TREE_TYPE (sav), sav, t);
dfafc897
FS
5822 TREE_SIDE_EFFECTS (t) = 1;
5823 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
5824}
5825
5826/* Implement va_arg. */
5827
23a60a04
JM
5828tree
5829rs6000_gimplify_va_arg (tree valist, tree type, tree *pre_p, tree *post_p)
cd3ce9b4 5830{
cd3ce9b4
JM
5831 tree f_gpr, f_fpr, f_res, f_ovf, f_sav;
5832 tree gpr, fpr, ovf, sav, reg, t, u;
08b0dc1b 5833 int size, rsize, n_reg, sav_ofs, sav_scale;
cd3ce9b4
JM
5834 tree lab_false, lab_over, addr;
5835 int align;
5836 tree ptrtype = build_pointer_type (type);
5837
08b0dc1b
RH
5838 if (pass_by_reference (NULL, TYPE_MODE (type), type, false))
5839 {
5840 t = rs6000_gimplify_va_arg (valist, ptrtype, pre_p, post_p);
872a65b5 5841 return build_va_arg_indirect_ref (t);
08b0dc1b
RH
5842 }
5843
cd3ce9b4
JM
5844 if (DEFAULT_ABI != ABI_V4)
5845 {
08b0dc1b 5846 if (targetm.calls.split_complex_arg && TREE_CODE (type) == COMPLEX_TYPE)
cd3ce9b4
JM
5847 {
5848 tree elem_type = TREE_TYPE (type);
5849 enum machine_mode elem_mode = TYPE_MODE (elem_type);
5850 int elem_size = GET_MODE_SIZE (elem_mode);
5851
5852 if (elem_size < UNITS_PER_WORD)
5853 {
23a60a04 5854 tree real_part, imag_part;
cd3ce9b4
JM
5855 tree post = NULL_TREE;
5856
23a60a04
JM
5857 real_part = rs6000_gimplify_va_arg (valist, elem_type, pre_p,
5858 &post);
5859 /* Copy the value into a temporary, lest the formal temporary
5860 be reused out from under us. */
5861 real_part = get_initialized_tmp_var (real_part, pre_p, &post);
cd3ce9b4
JM
5862 append_to_statement_list (post, pre_p);
5863
23a60a04
JM
5864 imag_part = rs6000_gimplify_va_arg (valist, elem_type, pre_p,
5865 post_p);
cd3ce9b4 5866
47a25a46 5867 return build2 (COMPLEX_EXPR, type, real_part, imag_part);
cd3ce9b4
JM
5868 }
5869 }
5870
23a60a04 5871 return std_gimplify_va_arg_expr (valist, type, pre_p, post_p);
cd3ce9b4
JM
5872 }
5873
5874 f_gpr = TYPE_FIELDS (TREE_TYPE (va_list_type_node));
5875 f_fpr = TREE_CHAIN (f_gpr);
5876 f_res = TREE_CHAIN (f_fpr);
5877 f_ovf = TREE_CHAIN (f_res);
5878 f_sav = TREE_CHAIN (f_ovf);
5879
872a65b5 5880 valist = build_va_arg_indirect_ref (valist);
47a25a46
RG
5881 gpr = build3 (COMPONENT_REF, TREE_TYPE (f_gpr), valist, f_gpr, NULL_TREE);
5882 fpr = build3 (COMPONENT_REF, TREE_TYPE (f_fpr), valist, f_fpr, NULL_TREE);
5883 ovf = build3 (COMPONENT_REF, TREE_TYPE (f_ovf), valist, f_ovf, NULL_TREE);
5884 sav = build3 (COMPONENT_REF, TREE_TYPE (f_sav), valist, f_sav, NULL_TREE);
cd3ce9b4
JM
5885
5886 size = int_size_in_bytes (type);
5887 rsize = (size + 3) / 4;
5888 align = 1;
5889
08b0dc1b 5890 if (TARGET_HARD_FLOAT && TARGET_FPRS
602ea4d3
JJ
5891 && (TYPE_MODE (type) == SFmode
5892 || TYPE_MODE (type) == DFmode
5893 || TYPE_MODE (type) == TFmode))
cd3ce9b4
JM
5894 {
5895 /* FP args go in FP registers, if present. */
cd3ce9b4 5896 reg = fpr;
602ea4d3 5897 n_reg = (size + 7) / 8;
cd3ce9b4
JM
5898 sav_ofs = 8*4;
5899 sav_scale = 8;
602ea4d3 5900 if (TYPE_MODE (type) != SFmode)
cd3ce9b4
JM
5901 align = 8;
5902 }
5903 else
5904 {
5905 /* Otherwise into GP registers. */
cd3ce9b4
JM
5906 reg = gpr;
5907 n_reg = rsize;
5908 sav_ofs = 0;
5909 sav_scale = 4;
5910 if (n_reg == 2)
5911 align = 8;
5912 }
5913
5914 /* Pull the value out of the saved registers.... */
5915
5916 lab_over = NULL;
5917 addr = create_tmp_var (ptr_type_node, "addr");
5918 DECL_POINTER_ALIAS_SET (addr) = get_varargs_alias_set ();
5919
5920 /* AltiVec vectors never go in registers when -mabi=altivec. */
5921 if (TARGET_ALTIVEC_ABI && ALTIVEC_VECTOR_MODE (TYPE_MODE (type)))
5922 align = 16;
5923 else
5924 {
5925 lab_false = create_artificial_label ();
5926 lab_over = create_artificial_label ();
5927
5928 /* Long long and SPE vectors are aligned in the registers.
5929 As are any other 2 gpr item such as complex int due to a
5930 historical mistake. */
5931 u = reg;
602ea4d3 5932 if (n_reg == 2 && reg == gpr)
cd3ce9b4
JM
5933 {
5934 u = build2 (BIT_AND_EXPR, TREE_TYPE (reg), reg,
95674810 5935 size_int (n_reg - 1));
cd3ce9b4
JM
5936 u = build2 (POSTINCREMENT_EXPR, TREE_TYPE (reg), reg, u);
5937 }
5938
95674810 5939 t = fold_convert (TREE_TYPE (reg), size_int (8 - n_reg + 1));
cd3ce9b4
JM
5940 t = build2 (GE_EXPR, boolean_type_node, u, t);
5941 u = build1 (GOTO_EXPR, void_type_node, lab_false);
5942 t = build3 (COND_EXPR, void_type_node, t, u, NULL_TREE);
5943 gimplify_and_add (t, pre_p);
5944
5945 t = sav;
5946 if (sav_ofs)
95674810 5947 t = build2 (PLUS_EXPR, ptr_type_node, sav, size_int (sav_ofs));
cd3ce9b4 5948
95674810 5949 u = build2 (POSTINCREMENT_EXPR, TREE_TYPE (reg), reg, size_int (n_reg));
cd3ce9b4 5950 u = build1 (CONVERT_EXPR, integer_type_node, u);
95674810 5951 u = build2 (MULT_EXPR, integer_type_node, u, size_int (sav_scale));
cd3ce9b4
JM
5952 t = build2 (PLUS_EXPR, ptr_type_node, t, u);
5953
5954 t = build2 (MODIFY_EXPR, void_type_node, addr, t);
5955 gimplify_and_add (t, pre_p);
5956
5957 t = build1 (GOTO_EXPR, void_type_node, lab_over);
5958 gimplify_and_add (t, pre_p);
5959
5960 t = build1 (LABEL_EXPR, void_type_node, lab_false);
5961 append_to_statement_list (t, pre_p);
5962
9a74f8ee 5963 if ((n_reg == 2 && reg != gpr) || n_reg > 2)
cd3ce9b4
JM
5964 {
5965 /* Ensure that we don't find any more args in regs.
56438901 5966 Alignment has taken care of the n_reg == 2 gpr case. */
47a25a46 5967 t = build2 (MODIFY_EXPR, TREE_TYPE (reg), reg, size_int (8));
cd3ce9b4
JM
5968 gimplify_and_add (t, pre_p);
5969 }
5970 }
5971
5972 /* ... otherwise out of the overflow area. */
5973
5974 /* Care for on-stack alignment if needed. */
5975 t = ovf;
5976 if (align != 1)
5977 {
95674810 5978 t = build2 (PLUS_EXPR, TREE_TYPE (t), t, size_int (align - 1));
4a90aeeb 5979 t = build2 (BIT_AND_EXPR, TREE_TYPE (t), t,
7d60be94 5980 build_int_cst (NULL_TREE, -align));
cd3ce9b4
JM
5981 }
5982 gimplify_expr (&t, pre_p, NULL, is_gimple_val, fb_rvalue);
5983
5984 u = build2 (MODIFY_EXPR, void_type_node, addr, t);
5985 gimplify_and_add (u, pre_p);
5986
95674810 5987 t = build2 (PLUS_EXPR, TREE_TYPE (t), t, size_int (size));
cd3ce9b4
JM
5988 t = build2 (MODIFY_EXPR, TREE_TYPE (ovf), ovf, t);
5989 gimplify_and_add (t, pre_p);
5990
5991 if (lab_over)
5992 {
5993 t = build1 (LABEL_EXPR, void_type_node, lab_over);
5994 append_to_statement_list (t, pre_p);
5995 }
5996
08b0dc1b 5997 addr = fold_convert (ptrtype, addr);
872a65b5 5998 return build_va_arg_indirect_ref (addr);
cd3ce9b4
JM
5999}
6000
0ac081f6
AH
6001/* Builtins. */
6002
58646b77
PB
6003static void
6004def_builtin (int mask, const char *name, tree type, int code)
6005{
6006 if (mask & target_flags)
6007 {
6008 if (rs6000_builtin_decls[code])
6009 abort ();
6010
6011 rs6000_builtin_decls[code] =
6012 lang_hooks.builtin_function (name, type, code, BUILT_IN_MD,
6013 NULL, NULL_TREE);
6014 }
6015}
0ac081f6 6016
24408032
AH
6017/* Simple ternary operations: VECd = foo (VECa, VECb, VECc). */
6018
2212663f 6019static const struct builtin_description bdesc_3arg[] =
24408032
AH
6020{
6021 { MASK_ALTIVEC, CODE_FOR_altivec_vmaddfp, "__builtin_altivec_vmaddfp", ALTIVEC_BUILTIN_VMADDFP },
6022 { MASK_ALTIVEC, CODE_FOR_altivec_vmhaddshs, "__builtin_altivec_vmhaddshs", ALTIVEC_BUILTIN_VMHADDSHS },
6023 { MASK_ALTIVEC, CODE_FOR_altivec_vmhraddshs, "__builtin_altivec_vmhraddshs", ALTIVEC_BUILTIN_VMHRADDSHS },
6024 { MASK_ALTIVEC, CODE_FOR_altivec_vmladduhm, "__builtin_altivec_vmladduhm", ALTIVEC_BUILTIN_VMLADDUHM},
6025 { MASK_ALTIVEC, CODE_FOR_altivec_vmsumubm, "__builtin_altivec_vmsumubm", ALTIVEC_BUILTIN_VMSUMUBM },
6026 { MASK_ALTIVEC, CODE_FOR_altivec_vmsummbm, "__builtin_altivec_vmsummbm", ALTIVEC_BUILTIN_VMSUMMBM },
6027 { MASK_ALTIVEC, CODE_FOR_altivec_vmsumuhm, "__builtin_altivec_vmsumuhm", ALTIVEC_BUILTIN_VMSUMUHM },
6028 { MASK_ALTIVEC, CODE_FOR_altivec_vmsumshm, "__builtin_altivec_vmsumshm", ALTIVEC_BUILTIN_VMSUMSHM },
6029 { MASK_ALTIVEC, CODE_FOR_altivec_vmsumuhs, "__builtin_altivec_vmsumuhs", ALTIVEC_BUILTIN_VMSUMUHS },
6030 { MASK_ALTIVEC, CODE_FOR_altivec_vmsumshs, "__builtin_altivec_vmsumshs", ALTIVEC_BUILTIN_VMSUMSHS },
f676971a 6031 { MASK_ALTIVEC, CODE_FOR_altivec_vnmsubfp, "__builtin_altivec_vnmsubfp", ALTIVEC_BUILTIN_VNMSUBFP },
aba5fb01
NS
6032 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v4sf, "__builtin_altivec_vperm_4sf", ALTIVEC_BUILTIN_VPERM_4SF },
6033 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v4si, "__builtin_altivec_vperm_4si", ALTIVEC_BUILTIN_VPERM_4SI },
6034 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v8hi, "__builtin_altivec_vperm_8hi", ALTIVEC_BUILTIN_VPERM_8HI },
6035 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v16qi, "__builtin_altivec_vperm_16qi", ALTIVEC_BUILTIN_VPERM_16QI },
6036 { MASK_ALTIVEC, CODE_FOR_altivec_vsel_v4sf, "__builtin_altivec_vsel_4sf", ALTIVEC_BUILTIN_VSEL_4SF },
6037 { MASK_ALTIVEC, CODE_FOR_altivec_vsel_v4si, "__builtin_altivec_vsel_4si", ALTIVEC_BUILTIN_VSEL_4SI },
6038 { MASK_ALTIVEC, CODE_FOR_altivec_vsel_v8hi, "__builtin_altivec_vsel_8hi", ALTIVEC_BUILTIN_VSEL_8HI },
6039 { MASK_ALTIVEC, CODE_FOR_altivec_vsel_v16qi, "__builtin_altivec_vsel_16qi", ALTIVEC_BUILTIN_VSEL_16QI },
6040 { MASK_ALTIVEC, CODE_FOR_altivec_vsldoi_v16qi, "__builtin_altivec_vsldoi_16qi", ALTIVEC_BUILTIN_VSLDOI_16QI },
6041 { MASK_ALTIVEC, CODE_FOR_altivec_vsldoi_v8hi, "__builtin_altivec_vsldoi_8hi", ALTIVEC_BUILTIN_VSLDOI_8HI },
6042 { MASK_ALTIVEC, CODE_FOR_altivec_vsldoi_v4si, "__builtin_altivec_vsldoi_4si", ALTIVEC_BUILTIN_VSLDOI_4SI },
6043 { MASK_ALTIVEC, CODE_FOR_altivec_vsldoi_v4sf, "__builtin_altivec_vsldoi_4sf", ALTIVEC_BUILTIN_VSLDOI_4SF },
58646b77
PB
6044
6045 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_madd", ALTIVEC_BUILTIN_VEC_MADD },
6046 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_madds", ALTIVEC_BUILTIN_VEC_MADDS },
6047 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mladd", ALTIVEC_BUILTIN_VEC_MLADD },
6048 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mradds", ALTIVEC_BUILTIN_VEC_MRADDS },
6049 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_msum", ALTIVEC_BUILTIN_VEC_MSUM },
6050 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmsumshm", ALTIVEC_BUILTIN_VEC_VMSUMSHM },
6051 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmsumuhm", ALTIVEC_BUILTIN_VEC_VMSUMUHM },
6052 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmsummbm", ALTIVEC_BUILTIN_VEC_VMSUMMBM },
6053 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmsumubm", ALTIVEC_BUILTIN_VEC_VMSUMUBM },
6054 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_msums", ALTIVEC_BUILTIN_VEC_MSUMS },
6055 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmsumshs", ALTIVEC_BUILTIN_VEC_VMSUMSHS },
6056 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmsumuhs", ALTIVEC_BUILTIN_VEC_VMSUMUHS },
6057 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_nmsub", ALTIVEC_BUILTIN_VEC_NMSUB },
6058 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_perm", ALTIVEC_BUILTIN_VEC_PERM },
6059 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sel", ALTIVEC_BUILTIN_VEC_SEL },
24408032 6060};
2212663f 6061
95385cbb
AH
6062/* DST operations: void foo (void *, const int, const char). */
6063
6064static const struct builtin_description bdesc_dst[] =
6065{
6066 { MASK_ALTIVEC, CODE_FOR_altivec_dst, "__builtin_altivec_dst", ALTIVEC_BUILTIN_DST },
6067 { MASK_ALTIVEC, CODE_FOR_altivec_dstt, "__builtin_altivec_dstt", ALTIVEC_BUILTIN_DSTT },
6068 { MASK_ALTIVEC, CODE_FOR_altivec_dstst, "__builtin_altivec_dstst", ALTIVEC_BUILTIN_DSTST },
58646b77
PB
6069 { MASK_ALTIVEC, CODE_FOR_altivec_dststt, "__builtin_altivec_dststt", ALTIVEC_BUILTIN_DSTSTT },
6070
6071 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_dst", ALTIVEC_BUILTIN_VEC_DST },
6072 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_dstt", ALTIVEC_BUILTIN_VEC_DSTT },
6073 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_dstst", ALTIVEC_BUILTIN_VEC_DSTST },
6074 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_dststt", ALTIVEC_BUILTIN_VEC_DSTSTT }
95385cbb
AH
6075};
6076
2212663f 6077/* Simple binary operations: VECc = foo (VECa, VECb). */
24408032 6078
a3170dc6 6079static struct builtin_description bdesc_2arg[] =
0ac081f6 6080{
f18c054f
DB
6081 { MASK_ALTIVEC, CODE_FOR_addv16qi3, "__builtin_altivec_vaddubm", ALTIVEC_BUILTIN_VADDUBM },
6082 { MASK_ALTIVEC, CODE_FOR_addv8hi3, "__builtin_altivec_vadduhm", ALTIVEC_BUILTIN_VADDUHM },
6083 { MASK_ALTIVEC, CODE_FOR_addv4si3, "__builtin_altivec_vadduwm", ALTIVEC_BUILTIN_VADDUWM },
6084 { MASK_ALTIVEC, CODE_FOR_addv4sf3, "__builtin_altivec_vaddfp", ALTIVEC_BUILTIN_VADDFP },
0ac081f6
AH
6085 { MASK_ALTIVEC, CODE_FOR_altivec_vaddcuw, "__builtin_altivec_vaddcuw", ALTIVEC_BUILTIN_VADDCUW },
6086 { MASK_ALTIVEC, CODE_FOR_altivec_vaddubs, "__builtin_altivec_vaddubs", ALTIVEC_BUILTIN_VADDUBS },
6087 { MASK_ALTIVEC, CODE_FOR_altivec_vaddsbs, "__builtin_altivec_vaddsbs", ALTIVEC_BUILTIN_VADDSBS },
6088 { MASK_ALTIVEC, CODE_FOR_altivec_vadduhs, "__builtin_altivec_vadduhs", ALTIVEC_BUILTIN_VADDUHS },
6089 { MASK_ALTIVEC, CODE_FOR_altivec_vaddshs, "__builtin_altivec_vaddshs", ALTIVEC_BUILTIN_VADDSHS },
6090 { MASK_ALTIVEC, CODE_FOR_altivec_vadduws, "__builtin_altivec_vadduws", ALTIVEC_BUILTIN_VADDUWS },
6091 { MASK_ALTIVEC, CODE_FOR_altivec_vaddsws, "__builtin_altivec_vaddsws", ALTIVEC_BUILTIN_VADDSWS },
f18c054f 6092 { MASK_ALTIVEC, CODE_FOR_andv4si3, "__builtin_altivec_vand", ALTIVEC_BUILTIN_VAND },
aba5fb01 6093 { MASK_ALTIVEC, CODE_FOR_andcv4si3, "__builtin_altivec_vandc", ALTIVEC_BUILTIN_VANDC },
0ac081f6
AH
6094 { MASK_ALTIVEC, CODE_FOR_altivec_vavgub, "__builtin_altivec_vavgub", ALTIVEC_BUILTIN_VAVGUB },
6095 { MASK_ALTIVEC, CODE_FOR_altivec_vavgsb, "__builtin_altivec_vavgsb", ALTIVEC_BUILTIN_VAVGSB },
6096 { MASK_ALTIVEC, CODE_FOR_altivec_vavguh, "__builtin_altivec_vavguh", ALTIVEC_BUILTIN_VAVGUH },
6097 { MASK_ALTIVEC, CODE_FOR_altivec_vavgsh, "__builtin_altivec_vavgsh", ALTIVEC_BUILTIN_VAVGSH },
6098 { MASK_ALTIVEC, CODE_FOR_altivec_vavguw, "__builtin_altivec_vavguw", ALTIVEC_BUILTIN_VAVGUW },
6099 { MASK_ALTIVEC, CODE_FOR_altivec_vavgsw, "__builtin_altivec_vavgsw", ALTIVEC_BUILTIN_VAVGSW },
617e0e1d
DB
6100 { MASK_ALTIVEC, CODE_FOR_altivec_vcfux, "__builtin_altivec_vcfux", ALTIVEC_BUILTIN_VCFUX },
6101 { MASK_ALTIVEC, CODE_FOR_altivec_vcfsx, "__builtin_altivec_vcfsx", ALTIVEC_BUILTIN_VCFSX },
0ac081f6
AH
6102 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpbfp, "__builtin_altivec_vcmpbfp", ALTIVEC_BUILTIN_VCMPBFP },
6103 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpequb, "__builtin_altivec_vcmpequb", ALTIVEC_BUILTIN_VCMPEQUB },
6104 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpequh, "__builtin_altivec_vcmpequh", ALTIVEC_BUILTIN_VCMPEQUH },
6105 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpequw, "__builtin_altivec_vcmpequw", ALTIVEC_BUILTIN_VCMPEQUW },
6106 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpeqfp, "__builtin_altivec_vcmpeqfp", ALTIVEC_BUILTIN_VCMPEQFP },
6107 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpgefp, "__builtin_altivec_vcmpgefp", ALTIVEC_BUILTIN_VCMPGEFP },
6108 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpgtub, "__builtin_altivec_vcmpgtub", ALTIVEC_BUILTIN_VCMPGTUB },
6109 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpgtsb, "__builtin_altivec_vcmpgtsb", ALTIVEC_BUILTIN_VCMPGTSB },
6110 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpgtuh, "__builtin_altivec_vcmpgtuh", ALTIVEC_BUILTIN_VCMPGTUH },
6111 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpgtsh, "__builtin_altivec_vcmpgtsh", ALTIVEC_BUILTIN_VCMPGTSH },
6112 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpgtuw, "__builtin_altivec_vcmpgtuw", ALTIVEC_BUILTIN_VCMPGTUW },
6113 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpgtsw, "__builtin_altivec_vcmpgtsw", ALTIVEC_BUILTIN_VCMPGTSW },
6114 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpgtfp, "__builtin_altivec_vcmpgtfp", ALTIVEC_BUILTIN_VCMPGTFP },
617e0e1d
DB
6115 { MASK_ALTIVEC, CODE_FOR_altivec_vctsxs, "__builtin_altivec_vctsxs", ALTIVEC_BUILTIN_VCTSXS },
6116 { MASK_ALTIVEC, CODE_FOR_altivec_vctuxs, "__builtin_altivec_vctuxs", ALTIVEC_BUILTIN_VCTUXS },
f18c054f
DB
6117 { MASK_ALTIVEC, CODE_FOR_umaxv16qi3, "__builtin_altivec_vmaxub", ALTIVEC_BUILTIN_VMAXUB },
6118 { MASK_ALTIVEC, CODE_FOR_smaxv16qi3, "__builtin_altivec_vmaxsb", ALTIVEC_BUILTIN_VMAXSB },
df966bff
AH
6119 { MASK_ALTIVEC, CODE_FOR_umaxv8hi3, "__builtin_altivec_vmaxuh", ALTIVEC_BUILTIN_VMAXUH },
6120 { MASK_ALTIVEC, CODE_FOR_smaxv8hi3, "__builtin_altivec_vmaxsh", ALTIVEC_BUILTIN_VMAXSH },
6121 { MASK_ALTIVEC, CODE_FOR_umaxv4si3, "__builtin_altivec_vmaxuw", ALTIVEC_BUILTIN_VMAXUW },
6122 { MASK_ALTIVEC, CODE_FOR_smaxv4si3, "__builtin_altivec_vmaxsw", ALTIVEC_BUILTIN_VMAXSW },
6123 { MASK_ALTIVEC, CODE_FOR_smaxv4sf3, "__builtin_altivec_vmaxfp", ALTIVEC_BUILTIN_VMAXFP },
0ac081f6
AH
6124 { MASK_ALTIVEC, CODE_FOR_altivec_vmrghb, "__builtin_altivec_vmrghb", ALTIVEC_BUILTIN_VMRGHB },
6125 { MASK_ALTIVEC, CODE_FOR_altivec_vmrghh, "__builtin_altivec_vmrghh", ALTIVEC_BUILTIN_VMRGHH },
6126 { MASK_ALTIVEC, CODE_FOR_altivec_vmrghw, "__builtin_altivec_vmrghw", ALTIVEC_BUILTIN_VMRGHW },
6127 { MASK_ALTIVEC, CODE_FOR_altivec_vmrglb, "__builtin_altivec_vmrglb", ALTIVEC_BUILTIN_VMRGLB },
6128 { MASK_ALTIVEC, CODE_FOR_altivec_vmrglh, "__builtin_altivec_vmrglh", ALTIVEC_BUILTIN_VMRGLH },
6129 { MASK_ALTIVEC, CODE_FOR_altivec_vmrglw, "__builtin_altivec_vmrglw", ALTIVEC_BUILTIN_VMRGLW },
f18c054f
DB
6130 { MASK_ALTIVEC, CODE_FOR_uminv16qi3, "__builtin_altivec_vminub", ALTIVEC_BUILTIN_VMINUB },
6131 { MASK_ALTIVEC, CODE_FOR_sminv16qi3, "__builtin_altivec_vminsb", ALTIVEC_BUILTIN_VMINSB },
6132 { MASK_ALTIVEC, CODE_FOR_uminv8hi3, "__builtin_altivec_vminuh", ALTIVEC_BUILTIN_VMINUH },
6133 { MASK_ALTIVEC, CODE_FOR_sminv8hi3, "__builtin_altivec_vminsh", ALTIVEC_BUILTIN_VMINSH },
6134 { MASK_ALTIVEC, CODE_FOR_uminv4si3, "__builtin_altivec_vminuw", ALTIVEC_BUILTIN_VMINUW },
6135 { MASK_ALTIVEC, CODE_FOR_sminv4si3, "__builtin_altivec_vminsw", ALTIVEC_BUILTIN_VMINSW },
6136 { MASK_ALTIVEC, CODE_FOR_sminv4sf3, "__builtin_altivec_vminfp", ALTIVEC_BUILTIN_VMINFP },
0ac081f6
AH
6137 { MASK_ALTIVEC, CODE_FOR_altivec_vmuleub, "__builtin_altivec_vmuleub", ALTIVEC_BUILTIN_VMULEUB },
6138 { MASK_ALTIVEC, CODE_FOR_altivec_vmulesb, "__builtin_altivec_vmulesb", ALTIVEC_BUILTIN_VMULESB },
6139 { MASK_ALTIVEC, CODE_FOR_altivec_vmuleuh, "__builtin_altivec_vmuleuh", ALTIVEC_BUILTIN_VMULEUH },
6140 { MASK_ALTIVEC, CODE_FOR_altivec_vmulesh, "__builtin_altivec_vmulesh", ALTIVEC_BUILTIN_VMULESH },
6141 { MASK_ALTIVEC, CODE_FOR_altivec_vmuloub, "__builtin_altivec_vmuloub", ALTIVEC_BUILTIN_VMULOUB },
6142 { MASK_ALTIVEC, CODE_FOR_altivec_vmulosb, "__builtin_altivec_vmulosb", ALTIVEC_BUILTIN_VMULOSB },
6143 { MASK_ALTIVEC, CODE_FOR_altivec_vmulouh, "__builtin_altivec_vmulouh", ALTIVEC_BUILTIN_VMULOUH },
6144 { MASK_ALTIVEC, CODE_FOR_altivec_vmulosh, "__builtin_altivec_vmulosh", ALTIVEC_BUILTIN_VMULOSH },
f96bc213 6145 { MASK_ALTIVEC, CODE_FOR_altivec_norv4si3, "__builtin_altivec_vnor", ALTIVEC_BUILTIN_VNOR },
f18c054f 6146 { MASK_ALTIVEC, CODE_FOR_iorv4si3, "__builtin_altivec_vor", ALTIVEC_BUILTIN_VOR },
0ac081f6
AH
6147 { MASK_ALTIVEC, CODE_FOR_altivec_vpkuhum, "__builtin_altivec_vpkuhum", ALTIVEC_BUILTIN_VPKUHUM },
6148 { MASK_ALTIVEC, CODE_FOR_altivec_vpkuwum, "__builtin_altivec_vpkuwum", ALTIVEC_BUILTIN_VPKUWUM },
6149 { MASK_ALTIVEC, CODE_FOR_altivec_vpkpx, "__builtin_altivec_vpkpx", ALTIVEC_BUILTIN_VPKPX },
0ac081f6 6150 { MASK_ALTIVEC, CODE_FOR_altivec_vpkshss, "__builtin_altivec_vpkshss", ALTIVEC_BUILTIN_VPKSHSS },
0ac081f6
AH
6151 { MASK_ALTIVEC, CODE_FOR_altivec_vpkswss, "__builtin_altivec_vpkswss", ALTIVEC_BUILTIN_VPKSWSS },
6152 { MASK_ALTIVEC, CODE_FOR_altivec_vpkuhus, "__builtin_altivec_vpkuhus", ALTIVEC_BUILTIN_VPKUHUS },
6153 { MASK_ALTIVEC, CODE_FOR_altivec_vpkshus, "__builtin_altivec_vpkshus", ALTIVEC_BUILTIN_VPKSHUS },
6154 { MASK_ALTIVEC, CODE_FOR_altivec_vpkuwus, "__builtin_altivec_vpkuwus", ALTIVEC_BUILTIN_VPKUWUS },
6155 { MASK_ALTIVEC, CODE_FOR_altivec_vpkswus, "__builtin_altivec_vpkswus", ALTIVEC_BUILTIN_VPKSWUS },
6156 { MASK_ALTIVEC, CODE_FOR_altivec_vrlb, "__builtin_altivec_vrlb", ALTIVEC_BUILTIN_VRLB },
6157 { MASK_ALTIVEC, CODE_FOR_altivec_vrlh, "__builtin_altivec_vrlh", ALTIVEC_BUILTIN_VRLH },
6158 { MASK_ALTIVEC, CODE_FOR_altivec_vrlw, "__builtin_altivec_vrlw", ALTIVEC_BUILTIN_VRLW },
6159 { MASK_ALTIVEC, CODE_FOR_altivec_vslb, "__builtin_altivec_vslb", ALTIVEC_BUILTIN_VSLB },
6160 { MASK_ALTIVEC, CODE_FOR_altivec_vslh, "__builtin_altivec_vslh", ALTIVEC_BUILTIN_VSLH },
6161 { MASK_ALTIVEC, CODE_FOR_altivec_vslw, "__builtin_altivec_vslw", ALTIVEC_BUILTIN_VSLW },
6162 { MASK_ALTIVEC, CODE_FOR_altivec_vsl, "__builtin_altivec_vsl", ALTIVEC_BUILTIN_VSL },
6163 { MASK_ALTIVEC, CODE_FOR_altivec_vslo, "__builtin_altivec_vslo", ALTIVEC_BUILTIN_VSLO },
2212663f
DB
6164 { MASK_ALTIVEC, CODE_FOR_altivec_vspltb, "__builtin_altivec_vspltb", ALTIVEC_BUILTIN_VSPLTB },
6165 { MASK_ALTIVEC, CODE_FOR_altivec_vsplth, "__builtin_altivec_vsplth", ALTIVEC_BUILTIN_VSPLTH },
6166 { MASK_ALTIVEC, CODE_FOR_altivec_vspltw, "__builtin_altivec_vspltw", ALTIVEC_BUILTIN_VSPLTW },
3e0de9d1
DP
6167 { MASK_ALTIVEC, CODE_FOR_lshrv16qi3, "__builtin_altivec_vsrb", ALTIVEC_BUILTIN_VSRB },
6168 { MASK_ALTIVEC, CODE_FOR_lshrv8hi3, "__builtin_altivec_vsrh", ALTIVEC_BUILTIN_VSRH },
6169 { MASK_ALTIVEC, CODE_FOR_lshrv4si3, "__builtin_altivec_vsrw", ALTIVEC_BUILTIN_VSRW },
6170 { MASK_ALTIVEC, CODE_FOR_ashrv16qi3, "__builtin_altivec_vsrab", ALTIVEC_BUILTIN_VSRAB },
6171 { MASK_ALTIVEC, CODE_FOR_ashrv8hi3, "__builtin_altivec_vsrah", ALTIVEC_BUILTIN_VSRAH },
6172 { MASK_ALTIVEC, CODE_FOR_ashrv4si3, "__builtin_altivec_vsraw", ALTIVEC_BUILTIN_VSRAW },
0ac081f6
AH
6173 { MASK_ALTIVEC, CODE_FOR_altivec_vsr, "__builtin_altivec_vsr", ALTIVEC_BUILTIN_VSR },
6174 { MASK_ALTIVEC, CODE_FOR_altivec_vsro, "__builtin_altivec_vsro", ALTIVEC_BUILTIN_VSRO },
f18c054f
DB
6175 { MASK_ALTIVEC, CODE_FOR_subv16qi3, "__builtin_altivec_vsububm", ALTIVEC_BUILTIN_VSUBUBM },
6176 { MASK_ALTIVEC, CODE_FOR_subv8hi3, "__builtin_altivec_vsubuhm", ALTIVEC_BUILTIN_VSUBUHM },
6177 { MASK_ALTIVEC, CODE_FOR_subv4si3, "__builtin_altivec_vsubuwm", ALTIVEC_BUILTIN_VSUBUWM },
6178 { MASK_ALTIVEC, CODE_FOR_subv4sf3, "__builtin_altivec_vsubfp", ALTIVEC_BUILTIN_VSUBFP },
0ac081f6
AH
6179 { MASK_ALTIVEC, CODE_FOR_altivec_vsubcuw, "__builtin_altivec_vsubcuw", ALTIVEC_BUILTIN_VSUBCUW },
6180 { MASK_ALTIVEC, CODE_FOR_altivec_vsububs, "__builtin_altivec_vsububs", ALTIVEC_BUILTIN_VSUBUBS },
6181 { MASK_ALTIVEC, CODE_FOR_altivec_vsubsbs, "__builtin_altivec_vsubsbs", ALTIVEC_BUILTIN_VSUBSBS },
6182 { MASK_ALTIVEC, CODE_FOR_altivec_vsubuhs, "__builtin_altivec_vsubuhs", ALTIVEC_BUILTIN_VSUBUHS },
6183 { MASK_ALTIVEC, CODE_FOR_altivec_vsubshs, "__builtin_altivec_vsubshs", ALTIVEC_BUILTIN_VSUBSHS },
6184 { MASK_ALTIVEC, CODE_FOR_altivec_vsubuws, "__builtin_altivec_vsubuws", ALTIVEC_BUILTIN_VSUBUWS },
6185 { MASK_ALTIVEC, CODE_FOR_altivec_vsubsws, "__builtin_altivec_vsubsws", ALTIVEC_BUILTIN_VSUBSWS },
6186 { MASK_ALTIVEC, CODE_FOR_altivec_vsum4ubs, "__builtin_altivec_vsum4ubs", ALTIVEC_BUILTIN_VSUM4UBS },
6187 { MASK_ALTIVEC, CODE_FOR_altivec_vsum4sbs, "__builtin_altivec_vsum4sbs", ALTIVEC_BUILTIN_VSUM4SBS },
6188 { MASK_ALTIVEC, CODE_FOR_altivec_vsum4shs, "__builtin_altivec_vsum4shs", ALTIVEC_BUILTIN_VSUM4SHS },
6189 { MASK_ALTIVEC, CODE_FOR_altivec_vsum2sws, "__builtin_altivec_vsum2sws", ALTIVEC_BUILTIN_VSUM2SWS },
6190 { MASK_ALTIVEC, CODE_FOR_altivec_vsumsws, "__builtin_altivec_vsumsws", ALTIVEC_BUILTIN_VSUMSWS },
f18c054f 6191 { MASK_ALTIVEC, CODE_FOR_xorv4si3, "__builtin_altivec_vxor", ALTIVEC_BUILTIN_VXOR },
a3170dc6 6192
58646b77
PB
6193 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_add", ALTIVEC_BUILTIN_VEC_ADD },
6194 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vaddfp", ALTIVEC_BUILTIN_VEC_VADDFP },
6195 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vadduwm", ALTIVEC_BUILTIN_VEC_VADDUWM },
6196 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vadduhm", ALTIVEC_BUILTIN_VEC_VADDUHM },
6197 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vaddubm", ALTIVEC_BUILTIN_VEC_VADDUBM },
6198 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_addc", ALTIVEC_BUILTIN_VEC_ADDC },
6199 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_adds", ALTIVEC_BUILTIN_VEC_ADDS },
6200 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vaddsws", ALTIVEC_BUILTIN_VEC_VADDSWS },
6201 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vadduws", ALTIVEC_BUILTIN_VEC_VADDUWS },
6202 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vaddshs", ALTIVEC_BUILTIN_VEC_VADDSHS },
6203 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vadduhs", ALTIVEC_BUILTIN_VEC_VADDUHS },
6204 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vaddsbs", ALTIVEC_BUILTIN_VEC_VADDSBS },
6205 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vaddubs", ALTIVEC_BUILTIN_VEC_VADDUBS },
6206 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_and", ALTIVEC_BUILTIN_VEC_AND },
6207 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_andc", ALTIVEC_BUILTIN_VEC_ANDC },
6208 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_avg", ALTIVEC_BUILTIN_VEC_AVG },
6209 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vavgsw", ALTIVEC_BUILTIN_VEC_VAVGSW },
6210 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vavguw", ALTIVEC_BUILTIN_VEC_VAVGUW },
6211 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vavgsh", ALTIVEC_BUILTIN_VEC_VAVGSH },
6212 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vavguh", ALTIVEC_BUILTIN_VEC_VAVGUH },
6213 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vavgsb", ALTIVEC_BUILTIN_VEC_VAVGSB },
6214 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vavgub", ALTIVEC_BUILTIN_VEC_VAVGUB },
6215 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_cmpb", ALTIVEC_BUILTIN_VEC_CMPB },
6216 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_cmpeq", ALTIVEC_BUILTIN_VEC_CMPEQ },
6217 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpeqfp", ALTIVEC_BUILTIN_VEC_VCMPEQFP },
6218 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpequw", ALTIVEC_BUILTIN_VEC_VCMPEQUW },
6219 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpequh", ALTIVEC_BUILTIN_VEC_VCMPEQUH },
6220 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpequb", ALTIVEC_BUILTIN_VEC_VCMPEQUB },
6221 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_cmpge", ALTIVEC_BUILTIN_VEC_CMPGE },
6222 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_cmpgt", ALTIVEC_BUILTIN_VEC_CMPGT },
6223 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtfp", ALTIVEC_BUILTIN_VEC_VCMPGTFP },
6224 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtsw", ALTIVEC_BUILTIN_VEC_VCMPGTSW },
6225 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtuw", ALTIVEC_BUILTIN_VEC_VCMPGTUW },
6226 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtsh", ALTIVEC_BUILTIN_VEC_VCMPGTSH },
6227 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtuh", ALTIVEC_BUILTIN_VEC_VCMPGTUH },
6228 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtsb", ALTIVEC_BUILTIN_VEC_VCMPGTSB },
6229 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtub", ALTIVEC_BUILTIN_VEC_VCMPGTUB },
6230 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_cmple", ALTIVEC_BUILTIN_VEC_CMPLE },
6231 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_cmplt", ALTIVEC_BUILTIN_VEC_CMPLT },
6232 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_max", ALTIVEC_BUILTIN_VEC_MAX },
6233 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxfp", ALTIVEC_BUILTIN_VEC_VMAXFP },
6234 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxsw", ALTIVEC_BUILTIN_VEC_VMAXSW },
6235 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxuw", ALTIVEC_BUILTIN_VEC_VMAXUW },
6236 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxsh", ALTIVEC_BUILTIN_VEC_VMAXSH },
6237 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxuh", ALTIVEC_BUILTIN_VEC_VMAXUH },
6238 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxsb", ALTIVEC_BUILTIN_VEC_VMAXSB },
6239 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxub", ALTIVEC_BUILTIN_VEC_VMAXUB },
6240 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mergeh", ALTIVEC_BUILTIN_VEC_MERGEH },
6241 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmrghw", ALTIVEC_BUILTIN_VEC_VMRGHW },
6242 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmrghh", ALTIVEC_BUILTIN_VEC_VMRGHH },
6243 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmrghb", ALTIVEC_BUILTIN_VEC_VMRGHB },
6244 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mergel", ALTIVEC_BUILTIN_VEC_MERGEL },
6245 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmrglw", ALTIVEC_BUILTIN_VEC_VMRGLW },
6246 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmrglh", ALTIVEC_BUILTIN_VEC_VMRGLH },
6247 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmrglb", ALTIVEC_BUILTIN_VEC_VMRGLB },
6248 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_min", ALTIVEC_BUILTIN_VEC_MIN },
6249 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminfp", ALTIVEC_BUILTIN_VEC_VMINFP },
6250 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminsw", ALTIVEC_BUILTIN_VEC_VMINSW },
6251 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminuw", ALTIVEC_BUILTIN_VEC_VMINUW },
6252 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminsh", ALTIVEC_BUILTIN_VEC_VMINSH },
6253 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminuh", ALTIVEC_BUILTIN_VEC_VMINUH },
6254 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminsb", ALTIVEC_BUILTIN_VEC_VMINSB },
6255 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminub", ALTIVEC_BUILTIN_VEC_VMINUB },
6256 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mule", ALTIVEC_BUILTIN_VEC_MULE },
6257 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmuleub", ALTIVEC_BUILTIN_VEC_VMULEUB },
6258 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmulesb", ALTIVEC_BUILTIN_VEC_VMULESB },
6259 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmuleuh", ALTIVEC_BUILTIN_VEC_VMULEUH },
6260 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmulesh", ALTIVEC_BUILTIN_VEC_VMULESH },
6261 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mulo", ALTIVEC_BUILTIN_VEC_MULO },
6262 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmulosh", ALTIVEC_BUILTIN_VEC_VMULOSH },
6263 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmulouh", ALTIVEC_BUILTIN_VEC_VMULOUH },
6264 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmulosb", ALTIVEC_BUILTIN_VEC_VMULOSB },
6265 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmuloub", ALTIVEC_BUILTIN_VEC_VMULOUB },
6266 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_nor", ALTIVEC_BUILTIN_VEC_NOR },
6267 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_or", ALTIVEC_BUILTIN_VEC_OR },
6268 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_pack", ALTIVEC_BUILTIN_VEC_PACK },
6269 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkuwum", ALTIVEC_BUILTIN_VEC_VPKUWUM },
6270 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkuhum", ALTIVEC_BUILTIN_VEC_VPKUHUM },
6271 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_packpx", ALTIVEC_BUILTIN_VEC_PACKPX },
6272 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_packs", ALTIVEC_BUILTIN_VEC_PACKS },
6273 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkswss", ALTIVEC_BUILTIN_VEC_VPKSWSS },
6274 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkuwus", ALTIVEC_BUILTIN_VEC_VPKUWUS },
6275 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkshss", ALTIVEC_BUILTIN_VEC_VPKSHSS },
6276 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkuhus", ALTIVEC_BUILTIN_VEC_VPKUHUS },
6277 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_packsu", ALTIVEC_BUILTIN_VEC_PACKSU },
6278 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkswus", ALTIVEC_BUILTIN_VEC_VPKSWUS },
6279 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkshus", ALTIVEC_BUILTIN_VEC_VPKSHUS },
6280 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_rl", ALTIVEC_BUILTIN_VEC_RL },
6281 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vrlw", ALTIVEC_BUILTIN_VEC_VRLW },
6282 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vrlh", ALTIVEC_BUILTIN_VEC_VRLH },
6283 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vrlb", ALTIVEC_BUILTIN_VEC_VRLB },
6284 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sl", ALTIVEC_BUILTIN_VEC_SL },
6285 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vslw", ALTIVEC_BUILTIN_VEC_VSLW },
6286 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vslh", ALTIVEC_BUILTIN_VEC_VSLH },
6287 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vslb", ALTIVEC_BUILTIN_VEC_VSLB },
6288 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sll", ALTIVEC_BUILTIN_VEC_SLL },
6289 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_slo", ALTIVEC_BUILTIN_VEC_SLO },
6290 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sr", ALTIVEC_BUILTIN_VEC_SR },
6291 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsrw", ALTIVEC_BUILTIN_VEC_VSRW },
6292 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsrh", ALTIVEC_BUILTIN_VEC_VSRH },
6293 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsrb", ALTIVEC_BUILTIN_VEC_VSRB },
6294 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sra", ALTIVEC_BUILTIN_VEC_SRA },
6295 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsraw", ALTIVEC_BUILTIN_VEC_VSRAW },
6296 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsrah", ALTIVEC_BUILTIN_VEC_VSRAH },
6297 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsrab", ALTIVEC_BUILTIN_VEC_VSRAB },
6298 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_srl", ALTIVEC_BUILTIN_VEC_SRL },
6299 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sro", ALTIVEC_BUILTIN_VEC_SRO },
6300 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sub", ALTIVEC_BUILTIN_VEC_SUB },
6301 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubfp", ALTIVEC_BUILTIN_VEC_VSUBFP },
6302 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubuwm", ALTIVEC_BUILTIN_VEC_VSUBUWM },
6303 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubuhm", ALTIVEC_BUILTIN_VEC_VSUBUHM },
6304 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsububm", ALTIVEC_BUILTIN_VEC_VSUBUBM },
6305 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_subc", ALTIVEC_BUILTIN_VEC_SUBC },
6306 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_subs", ALTIVEC_BUILTIN_VEC_SUBS },
6307 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubsws", ALTIVEC_BUILTIN_VEC_VSUBSWS },
6308 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubuws", ALTIVEC_BUILTIN_VEC_VSUBUWS },
6309 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubshs", ALTIVEC_BUILTIN_VEC_VSUBSHS },
6310 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubuhs", ALTIVEC_BUILTIN_VEC_VSUBUHS },
6311 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubsbs", ALTIVEC_BUILTIN_VEC_VSUBSBS },
6312 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsububs", ALTIVEC_BUILTIN_VEC_VSUBUBS },
6313 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sum4s", ALTIVEC_BUILTIN_VEC_SUM4S },
6314 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsum4shs", ALTIVEC_BUILTIN_VEC_VSUM4SHS },
6315 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsum4sbs", ALTIVEC_BUILTIN_VEC_VSUM4SBS },
6316 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsum4ubs", ALTIVEC_BUILTIN_VEC_VSUM4UBS },
6317 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sum2s", ALTIVEC_BUILTIN_VEC_SUM2S },
6318 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sums", ALTIVEC_BUILTIN_VEC_SUMS },
6319 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_xor", ALTIVEC_BUILTIN_VEC_XOR },
6320
a3170dc6
AH
6321 /* Place holder, leave as first spe builtin. */
6322 { 0, CODE_FOR_spe_evaddw, "__builtin_spe_evaddw", SPE_BUILTIN_EVADDW },
6323 { 0, CODE_FOR_spe_evand, "__builtin_spe_evand", SPE_BUILTIN_EVAND },
6324 { 0, CODE_FOR_spe_evandc, "__builtin_spe_evandc", SPE_BUILTIN_EVANDC },
6325 { 0, CODE_FOR_spe_evdivws, "__builtin_spe_evdivws", SPE_BUILTIN_EVDIVWS },
6326 { 0, CODE_FOR_spe_evdivwu, "__builtin_spe_evdivwu", SPE_BUILTIN_EVDIVWU },
6327 { 0, CODE_FOR_spe_eveqv, "__builtin_spe_eveqv", SPE_BUILTIN_EVEQV },
6328 { 0, CODE_FOR_spe_evfsadd, "__builtin_spe_evfsadd", SPE_BUILTIN_EVFSADD },
6329 { 0, CODE_FOR_spe_evfsdiv, "__builtin_spe_evfsdiv", SPE_BUILTIN_EVFSDIV },
6330 { 0, CODE_FOR_spe_evfsmul, "__builtin_spe_evfsmul", SPE_BUILTIN_EVFSMUL },
6331 { 0, CODE_FOR_spe_evfssub, "__builtin_spe_evfssub", SPE_BUILTIN_EVFSSUB },
6332 { 0, CODE_FOR_spe_evmergehi, "__builtin_spe_evmergehi", SPE_BUILTIN_EVMERGEHI },
6333 { 0, CODE_FOR_spe_evmergehilo, "__builtin_spe_evmergehilo", SPE_BUILTIN_EVMERGEHILO },
6334 { 0, CODE_FOR_spe_evmergelo, "__builtin_spe_evmergelo", SPE_BUILTIN_EVMERGELO },
6335 { 0, CODE_FOR_spe_evmergelohi, "__builtin_spe_evmergelohi", SPE_BUILTIN_EVMERGELOHI },
6336 { 0, CODE_FOR_spe_evmhegsmfaa, "__builtin_spe_evmhegsmfaa", SPE_BUILTIN_EVMHEGSMFAA },
6337 { 0, CODE_FOR_spe_evmhegsmfan, "__builtin_spe_evmhegsmfan", SPE_BUILTIN_EVMHEGSMFAN },
6338 { 0, CODE_FOR_spe_evmhegsmiaa, "__builtin_spe_evmhegsmiaa", SPE_BUILTIN_EVMHEGSMIAA },
6339 { 0, CODE_FOR_spe_evmhegsmian, "__builtin_spe_evmhegsmian", SPE_BUILTIN_EVMHEGSMIAN },
6340 { 0, CODE_FOR_spe_evmhegumiaa, "__builtin_spe_evmhegumiaa", SPE_BUILTIN_EVMHEGUMIAA },
6341 { 0, CODE_FOR_spe_evmhegumian, "__builtin_spe_evmhegumian", SPE_BUILTIN_EVMHEGUMIAN },
6342 { 0, CODE_FOR_spe_evmhesmf, "__builtin_spe_evmhesmf", SPE_BUILTIN_EVMHESMF },
6343 { 0, CODE_FOR_spe_evmhesmfa, "__builtin_spe_evmhesmfa", SPE_BUILTIN_EVMHESMFA },
6344 { 0, CODE_FOR_spe_evmhesmfaaw, "__builtin_spe_evmhesmfaaw", SPE_BUILTIN_EVMHESMFAAW },
6345 { 0, CODE_FOR_spe_evmhesmfanw, "__builtin_spe_evmhesmfanw", SPE_BUILTIN_EVMHESMFANW },
6346 { 0, CODE_FOR_spe_evmhesmi, "__builtin_spe_evmhesmi", SPE_BUILTIN_EVMHESMI },
6347 { 0, CODE_FOR_spe_evmhesmia, "__builtin_spe_evmhesmia", SPE_BUILTIN_EVMHESMIA },
6348 { 0, CODE_FOR_spe_evmhesmiaaw, "__builtin_spe_evmhesmiaaw", SPE_BUILTIN_EVMHESMIAAW },
6349 { 0, CODE_FOR_spe_evmhesmianw, "__builtin_spe_evmhesmianw", SPE_BUILTIN_EVMHESMIANW },
6350 { 0, CODE_FOR_spe_evmhessf, "__builtin_spe_evmhessf", SPE_BUILTIN_EVMHESSF },
6351 { 0, CODE_FOR_spe_evmhessfa, "__builtin_spe_evmhessfa", SPE_BUILTIN_EVMHESSFA },
6352 { 0, CODE_FOR_spe_evmhessfaaw, "__builtin_spe_evmhessfaaw", SPE_BUILTIN_EVMHESSFAAW },
6353 { 0, CODE_FOR_spe_evmhessfanw, "__builtin_spe_evmhessfanw", SPE_BUILTIN_EVMHESSFANW },
6354 { 0, CODE_FOR_spe_evmhessiaaw, "__builtin_spe_evmhessiaaw", SPE_BUILTIN_EVMHESSIAAW },
6355 { 0, CODE_FOR_spe_evmhessianw, "__builtin_spe_evmhessianw", SPE_BUILTIN_EVMHESSIANW },
6356 { 0, CODE_FOR_spe_evmheumi, "__builtin_spe_evmheumi", SPE_BUILTIN_EVMHEUMI },
6357 { 0, CODE_FOR_spe_evmheumia, "__builtin_spe_evmheumia", SPE_BUILTIN_EVMHEUMIA },
6358 { 0, CODE_FOR_spe_evmheumiaaw, "__builtin_spe_evmheumiaaw", SPE_BUILTIN_EVMHEUMIAAW },
6359 { 0, CODE_FOR_spe_evmheumianw, "__builtin_spe_evmheumianw", SPE_BUILTIN_EVMHEUMIANW },
6360 { 0, CODE_FOR_spe_evmheusiaaw, "__builtin_spe_evmheusiaaw", SPE_BUILTIN_EVMHEUSIAAW },
6361 { 0, CODE_FOR_spe_evmheusianw, "__builtin_spe_evmheusianw", SPE_BUILTIN_EVMHEUSIANW },
6362 { 0, CODE_FOR_spe_evmhogsmfaa, "__builtin_spe_evmhogsmfaa", SPE_BUILTIN_EVMHOGSMFAA },
6363 { 0, CODE_FOR_spe_evmhogsmfan, "__builtin_spe_evmhogsmfan", SPE_BUILTIN_EVMHOGSMFAN },
6364 { 0, CODE_FOR_spe_evmhogsmiaa, "__builtin_spe_evmhogsmiaa", SPE_BUILTIN_EVMHOGSMIAA },
6365 { 0, CODE_FOR_spe_evmhogsmian, "__builtin_spe_evmhogsmian", SPE_BUILTIN_EVMHOGSMIAN },
6366 { 0, CODE_FOR_spe_evmhogumiaa, "__builtin_spe_evmhogumiaa", SPE_BUILTIN_EVMHOGUMIAA },
6367 { 0, CODE_FOR_spe_evmhogumian, "__builtin_spe_evmhogumian", SPE_BUILTIN_EVMHOGUMIAN },
6368 { 0, CODE_FOR_spe_evmhosmf, "__builtin_spe_evmhosmf", SPE_BUILTIN_EVMHOSMF },
6369 { 0, CODE_FOR_spe_evmhosmfa, "__builtin_spe_evmhosmfa", SPE_BUILTIN_EVMHOSMFA },
6370 { 0, CODE_FOR_spe_evmhosmfaaw, "__builtin_spe_evmhosmfaaw", SPE_BUILTIN_EVMHOSMFAAW },
6371 { 0, CODE_FOR_spe_evmhosmfanw, "__builtin_spe_evmhosmfanw", SPE_BUILTIN_EVMHOSMFANW },
6372 { 0, CODE_FOR_spe_evmhosmi, "__builtin_spe_evmhosmi", SPE_BUILTIN_EVMHOSMI },
6373 { 0, CODE_FOR_spe_evmhosmia, "__builtin_spe_evmhosmia", SPE_BUILTIN_EVMHOSMIA },
6374 { 0, CODE_FOR_spe_evmhosmiaaw, "__builtin_spe_evmhosmiaaw", SPE_BUILTIN_EVMHOSMIAAW },
6375 { 0, CODE_FOR_spe_evmhosmianw, "__builtin_spe_evmhosmianw", SPE_BUILTIN_EVMHOSMIANW },
6376 { 0, CODE_FOR_spe_evmhossf, "__builtin_spe_evmhossf", SPE_BUILTIN_EVMHOSSF },
6377 { 0, CODE_FOR_spe_evmhossfa, "__builtin_spe_evmhossfa", SPE_BUILTIN_EVMHOSSFA },
6378 { 0, CODE_FOR_spe_evmhossfaaw, "__builtin_spe_evmhossfaaw", SPE_BUILTIN_EVMHOSSFAAW },
6379 { 0, CODE_FOR_spe_evmhossfanw, "__builtin_spe_evmhossfanw", SPE_BUILTIN_EVMHOSSFANW },
6380 { 0, CODE_FOR_spe_evmhossiaaw, "__builtin_spe_evmhossiaaw", SPE_BUILTIN_EVMHOSSIAAW },
6381 { 0, CODE_FOR_spe_evmhossianw, "__builtin_spe_evmhossianw", SPE_BUILTIN_EVMHOSSIANW },
6382 { 0, CODE_FOR_spe_evmhoumi, "__builtin_spe_evmhoumi", SPE_BUILTIN_EVMHOUMI },
6383 { 0, CODE_FOR_spe_evmhoumia, "__builtin_spe_evmhoumia", SPE_BUILTIN_EVMHOUMIA },
6384 { 0, CODE_FOR_spe_evmhoumiaaw, "__builtin_spe_evmhoumiaaw", SPE_BUILTIN_EVMHOUMIAAW },
6385 { 0, CODE_FOR_spe_evmhoumianw, "__builtin_spe_evmhoumianw", SPE_BUILTIN_EVMHOUMIANW },
6386 { 0, CODE_FOR_spe_evmhousiaaw, "__builtin_spe_evmhousiaaw", SPE_BUILTIN_EVMHOUSIAAW },
6387 { 0, CODE_FOR_spe_evmhousianw, "__builtin_spe_evmhousianw", SPE_BUILTIN_EVMHOUSIANW },
6388 { 0, CODE_FOR_spe_evmwhsmf, "__builtin_spe_evmwhsmf", SPE_BUILTIN_EVMWHSMF },
6389 { 0, CODE_FOR_spe_evmwhsmfa, "__builtin_spe_evmwhsmfa", SPE_BUILTIN_EVMWHSMFA },
6390 { 0, CODE_FOR_spe_evmwhsmi, "__builtin_spe_evmwhsmi", SPE_BUILTIN_EVMWHSMI },
6391 { 0, CODE_FOR_spe_evmwhsmia, "__builtin_spe_evmwhsmia", SPE_BUILTIN_EVMWHSMIA },
6392 { 0, CODE_FOR_spe_evmwhssf, "__builtin_spe_evmwhssf", SPE_BUILTIN_EVMWHSSF },
6393 { 0, CODE_FOR_spe_evmwhssfa, "__builtin_spe_evmwhssfa", SPE_BUILTIN_EVMWHSSFA },
6394 { 0, CODE_FOR_spe_evmwhumi, "__builtin_spe_evmwhumi", SPE_BUILTIN_EVMWHUMI },
6395 { 0, CODE_FOR_spe_evmwhumia, "__builtin_spe_evmwhumia", SPE_BUILTIN_EVMWHUMIA },
a3170dc6
AH
6396 { 0, CODE_FOR_spe_evmwlsmiaaw, "__builtin_spe_evmwlsmiaaw", SPE_BUILTIN_EVMWLSMIAAW },
6397 { 0, CODE_FOR_spe_evmwlsmianw, "__builtin_spe_evmwlsmianw", SPE_BUILTIN_EVMWLSMIANW },
a3170dc6
AH
6398 { 0, CODE_FOR_spe_evmwlssiaaw, "__builtin_spe_evmwlssiaaw", SPE_BUILTIN_EVMWLSSIAAW },
6399 { 0, CODE_FOR_spe_evmwlssianw, "__builtin_spe_evmwlssianw", SPE_BUILTIN_EVMWLSSIANW },
6400 { 0, CODE_FOR_spe_evmwlumi, "__builtin_spe_evmwlumi", SPE_BUILTIN_EVMWLUMI },
6401 { 0, CODE_FOR_spe_evmwlumia, "__builtin_spe_evmwlumia", SPE_BUILTIN_EVMWLUMIA },
6402 { 0, CODE_FOR_spe_evmwlumiaaw, "__builtin_spe_evmwlumiaaw", SPE_BUILTIN_EVMWLUMIAAW },
6403 { 0, CODE_FOR_spe_evmwlumianw, "__builtin_spe_evmwlumianw", SPE_BUILTIN_EVMWLUMIANW },
6404 { 0, CODE_FOR_spe_evmwlusiaaw, "__builtin_spe_evmwlusiaaw", SPE_BUILTIN_EVMWLUSIAAW },
6405 { 0, CODE_FOR_spe_evmwlusianw, "__builtin_spe_evmwlusianw", SPE_BUILTIN_EVMWLUSIANW },
6406 { 0, CODE_FOR_spe_evmwsmf, "__builtin_spe_evmwsmf", SPE_BUILTIN_EVMWSMF },
6407 { 0, CODE_FOR_spe_evmwsmfa, "__builtin_spe_evmwsmfa", SPE_BUILTIN_EVMWSMFA },
6408 { 0, CODE_FOR_spe_evmwsmfaa, "__builtin_spe_evmwsmfaa", SPE_BUILTIN_EVMWSMFAA },
6409 { 0, CODE_FOR_spe_evmwsmfan, "__builtin_spe_evmwsmfan", SPE_BUILTIN_EVMWSMFAN },
6410 { 0, CODE_FOR_spe_evmwsmi, "__builtin_spe_evmwsmi", SPE_BUILTIN_EVMWSMI },
6411 { 0, CODE_FOR_spe_evmwsmia, "__builtin_spe_evmwsmia", SPE_BUILTIN_EVMWSMIA },
6412 { 0, CODE_FOR_spe_evmwsmiaa, "__builtin_spe_evmwsmiaa", SPE_BUILTIN_EVMWSMIAA },
6413 { 0, CODE_FOR_spe_evmwsmian, "__builtin_spe_evmwsmian", SPE_BUILTIN_EVMWSMIAN },
6414 { 0, CODE_FOR_spe_evmwssf, "__builtin_spe_evmwssf", SPE_BUILTIN_EVMWSSF },
6415 { 0, CODE_FOR_spe_evmwssfa, "__builtin_spe_evmwssfa", SPE_BUILTIN_EVMWSSFA },
6416 { 0, CODE_FOR_spe_evmwssfaa, "__builtin_spe_evmwssfaa", SPE_BUILTIN_EVMWSSFAA },
6417 { 0, CODE_FOR_spe_evmwssfan, "__builtin_spe_evmwssfan", SPE_BUILTIN_EVMWSSFAN },
6418 { 0, CODE_FOR_spe_evmwumi, "__builtin_spe_evmwumi", SPE_BUILTIN_EVMWUMI },
6419 { 0, CODE_FOR_spe_evmwumia, "__builtin_spe_evmwumia", SPE_BUILTIN_EVMWUMIA },
6420 { 0, CODE_FOR_spe_evmwumiaa, "__builtin_spe_evmwumiaa", SPE_BUILTIN_EVMWUMIAA },
6421 { 0, CODE_FOR_spe_evmwumian, "__builtin_spe_evmwumian", SPE_BUILTIN_EVMWUMIAN },
6422 { 0, CODE_FOR_spe_evnand, "__builtin_spe_evnand", SPE_BUILTIN_EVNAND },
6423 { 0, CODE_FOR_spe_evnor, "__builtin_spe_evnor", SPE_BUILTIN_EVNOR },
6424 { 0, CODE_FOR_spe_evor, "__builtin_spe_evor", SPE_BUILTIN_EVOR },
6425 { 0, CODE_FOR_spe_evorc, "__builtin_spe_evorc", SPE_BUILTIN_EVORC },
6426 { 0, CODE_FOR_spe_evrlw, "__builtin_spe_evrlw", SPE_BUILTIN_EVRLW },
6427 { 0, CODE_FOR_spe_evslw, "__builtin_spe_evslw", SPE_BUILTIN_EVSLW },
6428 { 0, CODE_FOR_spe_evsrws, "__builtin_spe_evsrws", SPE_BUILTIN_EVSRWS },
6429 { 0, CODE_FOR_spe_evsrwu, "__builtin_spe_evsrwu", SPE_BUILTIN_EVSRWU },
6430 { 0, CODE_FOR_spe_evsubfw, "__builtin_spe_evsubfw", SPE_BUILTIN_EVSUBFW },
6431
6432 /* SPE binary operations expecting a 5-bit unsigned literal. */
6433 { 0, CODE_FOR_spe_evaddiw, "__builtin_spe_evaddiw", SPE_BUILTIN_EVADDIW },
6434
6435 { 0, CODE_FOR_spe_evrlwi, "__builtin_spe_evrlwi", SPE_BUILTIN_EVRLWI },
6436 { 0, CODE_FOR_spe_evslwi, "__builtin_spe_evslwi", SPE_BUILTIN_EVSLWI },
6437 { 0, CODE_FOR_spe_evsrwis, "__builtin_spe_evsrwis", SPE_BUILTIN_EVSRWIS },
6438 { 0, CODE_FOR_spe_evsrwiu, "__builtin_spe_evsrwiu", SPE_BUILTIN_EVSRWIU },
6439 { 0, CODE_FOR_spe_evsubifw, "__builtin_spe_evsubifw", SPE_BUILTIN_EVSUBIFW },
6440 { 0, CODE_FOR_spe_evmwhssfaa, "__builtin_spe_evmwhssfaa", SPE_BUILTIN_EVMWHSSFAA },
6441 { 0, CODE_FOR_spe_evmwhssmaa, "__builtin_spe_evmwhssmaa", SPE_BUILTIN_EVMWHSSMAA },
6442 { 0, CODE_FOR_spe_evmwhsmfaa, "__builtin_spe_evmwhsmfaa", SPE_BUILTIN_EVMWHSMFAA },
6443 { 0, CODE_FOR_spe_evmwhsmiaa, "__builtin_spe_evmwhsmiaa", SPE_BUILTIN_EVMWHSMIAA },
6444 { 0, CODE_FOR_spe_evmwhusiaa, "__builtin_spe_evmwhusiaa", SPE_BUILTIN_EVMWHUSIAA },
6445 { 0, CODE_FOR_spe_evmwhumiaa, "__builtin_spe_evmwhumiaa", SPE_BUILTIN_EVMWHUMIAA },
6446 { 0, CODE_FOR_spe_evmwhssfan, "__builtin_spe_evmwhssfan", SPE_BUILTIN_EVMWHSSFAN },
6447 { 0, CODE_FOR_spe_evmwhssian, "__builtin_spe_evmwhssian", SPE_BUILTIN_EVMWHSSIAN },
6448 { 0, CODE_FOR_spe_evmwhsmfan, "__builtin_spe_evmwhsmfan", SPE_BUILTIN_EVMWHSMFAN },
6449 { 0, CODE_FOR_spe_evmwhsmian, "__builtin_spe_evmwhsmian", SPE_BUILTIN_EVMWHSMIAN },
6450 { 0, CODE_FOR_spe_evmwhusian, "__builtin_spe_evmwhusian", SPE_BUILTIN_EVMWHUSIAN },
6451 { 0, CODE_FOR_spe_evmwhumian, "__builtin_spe_evmwhumian", SPE_BUILTIN_EVMWHUMIAN },
6452 { 0, CODE_FOR_spe_evmwhgssfaa, "__builtin_spe_evmwhgssfaa", SPE_BUILTIN_EVMWHGSSFAA },
6453 { 0, CODE_FOR_spe_evmwhgsmfaa, "__builtin_spe_evmwhgsmfaa", SPE_BUILTIN_EVMWHGSMFAA },
6454 { 0, CODE_FOR_spe_evmwhgsmiaa, "__builtin_spe_evmwhgsmiaa", SPE_BUILTIN_EVMWHGSMIAA },
6455 { 0, CODE_FOR_spe_evmwhgumiaa, "__builtin_spe_evmwhgumiaa", SPE_BUILTIN_EVMWHGUMIAA },
6456 { 0, CODE_FOR_spe_evmwhgssfan, "__builtin_spe_evmwhgssfan", SPE_BUILTIN_EVMWHGSSFAN },
6457 { 0, CODE_FOR_spe_evmwhgsmfan, "__builtin_spe_evmwhgsmfan", SPE_BUILTIN_EVMWHGSMFAN },
6458 { 0, CODE_FOR_spe_evmwhgsmian, "__builtin_spe_evmwhgsmian", SPE_BUILTIN_EVMWHGSMIAN },
6459 { 0, CODE_FOR_spe_evmwhgumian, "__builtin_spe_evmwhgumian", SPE_BUILTIN_EVMWHGUMIAN },
6460 { 0, CODE_FOR_spe_brinc, "__builtin_spe_brinc", SPE_BUILTIN_BRINC },
6461
6462 /* Place-holder. Leave as last binary SPE builtin. */
58646b77 6463 { 0, CODE_FOR_xorv2si3, "__builtin_spe_evxor", SPE_BUILTIN_EVXOR }
ae4b4a02
AH
6464};
6465
6466/* AltiVec predicates. */
6467
6468struct builtin_description_predicates
6469{
6470 const unsigned int mask;
6471 const enum insn_code icode;
6472 const char *opcode;
6473 const char *const name;
6474 const enum rs6000_builtins code;
6475};
6476
6477static const struct builtin_description_predicates bdesc_altivec_preds[] =
6478{
6479 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v4sf, "*vcmpbfp.", "__builtin_altivec_vcmpbfp_p", ALTIVEC_BUILTIN_VCMPBFP_P },
6480 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v4sf, "*vcmpeqfp.", "__builtin_altivec_vcmpeqfp_p", ALTIVEC_BUILTIN_VCMPEQFP_P },
6481 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v4sf, "*vcmpgefp.", "__builtin_altivec_vcmpgefp_p", ALTIVEC_BUILTIN_VCMPGEFP_P },
6482 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v4sf, "*vcmpgtfp.", "__builtin_altivec_vcmpgtfp_p", ALTIVEC_BUILTIN_VCMPGTFP_P },
6483 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v4si, "*vcmpequw.", "__builtin_altivec_vcmpequw_p", ALTIVEC_BUILTIN_VCMPEQUW_P },
6484 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v4si, "*vcmpgtsw.", "__builtin_altivec_vcmpgtsw_p", ALTIVEC_BUILTIN_VCMPGTSW_P },
6485 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v4si, "*vcmpgtuw.", "__builtin_altivec_vcmpgtuw_p", ALTIVEC_BUILTIN_VCMPGTUW_P },
6486 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v8hi, "*vcmpgtuh.", "__builtin_altivec_vcmpgtuh_p", ALTIVEC_BUILTIN_VCMPGTUH_P },
6487 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v8hi, "*vcmpgtsh.", "__builtin_altivec_vcmpgtsh_p", ALTIVEC_BUILTIN_VCMPGTSH_P },
6488 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v8hi, "*vcmpequh.", "__builtin_altivec_vcmpequh_p", ALTIVEC_BUILTIN_VCMPEQUH_P },
6489 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v16qi, "*vcmpequb.", "__builtin_altivec_vcmpequb_p", ALTIVEC_BUILTIN_VCMPEQUB_P },
6490 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v16qi, "*vcmpgtsb.", "__builtin_altivec_vcmpgtsb_p", ALTIVEC_BUILTIN_VCMPGTSB_P },
58646b77
PB
6491 { MASK_ALTIVEC, CODE_FOR_altivec_predicate_v16qi, "*vcmpgtub.", "__builtin_altivec_vcmpgtub_p", ALTIVEC_BUILTIN_VCMPGTUB_P },
6492
6493 { MASK_ALTIVEC, 0, NULL, "__builtin_vec_vcmpeq_p", ALTIVEC_BUILTIN_VCMPEQ_P },
6494 { MASK_ALTIVEC, 0, NULL, "__builtin_vec_vcmpgt_p", ALTIVEC_BUILTIN_VCMPGT_P },
6495 { MASK_ALTIVEC, 0, NULL, "__builtin_vec_vcmpge_p", ALTIVEC_BUILTIN_VCMPGE_P }
0ac081f6 6496};
24408032 6497
a3170dc6
AH
6498/* SPE predicates. */
6499static struct builtin_description bdesc_spe_predicates[] =
6500{
6501 /* Place-holder. Leave as first. */
6502 { 0, CODE_FOR_spe_evcmpeq, "__builtin_spe_evcmpeq", SPE_BUILTIN_EVCMPEQ },
6503 { 0, CODE_FOR_spe_evcmpgts, "__builtin_spe_evcmpgts", SPE_BUILTIN_EVCMPGTS },
6504 { 0, CODE_FOR_spe_evcmpgtu, "__builtin_spe_evcmpgtu", SPE_BUILTIN_EVCMPGTU },
6505 { 0, CODE_FOR_spe_evcmplts, "__builtin_spe_evcmplts", SPE_BUILTIN_EVCMPLTS },
6506 { 0, CODE_FOR_spe_evcmpltu, "__builtin_spe_evcmpltu", SPE_BUILTIN_EVCMPLTU },
6507 { 0, CODE_FOR_spe_evfscmpeq, "__builtin_spe_evfscmpeq", SPE_BUILTIN_EVFSCMPEQ },
6508 { 0, CODE_FOR_spe_evfscmpgt, "__builtin_spe_evfscmpgt", SPE_BUILTIN_EVFSCMPGT },
6509 { 0, CODE_FOR_spe_evfscmplt, "__builtin_spe_evfscmplt", SPE_BUILTIN_EVFSCMPLT },
6510 { 0, CODE_FOR_spe_evfststeq, "__builtin_spe_evfststeq", SPE_BUILTIN_EVFSTSTEQ },
6511 { 0, CODE_FOR_spe_evfststgt, "__builtin_spe_evfststgt", SPE_BUILTIN_EVFSTSTGT },
6512 /* Place-holder. Leave as last. */
6513 { 0, CODE_FOR_spe_evfststlt, "__builtin_spe_evfststlt", SPE_BUILTIN_EVFSTSTLT },
6514};
6515
6516/* SPE evsel predicates. */
6517static struct builtin_description bdesc_spe_evsel[] =
6518{
6519 /* Place-holder. Leave as first. */
6520 { 0, CODE_FOR_spe_evcmpgts, "__builtin_spe_evsel_gts", SPE_BUILTIN_EVSEL_CMPGTS },
6521 { 0, CODE_FOR_spe_evcmpgtu, "__builtin_spe_evsel_gtu", SPE_BUILTIN_EVSEL_CMPGTU },
6522 { 0, CODE_FOR_spe_evcmplts, "__builtin_spe_evsel_lts", SPE_BUILTIN_EVSEL_CMPLTS },
6523 { 0, CODE_FOR_spe_evcmpltu, "__builtin_spe_evsel_ltu", SPE_BUILTIN_EVSEL_CMPLTU },
6524 { 0, CODE_FOR_spe_evcmpeq, "__builtin_spe_evsel_eq", SPE_BUILTIN_EVSEL_CMPEQ },
6525 { 0, CODE_FOR_spe_evfscmpgt, "__builtin_spe_evsel_fsgt", SPE_BUILTIN_EVSEL_FSCMPGT },
6526 { 0, CODE_FOR_spe_evfscmplt, "__builtin_spe_evsel_fslt", SPE_BUILTIN_EVSEL_FSCMPLT },
6527 { 0, CODE_FOR_spe_evfscmpeq, "__builtin_spe_evsel_fseq", SPE_BUILTIN_EVSEL_FSCMPEQ },
6528 { 0, CODE_FOR_spe_evfststgt, "__builtin_spe_evsel_fststgt", SPE_BUILTIN_EVSEL_FSTSTGT },
6529 { 0, CODE_FOR_spe_evfststlt, "__builtin_spe_evsel_fststlt", SPE_BUILTIN_EVSEL_FSTSTLT },
6530 /* Place-holder. Leave as last. */
6531 { 0, CODE_FOR_spe_evfststeq, "__builtin_spe_evsel_fststeq", SPE_BUILTIN_EVSEL_FSTSTEQ },
6532};
6533
b6d08ca1 6534/* ABS* operations. */
100c4561
AH
6535
6536static const struct builtin_description bdesc_abs[] =
6537{
6538 { MASK_ALTIVEC, CODE_FOR_absv4si2, "__builtin_altivec_abs_v4si", ALTIVEC_BUILTIN_ABS_V4SI },
6539 { MASK_ALTIVEC, CODE_FOR_absv8hi2, "__builtin_altivec_abs_v8hi", ALTIVEC_BUILTIN_ABS_V8HI },
6540 { MASK_ALTIVEC, CODE_FOR_absv4sf2, "__builtin_altivec_abs_v4sf", ALTIVEC_BUILTIN_ABS_V4SF },
6541 { MASK_ALTIVEC, CODE_FOR_absv16qi2, "__builtin_altivec_abs_v16qi", ALTIVEC_BUILTIN_ABS_V16QI },
6542 { MASK_ALTIVEC, CODE_FOR_altivec_abss_v4si, "__builtin_altivec_abss_v4si", ALTIVEC_BUILTIN_ABSS_V4SI },
6543 { MASK_ALTIVEC, CODE_FOR_altivec_abss_v8hi, "__builtin_altivec_abss_v8hi", ALTIVEC_BUILTIN_ABSS_V8HI },
6544 { MASK_ALTIVEC, CODE_FOR_altivec_abss_v16qi, "__builtin_altivec_abss_v16qi", ALTIVEC_BUILTIN_ABSS_V16QI }
6545};
6546
617e0e1d
DB
6547/* Simple unary operations: VECb = foo (unsigned literal) or VECb =
6548 foo (VECa). */
24408032 6549
a3170dc6 6550static struct builtin_description bdesc_1arg[] =
2212663f 6551{
617e0e1d
DB
6552 { MASK_ALTIVEC, CODE_FOR_altivec_vexptefp, "__builtin_altivec_vexptefp", ALTIVEC_BUILTIN_VEXPTEFP },
6553 { MASK_ALTIVEC, CODE_FOR_altivec_vlogefp, "__builtin_altivec_vlogefp", ALTIVEC_BUILTIN_VLOGEFP },
6554 { MASK_ALTIVEC, CODE_FOR_altivec_vrefp, "__builtin_altivec_vrefp", ALTIVEC_BUILTIN_VREFP },
6555 { MASK_ALTIVEC, CODE_FOR_altivec_vrfim, "__builtin_altivec_vrfim", ALTIVEC_BUILTIN_VRFIM },
6556 { MASK_ALTIVEC, CODE_FOR_altivec_vrfin, "__builtin_altivec_vrfin", ALTIVEC_BUILTIN_VRFIN },
6557 { MASK_ALTIVEC, CODE_FOR_altivec_vrfip, "__builtin_altivec_vrfip", ALTIVEC_BUILTIN_VRFIP },
6558 { MASK_ALTIVEC, CODE_FOR_ftruncv4sf2, "__builtin_altivec_vrfiz", ALTIVEC_BUILTIN_VRFIZ },
6559 { MASK_ALTIVEC, CODE_FOR_altivec_vrsqrtefp, "__builtin_altivec_vrsqrtefp", ALTIVEC_BUILTIN_VRSQRTEFP },
2212663f
DB
6560 { MASK_ALTIVEC, CODE_FOR_altivec_vspltisb, "__builtin_altivec_vspltisb", ALTIVEC_BUILTIN_VSPLTISB },
6561 { MASK_ALTIVEC, CODE_FOR_altivec_vspltish, "__builtin_altivec_vspltish", ALTIVEC_BUILTIN_VSPLTISH },
6562 { MASK_ALTIVEC, CODE_FOR_altivec_vspltisw, "__builtin_altivec_vspltisw", ALTIVEC_BUILTIN_VSPLTISW },
20e26713
AH
6563 { MASK_ALTIVEC, CODE_FOR_altivec_vupkhsb, "__builtin_altivec_vupkhsb", ALTIVEC_BUILTIN_VUPKHSB },
6564 { MASK_ALTIVEC, CODE_FOR_altivec_vupkhpx, "__builtin_altivec_vupkhpx", ALTIVEC_BUILTIN_VUPKHPX },
6565 { MASK_ALTIVEC, CODE_FOR_altivec_vupkhsh, "__builtin_altivec_vupkhsh", ALTIVEC_BUILTIN_VUPKHSH },
6566 { MASK_ALTIVEC, CODE_FOR_altivec_vupklsb, "__builtin_altivec_vupklsb", ALTIVEC_BUILTIN_VUPKLSB },
6567 { MASK_ALTIVEC, CODE_FOR_altivec_vupklpx, "__builtin_altivec_vupklpx", ALTIVEC_BUILTIN_VUPKLPX },
6568 { MASK_ALTIVEC, CODE_FOR_altivec_vupklsh, "__builtin_altivec_vupklsh", ALTIVEC_BUILTIN_VUPKLSH },
a3170dc6 6569
58646b77
PB
6570 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_abs", ALTIVEC_BUILTIN_VEC_ABS },
6571 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_abss", ALTIVEC_BUILTIN_VEC_ABSS },
6572 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_ceil", ALTIVEC_BUILTIN_VEC_CEIL },
6573 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_expte", ALTIVEC_BUILTIN_VEC_EXPTE },
6574 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_floor", ALTIVEC_BUILTIN_VEC_FLOOR },
6575 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_loge", ALTIVEC_BUILTIN_VEC_LOGE },
6576 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mtvscr", ALTIVEC_BUILTIN_VEC_MTVSCR },
6577 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_re", ALTIVEC_BUILTIN_VEC_RE },
6578 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_round", ALTIVEC_BUILTIN_VEC_ROUND },
6579 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_rsqrte", ALTIVEC_BUILTIN_VEC_RSQRTE },
6580 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_trunc", ALTIVEC_BUILTIN_VEC_TRUNC },
6581 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_unpackh", ALTIVEC_BUILTIN_VEC_UNPACKH },
6582 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vupkhsh", ALTIVEC_BUILTIN_VEC_VUPKHSH },
6583 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vupkhpx", ALTIVEC_BUILTIN_VEC_VUPKHPX },
6584 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vupkhsb", ALTIVEC_BUILTIN_VEC_VUPKHSB },
6585 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_unpackl", ALTIVEC_BUILTIN_VEC_UNPACKL },
6586 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vupklpx", ALTIVEC_BUILTIN_VEC_VUPKLPX },
6587 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vupklsh", ALTIVEC_BUILTIN_VEC_VUPKLSH },
6588 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vupklsb", ALTIVEC_BUILTIN_VEC_VUPKLSB },
6589
a3170dc6
AH
6590 /* The SPE unary builtins must start with SPE_BUILTIN_EVABS and
6591 end with SPE_BUILTIN_EVSUBFUSIAAW. */
6592 { 0, CODE_FOR_spe_evabs, "__builtin_spe_evabs", SPE_BUILTIN_EVABS },
6593 { 0, CODE_FOR_spe_evaddsmiaaw, "__builtin_spe_evaddsmiaaw", SPE_BUILTIN_EVADDSMIAAW },
6594 { 0, CODE_FOR_spe_evaddssiaaw, "__builtin_spe_evaddssiaaw", SPE_BUILTIN_EVADDSSIAAW },
6595 { 0, CODE_FOR_spe_evaddumiaaw, "__builtin_spe_evaddumiaaw", SPE_BUILTIN_EVADDUMIAAW },
6596 { 0, CODE_FOR_spe_evaddusiaaw, "__builtin_spe_evaddusiaaw", SPE_BUILTIN_EVADDUSIAAW },
6597 { 0, CODE_FOR_spe_evcntlsw, "__builtin_spe_evcntlsw", SPE_BUILTIN_EVCNTLSW },
6598 { 0, CODE_FOR_spe_evcntlzw, "__builtin_spe_evcntlzw", SPE_BUILTIN_EVCNTLZW },
6599 { 0, CODE_FOR_spe_evextsb, "__builtin_spe_evextsb", SPE_BUILTIN_EVEXTSB },
6600 { 0, CODE_FOR_spe_evextsh, "__builtin_spe_evextsh", SPE_BUILTIN_EVEXTSH },
6601 { 0, CODE_FOR_spe_evfsabs, "__builtin_spe_evfsabs", SPE_BUILTIN_EVFSABS },
6602 { 0, CODE_FOR_spe_evfscfsf, "__builtin_spe_evfscfsf", SPE_BUILTIN_EVFSCFSF },
6603 { 0, CODE_FOR_spe_evfscfsi, "__builtin_spe_evfscfsi", SPE_BUILTIN_EVFSCFSI },
6604 { 0, CODE_FOR_spe_evfscfuf, "__builtin_spe_evfscfuf", SPE_BUILTIN_EVFSCFUF },
6605 { 0, CODE_FOR_spe_evfscfui, "__builtin_spe_evfscfui", SPE_BUILTIN_EVFSCFUI },
6606 { 0, CODE_FOR_spe_evfsctsf, "__builtin_spe_evfsctsf", SPE_BUILTIN_EVFSCTSF },
6607 { 0, CODE_FOR_spe_evfsctsi, "__builtin_spe_evfsctsi", SPE_BUILTIN_EVFSCTSI },
6608 { 0, CODE_FOR_spe_evfsctsiz, "__builtin_spe_evfsctsiz", SPE_BUILTIN_EVFSCTSIZ },
6609 { 0, CODE_FOR_spe_evfsctuf, "__builtin_spe_evfsctuf", SPE_BUILTIN_EVFSCTUF },
6610 { 0, CODE_FOR_spe_evfsctui, "__builtin_spe_evfsctui", SPE_BUILTIN_EVFSCTUI },
6611 { 0, CODE_FOR_spe_evfsctuiz, "__builtin_spe_evfsctuiz", SPE_BUILTIN_EVFSCTUIZ },
6612 { 0, CODE_FOR_spe_evfsnabs, "__builtin_spe_evfsnabs", SPE_BUILTIN_EVFSNABS },
6613 { 0, CODE_FOR_spe_evfsneg, "__builtin_spe_evfsneg", SPE_BUILTIN_EVFSNEG },
6614 { 0, CODE_FOR_spe_evmra, "__builtin_spe_evmra", SPE_BUILTIN_EVMRA },
6a599451 6615 { 0, CODE_FOR_negv2si2, "__builtin_spe_evneg", SPE_BUILTIN_EVNEG },
a3170dc6
AH
6616 { 0, CODE_FOR_spe_evrndw, "__builtin_spe_evrndw", SPE_BUILTIN_EVRNDW },
6617 { 0, CODE_FOR_spe_evsubfsmiaaw, "__builtin_spe_evsubfsmiaaw", SPE_BUILTIN_EVSUBFSMIAAW },
6618 { 0, CODE_FOR_spe_evsubfssiaaw, "__builtin_spe_evsubfssiaaw", SPE_BUILTIN_EVSUBFSSIAAW },
6619 { 0, CODE_FOR_spe_evsubfumiaaw, "__builtin_spe_evsubfumiaaw", SPE_BUILTIN_EVSUBFUMIAAW },
a3170dc6
AH
6620
6621 /* Place-holder. Leave as last unary SPE builtin. */
58646b77 6622 { 0, CODE_FOR_spe_evsubfusiaaw, "__builtin_spe_evsubfusiaaw", SPE_BUILTIN_EVSUBFUSIAAW }
2212663f
DB
6623};
6624
6625static rtx
a2369ed3 6626rs6000_expand_unop_builtin (enum insn_code icode, tree arglist, rtx target)
2212663f
DB
6627{
6628 rtx pat;
6629 tree arg0 = TREE_VALUE (arglist);
84217346 6630 rtx op0 = expand_normal (arg0);
2212663f
DB
6631 enum machine_mode tmode = insn_data[icode].operand[0].mode;
6632 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
6633
0559cc77
DE
6634 if (icode == CODE_FOR_nothing)
6635 /* Builtin not supported on this processor. */
6636 return 0;
6637
20e26713
AH
6638 /* If we got invalid arguments bail out before generating bad rtl. */
6639 if (arg0 == error_mark_node)
9a171fcd 6640 return const0_rtx;
20e26713 6641
0559cc77
DE
6642 if (icode == CODE_FOR_altivec_vspltisb
6643 || icode == CODE_FOR_altivec_vspltish
6644 || icode == CODE_FOR_altivec_vspltisw
6645 || icode == CODE_FOR_spe_evsplatfi
6646 || icode == CODE_FOR_spe_evsplati)
b44140e7
AH
6647 {
6648 /* Only allow 5-bit *signed* literals. */
b44140e7 6649 if (GET_CODE (op0) != CONST_INT
afca671b
DP
6650 || INTVAL (op0) > 15
6651 || INTVAL (op0) < -16)
b44140e7
AH
6652 {
6653 error ("argument 1 must be a 5-bit signed literal");
9a171fcd 6654 return const0_rtx;
b44140e7 6655 }
b44140e7
AH
6656 }
6657
c62f2db5 6658 if (target == 0
2212663f
DB
6659 || GET_MODE (target) != tmode
6660 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
6661 target = gen_reg_rtx (tmode);
6662
6663 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
6664 op0 = copy_to_mode_reg (mode0, op0);
6665
6666 pat = GEN_FCN (icode) (target, op0);
6667 if (! pat)
6668 return 0;
6669 emit_insn (pat);
0ac081f6 6670
2212663f
DB
6671 return target;
6672}
ae4b4a02 6673
100c4561 6674static rtx
a2369ed3 6675altivec_expand_abs_builtin (enum insn_code icode, tree arglist, rtx target)
100c4561
AH
6676{
6677 rtx pat, scratch1, scratch2;
6678 tree arg0 = TREE_VALUE (arglist);
84217346 6679 rtx op0 = expand_normal (arg0);
100c4561
AH
6680 enum machine_mode tmode = insn_data[icode].operand[0].mode;
6681 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
6682
6683 /* If we have invalid arguments, bail out before generating bad rtl. */
6684 if (arg0 == error_mark_node)
9a171fcd 6685 return const0_rtx;
100c4561
AH
6686
6687 if (target == 0
6688 || GET_MODE (target) != tmode
6689 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
6690 target = gen_reg_rtx (tmode);
6691
6692 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
6693 op0 = copy_to_mode_reg (mode0, op0);
6694
6695 scratch1 = gen_reg_rtx (mode0);
6696 scratch2 = gen_reg_rtx (mode0);
6697
6698 pat = GEN_FCN (icode) (target, op0, scratch1, scratch2);
6699 if (! pat)
6700 return 0;
6701 emit_insn (pat);
6702
6703 return target;
6704}
6705
0ac081f6 6706static rtx
a2369ed3 6707rs6000_expand_binop_builtin (enum insn_code icode, tree arglist, rtx target)
0ac081f6
AH
6708{
6709 rtx pat;
6710 tree arg0 = TREE_VALUE (arglist);
6711 tree arg1 = TREE_VALUE (TREE_CHAIN (arglist));
84217346
MD
6712 rtx op0 = expand_normal (arg0);
6713 rtx op1 = expand_normal (arg1);
0ac081f6
AH
6714 enum machine_mode tmode = insn_data[icode].operand[0].mode;
6715 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
6716 enum machine_mode mode1 = insn_data[icode].operand[2].mode;
6717
0559cc77
DE
6718 if (icode == CODE_FOR_nothing)
6719 /* Builtin not supported on this processor. */
6720 return 0;
6721
20e26713
AH
6722 /* If we got invalid arguments bail out before generating bad rtl. */
6723 if (arg0 == error_mark_node || arg1 == error_mark_node)
9a171fcd 6724 return const0_rtx;
20e26713 6725
0559cc77
DE
6726 if (icode == CODE_FOR_altivec_vcfux
6727 || icode == CODE_FOR_altivec_vcfsx
6728 || icode == CODE_FOR_altivec_vctsxs
6729 || icode == CODE_FOR_altivec_vctuxs
6730 || icode == CODE_FOR_altivec_vspltb
6731 || icode == CODE_FOR_altivec_vsplth
6732 || icode == CODE_FOR_altivec_vspltw
6733 || icode == CODE_FOR_spe_evaddiw
6734 || icode == CODE_FOR_spe_evldd
6735 || icode == CODE_FOR_spe_evldh
6736 || icode == CODE_FOR_spe_evldw
6737 || icode == CODE_FOR_spe_evlhhesplat
6738 || icode == CODE_FOR_spe_evlhhossplat
6739 || icode == CODE_FOR_spe_evlhhousplat
6740 || icode == CODE_FOR_spe_evlwhe
6741 || icode == CODE_FOR_spe_evlwhos
6742 || icode == CODE_FOR_spe_evlwhou
6743 || icode == CODE_FOR_spe_evlwhsplat
6744 || icode == CODE_FOR_spe_evlwwsplat
6745 || icode == CODE_FOR_spe_evrlwi
6746 || icode == CODE_FOR_spe_evslwi
6747 || icode == CODE_FOR_spe_evsrwis
f5119d10 6748 || icode == CODE_FOR_spe_evsubifw
0559cc77 6749 || icode == CODE_FOR_spe_evsrwiu)
b44140e7
AH
6750 {
6751 /* Only allow 5-bit unsigned literals. */
8bb418a3 6752 STRIP_NOPS (arg1);
b44140e7
AH
6753 if (TREE_CODE (arg1) != INTEGER_CST
6754 || TREE_INT_CST_LOW (arg1) & ~0x1f)
6755 {
6756 error ("argument 2 must be a 5-bit unsigned literal");
9a171fcd 6757 return const0_rtx;
b44140e7 6758 }
b44140e7
AH
6759 }
6760
c62f2db5 6761 if (target == 0
0ac081f6
AH
6762 || GET_MODE (target) != tmode
6763 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
6764 target = gen_reg_rtx (tmode);
6765
6766 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
6767 op0 = copy_to_mode_reg (mode0, op0);
6768 if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
6769 op1 = copy_to_mode_reg (mode1, op1);
6770
6771 pat = GEN_FCN (icode) (target, op0, op1);
6772 if (! pat)
6773 return 0;
6774 emit_insn (pat);
6775
6776 return target;
6777}
6525c0e7 6778
ae4b4a02 6779static rtx
f676971a 6780altivec_expand_predicate_builtin (enum insn_code icode, const char *opcode,
a2369ed3 6781 tree arglist, rtx target)
ae4b4a02
AH
6782{
6783 rtx pat, scratch;
6784 tree cr6_form = TREE_VALUE (arglist);
6785 tree arg0 = TREE_VALUE (TREE_CHAIN (arglist));
6786 tree arg1 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
84217346
MD
6787 rtx op0 = expand_normal (arg0);
6788 rtx op1 = expand_normal (arg1);
ae4b4a02
AH
6789 enum machine_mode tmode = SImode;
6790 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
6791 enum machine_mode mode1 = insn_data[icode].operand[2].mode;
6792 int cr6_form_int;
6793
6794 if (TREE_CODE (cr6_form) != INTEGER_CST)
6795 {
6796 error ("argument 1 of __builtin_altivec_predicate must be a constant");
9a171fcd 6797 return const0_rtx;
ae4b4a02
AH
6798 }
6799 else
6800 cr6_form_int = TREE_INT_CST_LOW (cr6_form);
6801
37409796 6802 gcc_assert (mode0 == mode1);
ae4b4a02
AH
6803
6804 /* If we have invalid arguments, bail out before generating bad rtl. */
6805 if (arg0 == error_mark_node || arg1 == error_mark_node)
9a171fcd 6806 return const0_rtx;
ae4b4a02
AH
6807
6808 if (target == 0
6809 || GET_MODE (target) != tmode
6810 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
6811 target = gen_reg_rtx (tmode);
6812
6813 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
6814 op0 = copy_to_mode_reg (mode0, op0);
6815 if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
6816 op1 = copy_to_mode_reg (mode1, op1);
6817
6818 scratch = gen_reg_rtx (mode0);
6819
6820 pat = GEN_FCN (icode) (scratch, op0, op1,
f1c25d3b 6821 gen_rtx_SYMBOL_REF (Pmode, opcode));
ae4b4a02
AH
6822 if (! pat)
6823 return 0;
6824 emit_insn (pat);
6825
6826 /* The vec_any* and vec_all* predicates use the same opcodes for two
6827 different operations, but the bits in CR6 will be different
6828 depending on what information we want. So we have to play tricks
6829 with CR6 to get the right bits out.
6830
6831 If you think this is disgusting, look at the specs for the
6832 AltiVec predicates. */
6833
c4ad648e
AM
6834 switch (cr6_form_int)
6835 {
6836 case 0:
6837 emit_insn (gen_cr6_test_for_zero (target));
6838 break;
6839 case 1:
6840 emit_insn (gen_cr6_test_for_zero_reverse (target));
6841 break;
6842 case 2:
6843 emit_insn (gen_cr6_test_for_lt (target));
6844 break;
6845 case 3:
6846 emit_insn (gen_cr6_test_for_lt_reverse (target));
6847 break;
6848 default:
6849 error ("argument 1 of __builtin_altivec_predicate is out of range");
6850 break;
6851 }
ae4b4a02
AH
6852
6853 return target;
6854}
6855
b4a62fa0 6856static rtx
38f391a5 6857altivec_expand_lv_builtin (enum insn_code icode, tree arglist, rtx target)
b4a62fa0
SB
6858{
6859 rtx pat, addr;
6860 tree arg0 = TREE_VALUE (arglist);
6861 tree arg1 = TREE_VALUE (TREE_CHAIN (arglist));
6862 enum machine_mode tmode = insn_data[icode].operand[0].mode;
6863 enum machine_mode mode0 = Pmode;
6864 enum machine_mode mode1 = Pmode;
84217346
MD
6865 rtx op0 = expand_normal (arg0);
6866 rtx op1 = expand_normal (arg1);
b4a62fa0
SB
6867
6868 if (icode == CODE_FOR_nothing)
6869 /* Builtin not supported on this processor. */
6870 return 0;
6871
6872 /* If we got invalid arguments bail out before generating bad rtl. */
6873 if (arg0 == error_mark_node || arg1 == error_mark_node)
6874 return const0_rtx;
6875
6876 if (target == 0
6877 || GET_MODE (target) != tmode
6878 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
6879 target = gen_reg_rtx (tmode);
6880
f676971a 6881 op1 = copy_to_mode_reg (mode1, op1);
b4a62fa0
SB
6882
6883 if (op0 == const0_rtx)
6884 {
6885 addr = gen_rtx_MEM (tmode, op1);
6886 }
6887 else
6888 {
6889 op0 = copy_to_mode_reg (mode0, op0);
6890 addr = gen_rtx_MEM (tmode, gen_rtx_PLUS (Pmode, op0, op1));
6891 }
6892
6893 pat = GEN_FCN (icode) (target, addr);
6894
6895 if (! pat)
6896 return 0;
6897 emit_insn (pat);
6898
6899 return target;
6900}
6901
61bea3b0
AH
6902static rtx
6903spe_expand_stv_builtin (enum insn_code icode, tree arglist)
6904{
6905 tree arg0 = TREE_VALUE (arglist);
6906 tree arg1 = TREE_VALUE (TREE_CHAIN (arglist));
6907 tree arg2 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
84217346
MD
6908 rtx op0 = expand_normal (arg0);
6909 rtx op1 = expand_normal (arg1);
6910 rtx op2 = expand_normal (arg2);
61bea3b0
AH
6911 rtx pat;
6912 enum machine_mode mode0 = insn_data[icode].operand[0].mode;
6913 enum machine_mode mode1 = insn_data[icode].operand[1].mode;
6914 enum machine_mode mode2 = insn_data[icode].operand[2].mode;
6915
6916 /* Invalid arguments. Bail before doing anything stoopid! */
6917 if (arg0 == error_mark_node
6918 || arg1 == error_mark_node
6919 || arg2 == error_mark_node)
6920 return const0_rtx;
6921
6922 if (! (*insn_data[icode].operand[2].predicate) (op0, mode2))
6923 op0 = copy_to_mode_reg (mode2, op0);
6924 if (! (*insn_data[icode].operand[0].predicate) (op1, mode0))
6925 op1 = copy_to_mode_reg (mode0, op1);
6926 if (! (*insn_data[icode].operand[1].predicate) (op2, mode1))
6927 op2 = copy_to_mode_reg (mode1, op2);
6928
6929 pat = GEN_FCN (icode) (op1, op2, op0);
6930 if (pat)
6931 emit_insn (pat);
6932 return NULL_RTX;
6933}
6934
6525c0e7 6935static rtx
a2369ed3 6936altivec_expand_stv_builtin (enum insn_code icode, tree arglist)
6525c0e7
AH
6937{
6938 tree arg0 = TREE_VALUE (arglist);
6939 tree arg1 = TREE_VALUE (TREE_CHAIN (arglist));
6940 tree arg2 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
84217346
MD
6941 rtx op0 = expand_normal (arg0);
6942 rtx op1 = expand_normal (arg1);
6943 rtx op2 = expand_normal (arg2);
b4a62fa0
SB
6944 rtx pat, addr;
6945 enum machine_mode tmode = insn_data[icode].operand[0].mode;
6946 enum machine_mode mode1 = Pmode;
6947 enum machine_mode mode2 = Pmode;
6525c0e7
AH
6948
6949 /* Invalid arguments. Bail before doing anything stoopid! */
6950 if (arg0 == error_mark_node
6951 || arg1 == error_mark_node
6952 || arg2 == error_mark_node)
9a171fcd 6953 return const0_rtx;
6525c0e7 6954
b4a62fa0
SB
6955 if (! (*insn_data[icode].operand[1].predicate) (op0, tmode))
6956 op0 = copy_to_mode_reg (tmode, op0);
6957
f676971a 6958 op2 = copy_to_mode_reg (mode2, op2);
b4a62fa0
SB
6959
6960 if (op1 == const0_rtx)
6961 {
6962 addr = gen_rtx_MEM (tmode, op2);
6963 }
6964 else
6965 {
6966 op1 = copy_to_mode_reg (mode1, op1);
6967 addr = gen_rtx_MEM (tmode, gen_rtx_PLUS (Pmode, op1, op2));
6968 }
6525c0e7 6969
b4a62fa0 6970 pat = GEN_FCN (icode) (addr, op0);
6525c0e7
AH
6971 if (pat)
6972 emit_insn (pat);
6973 return NULL_RTX;
6974}
6975
2212663f 6976static rtx
a2369ed3 6977rs6000_expand_ternop_builtin (enum insn_code icode, tree arglist, rtx target)
2212663f
DB
6978{
6979 rtx pat;
6980 tree arg0 = TREE_VALUE (arglist);
6981 tree arg1 = TREE_VALUE (TREE_CHAIN (arglist));
6982 tree arg2 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
84217346
MD
6983 rtx op0 = expand_normal (arg0);
6984 rtx op1 = expand_normal (arg1);
6985 rtx op2 = expand_normal (arg2);
2212663f
DB
6986 enum machine_mode tmode = insn_data[icode].operand[0].mode;
6987 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
6988 enum machine_mode mode1 = insn_data[icode].operand[2].mode;
6989 enum machine_mode mode2 = insn_data[icode].operand[3].mode;
0ac081f6 6990
774b5662
DE
6991 if (icode == CODE_FOR_nothing)
6992 /* Builtin not supported on this processor. */
6993 return 0;
6994
20e26713
AH
6995 /* If we got invalid arguments bail out before generating bad rtl. */
6996 if (arg0 == error_mark_node
6997 || arg1 == error_mark_node
6998 || arg2 == error_mark_node)
9a171fcd 6999 return const0_rtx;
20e26713 7000
aba5fb01
NS
7001 if (icode == CODE_FOR_altivec_vsldoi_v4sf
7002 || icode == CODE_FOR_altivec_vsldoi_v4si
7003 || icode == CODE_FOR_altivec_vsldoi_v8hi
7004 || icode == CODE_FOR_altivec_vsldoi_v16qi)
b44140e7
AH
7005 {
7006 /* Only allow 4-bit unsigned literals. */
8bb418a3 7007 STRIP_NOPS (arg2);
b44140e7
AH
7008 if (TREE_CODE (arg2) != INTEGER_CST
7009 || TREE_INT_CST_LOW (arg2) & ~0xf)
7010 {
7011 error ("argument 3 must be a 4-bit unsigned literal");
e3277ffb 7012 return const0_rtx;
b44140e7 7013 }
b44140e7
AH
7014 }
7015
c62f2db5 7016 if (target == 0
2212663f
DB
7017 || GET_MODE (target) != tmode
7018 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
7019 target = gen_reg_rtx (tmode);
7020
7021 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
7022 op0 = copy_to_mode_reg (mode0, op0);
7023 if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
7024 op1 = copy_to_mode_reg (mode1, op1);
7025 if (! (*insn_data[icode].operand[3].predicate) (op2, mode2))
7026 op2 = copy_to_mode_reg (mode2, op2);
7027
7028 pat = GEN_FCN (icode) (target, op0, op1, op2);
7029 if (! pat)
7030 return 0;
7031 emit_insn (pat);
7032
7033 return target;
7034}
92898235 7035
3a9b8c7e 7036/* Expand the lvx builtins. */
0ac081f6 7037static rtx
a2369ed3 7038altivec_expand_ld_builtin (tree exp, rtx target, bool *expandedp)
0ac081f6 7039{
0ac081f6
AH
7040 tree fndecl = TREE_OPERAND (TREE_OPERAND (exp, 0), 0);
7041 tree arglist = TREE_OPERAND (exp, 1);
0ac081f6 7042 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
3a9b8c7e
AH
7043 tree arg0;
7044 enum machine_mode tmode, mode0;
7c3abc73 7045 rtx pat, op0;
3a9b8c7e 7046 enum insn_code icode;
92898235 7047
0ac081f6
AH
7048 switch (fcode)
7049 {
f18c054f 7050 case ALTIVEC_BUILTIN_LD_INTERNAL_16qi:
81466555 7051 icode = CODE_FOR_altivec_lvx_v16qi;
3a9b8c7e 7052 break;
f18c054f 7053 case ALTIVEC_BUILTIN_LD_INTERNAL_8hi:
81466555 7054 icode = CODE_FOR_altivec_lvx_v8hi;
3a9b8c7e
AH
7055 break;
7056 case ALTIVEC_BUILTIN_LD_INTERNAL_4si:
81466555 7057 icode = CODE_FOR_altivec_lvx_v4si;
3a9b8c7e
AH
7058 break;
7059 case ALTIVEC_BUILTIN_LD_INTERNAL_4sf:
81466555 7060 icode = CODE_FOR_altivec_lvx_v4sf;
3a9b8c7e
AH
7061 break;
7062 default:
7063 *expandedp = false;
7064 return NULL_RTX;
7065 }
0ac081f6 7066
3a9b8c7e 7067 *expandedp = true;
f18c054f 7068
3a9b8c7e 7069 arg0 = TREE_VALUE (arglist);
84217346 7070 op0 = expand_normal (arg0);
3a9b8c7e
AH
7071 tmode = insn_data[icode].operand[0].mode;
7072 mode0 = insn_data[icode].operand[1].mode;
f18c054f 7073
3a9b8c7e
AH
7074 if (target == 0
7075 || GET_MODE (target) != tmode
7076 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
7077 target = gen_reg_rtx (tmode);
24408032 7078
3a9b8c7e
AH
7079 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
7080 op0 = gen_rtx_MEM (mode0, copy_to_mode_reg (Pmode, op0));
f18c054f 7081
3a9b8c7e
AH
7082 pat = GEN_FCN (icode) (target, op0);
7083 if (! pat)
7084 return 0;
7085 emit_insn (pat);
7086 return target;
7087}
f18c054f 7088
3a9b8c7e
AH
7089/* Expand the stvx builtins. */
7090static rtx
f676971a 7091altivec_expand_st_builtin (tree exp, rtx target ATTRIBUTE_UNUSED,
a2369ed3 7092 bool *expandedp)
3a9b8c7e
AH
7093{
7094 tree fndecl = TREE_OPERAND (TREE_OPERAND (exp, 0), 0);
7095 tree arglist = TREE_OPERAND (exp, 1);
7096 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
7097 tree arg0, arg1;
7098 enum machine_mode mode0, mode1;
7c3abc73 7099 rtx pat, op0, op1;
3a9b8c7e 7100 enum insn_code icode;
f18c054f 7101
3a9b8c7e
AH
7102 switch (fcode)
7103 {
7104 case ALTIVEC_BUILTIN_ST_INTERNAL_16qi:
81466555 7105 icode = CODE_FOR_altivec_stvx_v16qi;
3a9b8c7e
AH
7106 break;
7107 case ALTIVEC_BUILTIN_ST_INTERNAL_8hi:
81466555 7108 icode = CODE_FOR_altivec_stvx_v8hi;
3a9b8c7e
AH
7109 break;
7110 case ALTIVEC_BUILTIN_ST_INTERNAL_4si:
81466555 7111 icode = CODE_FOR_altivec_stvx_v4si;
3a9b8c7e
AH
7112 break;
7113 case ALTIVEC_BUILTIN_ST_INTERNAL_4sf:
81466555 7114 icode = CODE_FOR_altivec_stvx_v4sf;
3a9b8c7e
AH
7115 break;
7116 default:
7117 *expandedp = false;
7118 return NULL_RTX;
7119 }
24408032 7120
3a9b8c7e
AH
7121 arg0 = TREE_VALUE (arglist);
7122 arg1 = TREE_VALUE (TREE_CHAIN (arglist));
84217346
MD
7123 op0 = expand_normal (arg0);
7124 op1 = expand_normal (arg1);
3a9b8c7e
AH
7125 mode0 = insn_data[icode].operand[0].mode;
7126 mode1 = insn_data[icode].operand[1].mode;
f18c054f 7127
3a9b8c7e
AH
7128 if (! (*insn_data[icode].operand[0].predicate) (op0, mode0))
7129 op0 = gen_rtx_MEM (mode0, copy_to_mode_reg (Pmode, op0));
7130 if (! (*insn_data[icode].operand[1].predicate) (op1, mode1))
7131 op1 = copy_to_mode_reg (mode1, op1);
f18c054f 7132
3a9b8c7e
AH
7133 pat = GEN_FCN (icode) (op0, op1);
7134 if (pat)
7135 emit_insn (pat);
f18c054f 7136
3a9b8c7e
AH
7137 *expandedp = true;
7138 return NULL_RTX;
7139}
f18c054f 7140
3a9b8c7e
AH
7141/* Expand the dst builtins. */
7142static rtx
f676971a 7143altivec_expand_dst_builtin (tree exp, rtx target ATTRIBUTE_UNUSED,
a2369ed3 7144 bool *expandedp)
3a9b8c7e
AH
7145{
7146 tree fndecl = TREE_OPERAND (TREE_OPERAND (exp, 0), 0);
7147 tree arglist = TREE_OPERAND (exp, 1);
7148 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
7149 tree arg0, arg1, arg2;
7150 enum machine_mode mode0, mode1, mode2;
7c3abc73 7151 rtx pat, op0, op1, op2;
3a9b8c7e 7152 struct builtin_description *d;
a3170dc6 7153 size_t i;
f18c054f 7154
3a9b8c7e 7155 *expandedp = false;
f18c054f 7156
3a9b8c7e
AH
7157 /* Handle DST variants. */
7158 d = (struct builtin_description *) bdesc_dst;
7159 for (i = 0; i < ARRAY_SIZE (bdesc_dst); i++, d++)
7160 if (d->code == fcode)
7161 {
7162 arg0 = TREE_VALUE (arglist);
7163 arg1 = TREE_VALUE (TREE_CHAIN (arglist));
7164 arg2 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
84217346
MD
7165 op0 = expand_normal (arg0);
7166 op1 = expand_normal (arg1);
7167 op2 = expand_normal (arg2);
3a9b8c7e
AH
7168 mode0 = insn_data[d->icode].operand[0].mode;
7169 mode1 = insn_data[d->icode].operand[1].mode;
7170 mode2 = insn_data[d->icode].operand[2].mode;
24408032 7171
3a9b8c7e
AH
7172 /* Invalid arguments, bail out before generating bad rtl. */
7173 if (arg0 == error_mark_node
7174 || arg1 == error_mark_node
7175 || arg2 == error_mark_node)
7176 return const0_rtx;
f18c054f 7177
86e7df90 7178 *expandedp = true;
8bb418a3 7179 STRIP_NOPS (arg2);
3a9b8c7e
AH
7180 if (TREE_CODE (arg2) != INTEGER_CST
7181 || TREE_INT_CST_LOW (arg2) & ~0x3)
7182 {
9e637a26 7183 error ("argument to %qs must be a 2-bit unsigned literal", d->name);
3a9b8c7e
AH
7184 return const0_rtx;
7185 }
f18c054f 7186
3a9b8c7e 7187 if (! (*insn_data[d->icode].operand[0].predicate) (op0, mode0))
666158b9 7188 op0 = copy_to_mode_reg (Pmode, op0);
3a9b8c7e
AH
7189 if (! (*insn_data[d->icode].operand[1].predicate) (op1, mode1))
7190 op1 = copy_to_mode_reg (mode1, op1);
24408032 7191
3a9b8c7e
AH
7192 pat = GEN_FCN (d->icode) (op0, op1, op2);
7193 if (pat != 0)
7194 emit_insn (pat);
f18c054f 7195
3a9b8c7e
AH
7196 return NULL_RTX;
7197 }
f18c054f 7198
3a9b8c7e
AH
7199 return NULL_RTX;
7200}
24408032 7201
7a4eca66
DE
7202/* Expand vec_init builtin. */
7203static rtx
7204altivec_expand_vec_init_builtin (tree type, tree arglist, rtx target)
7205{
7206 enum machine_mode tmode = TYPE_MODE (type);
7207 enum machine_mode inner_mode = GET_MODE_INNER (tmode);
7208 int i, n_elt = GET_MODE_NUNITS (tmode);
7209 rtvec v = rtvec_alloc (n_elt);
7210
7211 gcc_assert (VECTOR_MODE_P (tmode));
7212
7213 for (i = 0; i < n_elt; ++i, arglist = TREE_CHAIN (arglist))
7214 {
84217346 7215 rtx x = expand_normal (TREE_VALUE (arglist));
7a4eca66
DE
7216 RTVEC_ELT (v, i) = gen_lowpart (inner_mode, x);
7217 }
7218
7219 gcc_assert (arglist == NULL);
7220
7221 if (!target || !register_operand (target, tmode))
7222 target = gen_reg_rtx (tmode);
7223
7224 rs6000_expand_vector_init (target, gen_rtx_PARALLEL (tmode, v));
7225 return target;
7226}
7227
7228/* Return the integer constant in ARG. Constrain it to be in the range
7229 of the subparts of VEC_TYPE; issue an error if not. */
7230
7231static int
7232get_element_number (tree vec_type, tree arg)
7233{
7234 unsigned HOST_WIDE_INT elt, max = TYPE_VECTOR_SUBPARTS (vec_type) - 1;
7235
7236 if (!host_integerp (arg, 1)
7237 || (elt = tree_low_cst (arg, 1), elt > max))
7238 {
7239 error ("selector must be an integer constant in the range 0..%wi", max);
7240 return 0;
7241 }
7242
7243 return elt;
7244}
7245
7246/* Expand vec_set builtin. */
7247static rtx
7248altivec_expand_vec_set_builtin (tree arglist)
7249{
7250 enum machine_mode tmode, mode1;
7251 tree arg0, arg1, arg2;
7252 int elt;
7253 rtx op0, op1;
7254
7255 arg0 = TREE_VALUE (arglist);
7256 arg1 = TREE_VALUE (TREE_CHAIN (arglist));
7257 arg2 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
7258
7259 tmode = TYPE_MODE (TREE_TYPE (arg0));
7260 mode1 = TYPE_MODE (TREE_TYPE (TREE_TYPE (arg0)));
7261 gcc_assert (VECTOR_MODE_P (tmode));
7262
7263 op0 = expand_expr (arg0, NULL_RTX, tmode, 0);
7264 op1 = expand_expr (arg1, NULL_RTX, mode1, 0);
7265 elt = get_element_number (TREE_TYPE (arg0), arg2);
7266
7267 if (GET_MODE (op1) != mode1 && GET_MODE (op1) != VOIDmode)
7268 op1 = convert_modes (mode1, GET_MODE (op1), op1, true);
7269
7270 op0 = force_reg (tmode, op0);
7271 op1 = force_reg (mode1, op1);
7272
7273 rs6000_expand_vector_set (op0, op1, elt);
7274
7275 return op0;
7276}
7277
7278/* Expand vec_ext builtin. */
7279static rtx
7280altivec_expand_vec_ext_builtin (tree arglist, rtx target)
7281{
7282 enum machine_mode tmode, mode0;
7283 tree arg0, arg1;
7284 int elt;
7285 rtx op0;
7286
7287 arg0 = TREE_VALUE (arglist);
7288 arg1 = TREE_VALUE (TREE_CHAIN (arglist));
7289
84217346 7290 op0 = expand_normal (arg0);
7a4eca66
DE
7291 elt = get_element_number (TREE_TYPE (arg0), arg1);
7292
7293 tmode = TYPE_MODE (TREE_TYPE (TREE_TYPE (arg0)));
7294 mode0 = TYPE_MODE (TREE_TYPE (arg0));
7295 gcc_assert (VECTOR_MODE_P (mode0));
7296
7297 op0 = force_reg (mode0, op0);
7298
7299 if (optimize || !target || !register_operand (target, tmode))
7300 target = gen_reg_rtx (tmode);
7301
7302 rs6000_expand_vector_extract (target, op0, elt);
7303
7304 return target;
7305}
7306
3a9b8c7e
AH
7307/* Expand the builtin in EXP and store the result in TARGET. Store
7308 true in *EXPANDEDP if we found a builtin to expand. */
7309static rtx
a2369ed3 7310altivec_expand_builtin (tree exp, rtx target, bool *expandedp)
3a9b8c7e
AH
7311{
7312 struct builtin_description *d;
7313 struct builtin_description_predicates *dp;
7314 size_t i;
7315 enum insn_code icode;
7316 tree fndecl = TREE_OPERAND (TREE_OPERAND (exp, 0), 0);
7317 tree arglist = TREE_OPERAND (exp, 1);
7c3abc73
AH
7318 tree arg0;
7319 rtx op0, pat;
7320 enum machine_mode tmode, mode0;
3a9b8c7e 7321 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
0ac081f6 7322
58646b77
PB
7323 if (fcode >= ALTIVEC_BUILTIN_OVERLOADED_FIRST
7324 && fcode <= ALTIVEC_BUILTIN_OVERLOADED_LAST)
7325 {
7326 *expandedp = true;
ea40ba9c 7327 error ("unresolved overload for Altivec builtin %qF", fndecl);
58646b77
PB
7328 return const0_rtx;
7329 }
7330
3a9b8c7e
AH
7331 target = altivec_expand_ld_builtin (exp, target, expandedp);
7332 if (*expandedp)
7333 return target;
0ac081f6 7334
3a9b8c7e
AH
7335 target = altivec_expand_st_builtin (exp, target, expandedp);
7336 if (*expandedp)
7337 return target;
7338
7339 target = altivec_expand_dst_builtin (exp, target, expandedp);
7340 if (*expandedp)
7341 return target;
7342
7343 *expandedp = true;
95385cbb 7344
3a9b8c7e
AH
7345 switch (fcode)
7346 {
6525c0e7
AH
7347 case ALTIVEC_BUILTIN_STVX:
7348 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvx, arglist);
7349 case ALTIVEC_BUILTIN_STVEBX:
7350 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvebx, arglist);
7351 case ALTIVEC_BUILTIN_STVEHX:
7352 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvehx, arglist);
7353 case ALTIVEC_BUILTIN_STVEWX:
7354 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvewx, arglist);
7355 case ALTIVEC_BUILTIN_STVXL:
7356 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvxl, arglist);
3a9b8c7e 7357
95385cbb
AH
7358 case ALTIVEC_BUILTIN_MFVSCR:
7359 icode = CODE_FOR_altivec_mfvscr;
7360 tmode = insn_data[icode].operand[0].mode;
7361
7362 if (target == 0
7363 || GET_MODE (target) != tmode
7364 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
7365 target = gen_reg_rtx (tmode);
f676971a 7366
95385cbb 7367 pat = GEN_FCN (icode) (target);
0ac081f6
AH
7368 if (! pat)
7369 return 0;
7370 emit_insn (pat);
95385cbb
AH
7371 return target;
7372
7373 case ALTIVEC_BUILTIN_MTVSCR:
7374 icode = CODE_FOR_altivec_mtvscr;
7375 arg0 = TREE_VALUE (arglist);
84217346 7376 op0 = expand_normal (arg0);
95385cbb
AH
7377 mode0 = insn_data[icode].operand[0].mode;
7378
7379 /* If we got invalid arguments bail out before generating bad rtl. */
7380 if (arg0 == error_mark_node)
9a171fcd 7381 return const0_rtx;
95385cbb
AH
7382
7383 if (! (*insn_data[icode].operand[0].predicate) (op0, mode0))
7384 op0 = copy_to_mode_reg (mode0, op0);
7385
7386 pat = GEN_FCN (icode) (op0);
7387 if (pat)
7388 emit_insn (pat);
7389 return NULL_RTX;
3a9b8c7e 7390
95385cbb
AH
7391 case ALTIVEC_BUILTIN_DSSALL:
7392 emit_insn (gen_altivec_dssall ());
7393 return NULL_RTX;
7394
7395 case ALTIVEC_BUILTIN_DSS:
7396 icode = CODE_FOR_altivec_dss;
7397 arg0 = TREE_VALUE (arglist);
8bb418a3 7398 STRIP_NOPS (arg0);
84217346 7399 op0 = expand_normal (arg0);
95385cbb
AH
7400 mode0 = insn_data[icode].operand[0].mode;
7401
7402 /* If we got invalid arguments bail out before generating bad rtl. */
7403 if (arg0 == error_mark_node)
9a171fcd 7404 return const0_rtx;
95385cbb 7405
b44140e7
AH
7406 if (TREE_CODE (arg0) != INTEGER_CST
7407 || TREE_INT_CST_LOW (arg0) & ~0x3)
7408 {
7409 error ("argument to dss must be a 2-bit unsigned literal");
9a171fcd 7410 return const0_rtx;
b44140e7
AH
7411 }
7412
95385cbb
AH
7413 if (! (*insn_data[icode].operand[0].predicate) (op0, mode0))
7414 op0 = copy_to_mode_reg (mode0, op0);
7415
7416 emit_insn (gen_altivec_dss (op0));
0ac081f6 7417 return NULL_RTX;
7a4eca66
DE
7418
7419 case ALTIVEC_BUILTIN_VEC_INIT_V4SI:
7420 case ALTIVEC_BUILTIN_VEC_INIT_V8HI:
7421 case ALTIVEC_BUILTIN_VEC_INIT_V16QI:
7422 case ALTIVEC_BUILTIN_VEC_INIT_V4SF:
7423 return altivec_expand_vec_init_builtin (TREE_TYPE (exp), arglist, target);
7424
7425 case ALTIVEC_BUILTIN_VEC_SET_V4SI:
7426 case ALTIVEC_BUILTIN_VEC_SET_V8HI:
7427 case ALTIVEC_BUILTIN_VEC_SET_V16QI:
7428 case ALTIVEC_BUILTIN_VEC_SET_V4SF:
7429 return altivec_expand_vec_set_builtin (arglist);
7430
7431 case ALTIVEC_BUILTIN_VEC_EXT_V4SI:
7432 case ALTIVEC_BUILTIN_VEC_EXT_V8HI:
7433 case ALTIVEC_BUILTIN_VEC_EXT_V16QI:
7434 case ALTIVEC_BUILTIN_VEC_EXT_V4SF:
7435 return altivec_expand_vec_ext_builtin (arglist, target);
7436
7437 default:
7438 break;
7439 /* Fall through. */
0ac081f6 7440 }
24408032 7441
100c4561
AH
7442 /* Expand abs* operations. */
7443 d = (struct builtin_description *) bdesc_abs;
ca7558fc 7444 for (i = 0; i < ARRAY_SIZE (bdesc_abs); i++, d++)
100c4561
AH
7445 if (d->code == fcode)
7446 return altivec_expand_abs_builtin (d->icode, arglist, target);
7447
ae4b4a02
AH
7448 /* Expand the AltiVec predicates. */
7449 dp = (struct builtin_description_predicates *) bdesc_altivec_preds;
ca7558fc 7450 for (i = 0; i < ARRAY_SIZE (bdesc_altivec_preds); i++, dp++)
ae4b4a02 7451 if (dp->code == fcode)
c4ad648e
AM
7452 return altivec_expand_predicate_builtin (dp->icode, dp->opcode,
7453 arglist, target);
ae4b4a02 7454
6525c0e7
AH
7455 /* LV* are funky. We initialized them differently. */
7456 switch (fcode)
7457 {
7458 case ALTIVEC_BUILTIN_LVSL:
b4a62fa0 7459 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvsl,
c4ad648e 7460 arglist, target);
6525c0e7 7461 case ALTIVEC_BUILTIN_LVSR:
b4a62fa0 7462 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvsr,
c4ad648e 7463 arglist, target);
6525c0e7 7464 case ALTIVEC_BUILTIN_LVEBX:
b4a62fa0 7465 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvebx,
c4ad648e 7466 arglist, target);
6525c0e7 7467 case ALTIVEC_BUILTIN_LVEHX:
b4a62fa0 7468 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvehx,
c4ad648e 7469 arglist, target);
6525c0e7 7470 case ALTIVEC_BUILTIN_LVEWX:
b4a62fa0 7471 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvewx,
c4ad648e 7472 arglist, target);
6525c0e7 7473 case ALTIVEC_BUILTIN_LVXL:
b4a62fa0 7474 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvxl,
c4ad648e 7475 arglist, target);
6525c0e7 7476 case ALTIVEC_BUILTIN_LVX:
b4a62fa0 7477 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvx,
c4ad648e 7478 arglist, target);
6525c0e7
AH
7479 default:
7480 break;
7481 /* Fall through. */
7482 }
95385cbb 7483
92898235 7484 *expandedp = false;
0ac081f6
AH
7485 return NULL_RTX;
7486}
7487
a3170dc6
AH
7488/* Binops that need to be initialized manually, but can be expanded
7489 automagically by rs6000_expand_binop_builtin. */
7490static struct builtin_description bdesc_2arg_spe[] =
7491{
7492 { 0, CODE_FOR_spe_evlddx, "__builtin_spe_evlddx", SPE_BUILTIN_EVLDDX },
7493 { 0, CODE_FOR_spe_evldwx, "__builtin_spe_evldwx", SPE_BUILTIN_EVLDWX },
7494 { 0, CODE_FOR_spe_evldhx, "__builtin_spe_evldhx", SPE_BUILTIN_EVLDHX },
7495 { 0, CODE_FOR_spe_evlwhex, "__builtin_spe_evlwhex", SPE_BUILTIN_EVLWHEX },
7496 { 0, CODE_FOR_spe_evlwhoux, "__builtin_spe_evlwhoux", SPE_BUILTIN_EVLWHOUX },
7497 { 0, CODE_FOR_spe_evlwhosx, "__builtin_spe_evlwhosx", SPE_BUILTIN_EVLWHOSX },
7498 { 0, CODE_FOR_spe_evlwwsplatx, "__builtin_spe_evlwwsplatx", SPE_BUILTIN_EVLWWSPLATX },
7499 { 0, CODE_FOR_spe_evlwhsplatx, "__builtin_spe_evlwhsplatx", SPE_BUILTIN_EVLWHSPLATX },
7500 { 0, CODE_FOR_spe_evlhhesplatx, "__builtin_spe_evlhhesplatx", SPE_BUILTIN_EVLHHESPLATX },
7501 { 0, CODE_FOR_spe_evlhhousplatx, "__builtin_spe_evlhhousplatx", SPE_BUILTIN_EVLHHOUSPLATX },
7502 { 0, CODE_FOR_spe_evlhhossplatx, "__builtin_spe_evlhhossplatx", SPE_BUILTIN_EVLHHOSSPLATX },
7503 { 0, CODE_FOR_spe_evldd, "__builtin_spe_evldd", SPE_BUILTIN_EVLDD },
7504 { 0, CODE_FOR_spe_evldw, "__builtin_spe_evldw", SPE_BUILTIN_EVLDW },
7505 { 0, CODE_FOR_spe_evldh, "__builtin_spe_evldh", SPE_BUILTIN_EVLDH },
7506 { 0, CODE_FOR_spe_evlwhe, "__builtin_spe_evlwhe", SPE_BUILTIN_EVLWHE },
7507 { 0, CODE_FOR_spe_evlwhou, "__builtin_spe_evlwhou", SPE_BUILTIN_EVLWHOU },
7508 { 0, CODE_FOR_spe_evlwhos, "__builtin_spe_evlwhos", SPE_BUILTIN_EVLWHOS },
7509 { 0, CODE_FOR_spe_evlwwsplat, "__builtin_spe_evlwwsplat", SPE_BUILTIN_EVLWWSPLAT },
7510 { 0, CODE_FOR_spe_evlwhsplat, "__builtin_spe_evlwhsplat", SPE_BUILTIN_EVLWHSPLAT },
7511 { 0, CODE_FOR_spe_evlhhesplat, "__builtin_spe_evlhhesplat", SPE_BUILTIN_EVLHHESPLAT },
7512 { 0, CODE_FOR_spe_evlhhousplat, "__builtin_spe_evlhhousplat", SPE_BUILTIN_EVLHHOUSPLAT },
7513 { 0, CODE_FOR_spe_evlhhossplat, "__builtin_spe_evlhhossplat", SPE_BUILTIN_EVLHHOSSPLAT }
7514};
7515
7516/* Expand the builtin in EXP and store the result in TARGET. Store
7517 true in *EXPANDEDP if we found a builtin to expand.
7518
7519 This expands the SPE builtins that are not simple unary and binary
7520 operations. */
7521static rtx
a2369ed3 7522spe_expand_builtin (tree exp, rtx target, bool *expandedp)
a3170dc6
AH
7523{
7524 tree fndecl = TREE_OPERAND (TREE_OPERAND (exp, 0), 0);
7525 tree arglist = TREE_OPERAND (exp, 1);
7526 tree arg1, arg0;
7527 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
7528 enum insn_code icode;
7529 enum machine_mode tmode, mode0;
7530 rtx pat, op0;
7531 struct builtin_description *d;
7532 size_t i;
7533
7534 *expandedp = true;
7535
7536 /* Syntax check for a 5-bit unsigned immediate. */
7537 switch (fcode)
7538 {
7539 case SPE_BUILTIN_EVSTDD:
7540 case SPE_BUILTIN_EVSTDH:
7541 case SPE_BUILTIN_EVSTDW:
7542 case SPE_BUILTIN_EVSTWHE:
7543 case SPE_BUILTIN_EVSTWHO:
7544 case SPE_BUILTIN_EVSTWWE:
7545 case SPE_BUILTIN_EVSTWWO:
7546 arg1 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
7547 if (TREE_CODE (arg1) != INTEGER_CST
7548 || TREE_INT_CST_LOW (arg1) & ~0x1f)
7549 {
7550 error ("argument 2 must be a 5-bit unsigned literal");
7551 return const0_rtx;
7552 }
7553 break;
7554 default:
7555 break;
7556 }
7557
00332c9f
AH
7558 /* The evsplat*i instructions are not quite generic. */
7559 switch (fcode)
7560 {
7561 case SPE_BUILTIN_EVSPLATFI:
7562 return rs6000_expand_unop_builtin (CODE_FOR_spe_evsplatfi,
7563 arglist, target);
7564 case SPE_BUILTIN_EVSPLATI:
7565 return rs6000_expand_unop_builtin (CODE_FOR_spe_evsplati,
7566 arglist, target);
7567 default:
7568 break;
7569 }
7570
a3170dc6
AH
7571 d = (struct builtin_description *) bdesc_2arg_spe;
7572 for (i = 0; i < ARRAY_SIZE (bdesc_2arg_spe); ++i, ++d)
7573 if (d->code == fcode)
7574 return rs6000_expand_binop_builtin (d->icode, arglist, target);
7575
7576 d = (struct builtin_description *) bdesc_spe_predicates;
7577 for (i = 0; i < ARRAY_SIZE (bdesc_spe_predicates); ++i, ++d)
7578 if (d->code == fcode)
7579 return spe_expand_predicate_builtin (d->icode, arglist, target);
7580
7581 d = (struct builtin_description *) bdesc_spe_evsel;
7582 for (i = 0; i < ARRAY_SIZE (bdesc_spe_evsel); ++i, ++d)
7583 if (d->code == fcode)
7584 return spe_expand_evsel_builtin (d->icode, arglist, target);
7585
7586 switch (fcode)
7587 {
7588 case SPE_BUILTIN_EVSTDDX:
61bea3b0 7589 return spe_expand_stv_builtin (CODE_FOR_spe_evstddx, arglist);
a3170dc6 7590 case SPE_BUILTIN_EVSTDHX:
61bea3b0 7591 return spe_expand_stv_builtin (CODE_FOR_spe_evstdhx, arglist);
a3170dc6 7592 case SPE_BUILTIN_EVSTDWX:
61bea3b0 7593 return spe_expand_stv_builtin (CODE_FOR_spe_evstdwx, arglist);
a3170dc6 7594 case SPE_BUILTIN_EVSTWHEX:
61bea3b0 7595 return spe_expand_stv_builtin (CODE_FOR_spe_evstwhex, arglist);
a3170dc6 7596 case SPE_BUILTIN_EVSTWHOX:
61bea3b0 7597 return spe_expand_stv_builtin (CODE_FOR_spe_evstwhox, arglist);
a3170dc6 7598 case SPE_BUILTIN_EVSTWWEX:
61bea3b0 7599 return spe_expand_stv_builtin (CODE_FOR_spe_evstwwex, arglist);
a3170dc6 7600 case SPE_BUILTIN_EVSTWWOX:
61bea3b0 7601 return spe_expand_stv_builtin (CODE_FOR_spe_evstwwox, arglist);
a3170dc6 7602 case SPE_BUILTIN_EVSTDD:
61bea3b0 7603 return spe_expand_stv_builtin (CODE_FOR_spe_evstdd, arglist);
a3170dc6 7604 case SPE_BUILTIN_EVSTDH:
61bea3b0 7605 return spe_expand_stv_builtin (CODE_FOR_spe_evstdh, arglist);
a3170dc6 7606 case SPE_BUILTIN_EVSTDW:
61bea3b0 7607 return spe_expand_stv_builtin (CODE_FOR_spe_evstdw, arglist);
a3170dc6 7608 case SPE_BUILTIN_EVSTWHE:
61bea3b0 7609 return spe_expand_stv_builtin (CODE_FOR_spe_evstwhe, arglist);
a3170dc6 7610 case SPE_BUILTIN_EVSTWHO:
61bea3b0 7611 return spe_expand_stv_builtin (CODE_FOR_spe_evstwho, arglist);
a3170dc6 7612 case SPE_BUILTIN_EVSTWWE:
61bea3b0 7613 return spe_expand_stv_builtin (CODE_FOR_spe_evstwwe, arglist);
a3170dc6 7614 case SPE_BUILTIN_EVSTWWO:
61bea3b0 7615 return spe_expand_stv_builtin (CODE_FOR_spe_evstwwo, arglist);
a3170dc6
AH
7616 case SPE_BUILTIN_MFSPEFSCR:
7617 icode = CODE_FOR_spe_mfspefscr;
7618 tmode = insn_data[icode].operand[0].mode;
7619
7620 if (target == 0
7621 || GET_MODE (target) != tmode
7622 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
7623 target = gen_reg_rtx (tmode);
f676971a 7624
a3170dc6
AH
7625 pat = GEN_FCN (icode) (target);
7626 if (! pat)
7627 return 0;
7628 emit_insn (pat);
7629 return target;
7630 case SPE_BUILTIN_MTSPEFSCR:
7631 icode = CODE_FOR_spe_mtspefscr;
7632 arg0 = TREE_VALUE (arglist);
84217346 7633 op0 = expand_normal (arg0);
a3170dc6
AH
7634 mode0 = insn_data[icode].operand[0].mode;
7635
7636 if (arg0 == error_mark_node)
7637 return const0_rtx;
7638
7639 if (! (*insn_data[icode].operand[0].predicate) (op0, mode0))
7640 op0 = copy_to_mode_reg (mode0, op0);
7641
7642 pat = GEN_FCN (icode) (op0);
7643 if (pat)
7644 emit_insn (pat);
7645 return NULL_RTX;
7646 default:
7647 break;
7648 }
7649
7650 *expandedp = false;
7651 return NULL_RTX;
7652}
7653
7654static rtx
a2369ed3 7655spe_expand_predicate_builtin (enum insn_code icode, tree arglist, rtx target)
a3170dc6
AH
7656{
7657 rtx pat, scratch, tmp;
7658 tree form = TREE_VALUE (arglist);
7659 tree arg0 = TREE_VALUE (TREE_CHAIN (arglist));
7660 tree arg1 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
84217346
MD
7661 rtx op0 = expand_normal (arg0);
7662 rtx op1 = expand_normal (arg1);
a3170dc6
AH
7663 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
7664 enum machine_mode mode1 = insn_data[icode].operand[2].mode;
7665 int form_int;
7666 enum rtx_code code;
7667
7668 if (TREE_CODE (form) != INTEGER_CST)
7669 {
7670 error ("argument 1 of __builtin_spe_predicate must be a constant");
7671 return const0_rtx;
7672 }
7673 else
7674 form_int = TREE_INT_CST_LOW (form);
7675
37409796 7676 gcc_assert (mode0 == mode1);
a3170dc6
AH
7677
7678 if (arg0 == error_mark_node || arg1 == error_mark_node)
7679 return const0_rtx;
7680
7681 if (target == 0
7682 || GET_MODE (target) != SImode
7683 || ! (*insn_data[icode].operand[0].predicate) (target, SImode))
7684 target = gen_reg_rtx (SImode);
7685
7686 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
7687 op0 = copy_to_mode_reg (mode0, op0);
7688 if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
7689 op1 = copy_to_mode_reg (mode1, op1);
7690
7691 scratch = gen_reg_rtx (CCmode);
7692
7693 pat = GEN_FCN (icode) (scratch, op0, op1);
7694 if (! pat)
7695 return const0_rtx;
7696 emit_insn (pat);
7697
7698 /* There are 4 variants for each predicate: _any_, _all_, _upper_,
7699 _lower_. We use one compare, but look in different bits of the
7700 CR for each variant.
7701
7702 There are 2 elements in each SPE simd type (upper/lower). The CR
7703 bits are set as follows:
7704
7705 BIT0 | BIT 1 | BIT 2 | BIT 3
7706 U | L | (U | L) | (U & L)
7707
7708 So, for an "all" relationship, BIT 3 would be set.
7709 For an "any" relationship, BIT 2 would be set. Etc.
7710
7711 Following traditional nomenclature, these bits map to:
7712
7713 BIT0 | BIT 1 | BIT 2 | BIT 3
7714 LT | GT | EQ | OV
7715
7716 Later, we will generate rtl to look in the LT/EQ/EQ/OV bits.
7717 */
7718
7719 switch (form_int)
7720 {
7721 /* All variant. OV bit. */
7722 case 0:
7723 /* We need to get to the OV bit, which is the ORDERED bit. We
7724 could generate (ordered:SI (reg:CC xx) (const_int 0)), but
992d08b1 7725 that's ugly and will make validate_condition_mode die.
a3170dc6
AH
7726 So let's just use another pattern. */
7727 emit_insn (gen_move_from_CR_ov_bit (target, scratch));
7728 return target;
7729 /* Any variant. EQ bit. */
7730 case 1:
7731 code = EQ;
7732 break;
7733 /* Upper variant. LT bit. */
7734 case 2:
7735 code = LT;
7736 break;
7737 /* Lower variant. GT bit. */
7738 case 3:
7739 code = GT;
7740 break;
7741 default:
7742 error ("argument 1 of __builtin_spe_predicate is out of range");
7743 return const0_rtx;
7744 }
7745
7746 tmp = gen_rtx_fmt_ee (code, SImode, scratch, const0_rtx);
7747 emit_move_insn (target, tmp);
7748
7749 return target;
7750}
7751
7752/* The evsel builtins look like this:
7753
7754 e = __builtin_spe_evsel_OP (a, b, c, d);
7755
7756 and work like this:
7757
7758 e[upper] = a[upper] *OP* b[upper] ? c[upper] : d[upper];
7759 e[lower] = a[lower] *OP* b[lower] ? c[lower] : d[lower];
7760*/
7761
7762static rtx
a2369ed3 7763spe_expand_evsel_builtin (enum insn_code icode, tree arglist, rtx target)
a3170dc6
AH
7764{
7765 rtx pat, scratch;
7766 tree arg0 = TREE_VALUE (arglist);
7767 tree arg1 = TREE_VALUE (TREE_CHAIN (arglist));
7768 tree arg2 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
7769 tree arg3 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (TREE_CHAIN (arglist))));
84217346
MD
7770 rtx op0 = expand_normal (arg0);
7771 rtx op1 = expand_normal (arg1);
7772 rtx op2 = expand_normal (arg2);
7773 rtx op3 = expand_normal (arg3);
a3170dc6
AH
7774 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
7775 enum machine_mode mode1 = insn_data[icode].operand[2].mode;
7776
37409796 7777 gcc_assert (mode0 == mode1);
a3170dc6
AH
7778
7779 if (arg0 == error_mark_node || arg1 == error_mark_node
7780 || arg2 == error_mark_node || arg3 == error_mark_node)
7781 return const0_rtx;
7782
7783 if (target == 0
7784 || GET_MODE (target) != mode0
7785 || ! (*insn_data[icode].operand[0].predicate) (target, mode0))
7786 target = gen_reg_rtx (mode0);
7787
7788 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
7789 op0 = copy_to_mode_reg (mode0, op0);
7790 if (! (*insn_data[icode].operand[1].predicate) (op1, mode1))
7791 op1 = copy_to_mode_reg (mode0, op1);
7792 if (! (*insn_data[icode].operand[1].predicate) (op2, mode1))
7793 op2 = copy_to_mode_reg (mode0, op2);
7794 if (! (*insn_data[icode].operand[1].predicate) (op3, mode1))
7795 op3 = copy_to_mode_reg (mode0, op3);
7796
7797 /* Generate the compare. */
7798 scratch = gen_reg_rtx (CCmode);
7799 pat = GEN_FCN (icode) (scratch, op0, op1);
7800 if (! pat)
7801 return const0_rtx;
7802 emit_insn (pat);
7803
7804 if (mode0 == V2SImode)
7805 emit_insn (gen_spe_evsel (target, op2, op3, scratch));
7806 else
7807 emit_insn (gen_spe_evsel_fs (target, op2, op3, scratch));
7808
7809 return target;
7810}
7811
0ac081f6
AH
7812/* Expand an expression EXP that calls a built-in function,
7813 with result going to TARGET if that's convenient
7814 (and in mode MODE if that's convenient).
7815 SUBTARGET may be used as the target for computing one of EXP's operands.
7816 IGNORE is nonzero if the value is to be ignored. */
7817
7818static rtx
a2369ed3 7819rs6000_expand_builtin (tree exp, rtx target, rtx subtarget ATTRIBUTE_UNUSED,
c4ad648e
AM
7820 enum machine_mode mode ATTRIBUTE_UNUSED,
7821 int ignore ATTRIBUTE_UNUSED)
0ac081f6 7822{
92898235
AH
7823 tree fndecl = TREE_OPERAND (TREE_OPERAND (exp, 0), 0);
7824 tree arglist = TREE_OPERAND (exp, 1);
7825 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
7826 struct builtin_description *d;
7827 size_t i;
7828 rtx ret;
7829 bool success;
f676971a 7830
7ccf35ed
DN
7831 if (fcode == ALTIVEC_BUILTIN_MASK_FOR_LOAD
7832 || fcode == ALTIVEC_BUILTIN_MASK_FOR_STORE)
7833 {
7834 int icode = (int) CODE_FOR_altivec_lvsr;
7835 enum machine_mode tmode = insn_data[icode].operand[0].mode;
7836 enum machine_mode mode = insn_data[icode].operand[1].mode;
7837 tree arg;
7838 rtx op, addr, pat;
7839
37409796 7840 gcc_assert (TARGET_ALTIVEC);
7ccf35ed
DN
7841
7842 arg = TREE_VALUE (arglist);
37409796 7843 gcc_assert (TREE_CODE (TREE_TYPE (arg)) == POINTER_TYPE);
7ccf35ed
DN
7844 op = expand_expr (arg, NULL_RTX, Pmode, EXPAND_NORMAL);
7845 addr = memory_address (mode, op);
7846 if (fcode == ALTIVEC_BUILTIN_MASK_FOR_STORE)
7847 op = addr;
7848 else
7849 {
7850 /* For the load case need to negate the address. */
7851 op = gen_reg_rtx (GET_MODE (addr));
7852 emit_insn (gen_rtx_SET (VOIDmode, op,
7853 gen_rtx_NEG (GET_MODE (addr), addr)));
c4ad648e 7854 }
7ccf35ed
DN
7855 op = gen_rtx_MEM (mode, op);
7856
7857 if (target == 0
7858 || GET_MODE (target) != tmode
7859 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
7860 target = gen_reg_rtx (tmode);
7861
7862 /*pat = gen_altivec_lvsr (target, op);*/
7863 pat = GEN_FCN (icode) (target, op);
7864 if (!pat)
7865 return 0;
7866 emit_insn (pat);
7867
7868 return target;
7869 }
7870
0ac081f6 7871 if (TARGET_ALTIVEC)
92898235
AH
7872 {
7873 ret = altivec_expand_builtin (exp, target, &success);
7874
a3170dc6
AH
7875 if (success)
7876 return ret;
7877 }
7878 if (TARGET_SPE)
7879 {
7880 ret = spe_expand_builtin (exp, target, &success);
7881
92898235
AH
7882 if (success)
7883 return ret;
7884 }
7885
37409796 7886 gcc_assert (TARGET_ALTIVEC || TARGET_SPE);
bb8df8a6 7887
37409796
NS
7888 /* Handle simple unary operations. */
7889 d = (struct builtin_description *) bdesc_1arg;
7890 for (i = 0; i < ARRAY_SIZE (bdesc_1arg); i++, d++)
7891 if (d->code == fcode)
7892 return rs6000_expand_unop_builtin (d->icode, arglist, target);
bb8df8a6 7893
37409796
NS
7894 /* Handle simple binary operations. */
7895 d = (struct builtin_description *) bdesc_2arg;
7896 for (i = 0; i < ARRAY_SIZE (bdesc_2arg); i++, d++)
7897 if (d->code == fcode)
7898 return rs6000_expand_binop_builtin (d->icode, arglist, target);
0ac081f6 7899
37409796
NS
7900 /* Handle simple ternary operations. */
7901 d = (struct builtin_description *) bdesc_3arg;
7902 for (i = 0; i < ARRAY_SIZE (bdesc_3arg); i++, d++)
7903 if (d->code == fcode)
7904 return rs6000_expand_ternop_builtin (d->icode, arglist, target);
bb8df8a6 7905
37409796 7906 gcc_unreachable ();
0ac081f6
AH
7907}
7908
7c62e993
PB
7909static tree
7910build_opaque_vector_type (tree node, int nunits)
7911{
7912 node = copy_node (node);
7913 TYPE_MAIN_VARIANT (node) = node;
7914 return build_vector_type (node, nunits);
7915}
7916
0ac081f6 7917static void
863d938c 7918rs6000_init_builtins (void)
0ac081f6 7919{
4a5eab38
PB
7920 V2SI_type_node = build_vector_type (intSI_type_node, 2);
7921 V2SF_type_node = build_vector_type (float_type_node, 2);
7922 V4HI_type_node = build_vector_type (intHI_type_node, 4);
7923 V4SI_type_node = build_vector_type (intSI_type_node, 4);
7924 V4SF_type_node = build_vector_type (float_type_node, 4);
7e463bda 7925 V8HI_type_node = build_vector_type (intHI_type_node, 8);
4a5eab38
PB
7926 V16QI_type_node = build_vector_type (intQI_type_node, 16);
7927
7928 unsigned_V16QI_type_node = build_vector_type (unsigned_intQI_type_node, 16);
7929 unsigned_V8HI_type_node = build_vector_type (unsigned_intHI_type_node, 8);
7930 unsigned_V4SI_type_node = build_vector_type (unsigned_intSI_type_node, 4);
7931
7c62e993
PB
7932 opaque_V2SF_type_node = build_opaque_vector_type (float_type_node, 2);
7933 opaque_V2SI_type_node = build_opaque_vector_type (intSI_type_node, 2);
6035d635 7934 opaque_p_V2SI_type_node = build_pointer_type (opaque_V2SI_type_node);
58646b77 7935 opaque_V4SI_type_node = copy_node (V4SI_type_node);
3fdaa45a 7936
8bb418a3
ZL
7937 /* The 'vector bool ...' types must be kept distinct from 'vector unsigned ...'
7938 types, especially in C++ land. Similarly, 'vector pixel' is distinct from
7939 'vector unsigned short'. */
7940
8dd16ecc
NS
7941 bool_char_type_node = build_distinct_type_copy (unsigned_intQI_type_node);
7942 bool_short_type_node = build_distinct_type_copy (unsigned_intHI_type_node);
7943 bool_int_type_node = build_distinct_type_copy (unsigned_intSI_type_node);
7944 pixel_type_node = build_distinct_type_copy (unsigned_intHI_type_node);
8bb418a3 7945
58646b77
PB
7946 long_integer_type_internal_node = long_integer_type_node;
7947 long_unsigned_type_internal_node = long_unsigned_type_node;
7948 intQI_type_internal_node = intQI_type_node;
7949 uintQI_type_internal_node = unsigned_intQI_type_node;
7950 intHI_type_internal_node = intHI_type_node;
7951 uintHI_type_internal_node = unsigned_intHI_type_node;
7952 intSI_type_internal_node = intSI_type_node;
7953 uintSI_type_internal_node = unsigned_intSI_type_node;
7954 float_type_internal_node = float_type_node;
7955 void_type_internal_node = void_type_node;
7956
8bb418a3
ZL
7957 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
7958 get_identifier ("__bool char"),
7959 bool_char_type_node));
7960 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
7961 get_identifier ("__bool short"),
7962 bool_short_type_node));
7963 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
7964 get_identifier ("__bool int"),
7965 bool_int_type_node));
7966 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
7967 get_identifier ("__pixel"),
7968 pixel_type_node));
7969
4a5eab38
PB
7970 bool_V16QI_type_node = build_vector_type (bool_char_type_node, 16);
7971 bool_V8HI_type_node = build_vector_type (bool_short_type_node, 8);
7972 bool_V4SI_type_node = build_vector_type (bool_int_type_node, 4);
7973 pixel_V8HI_type_node = build_vector_type (pixel_type_node, 8);
8bb418a3
ZL
7974
7975 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
7976 get_identifier ("__vector unsigned char"),
7977 unsigned_V16QI_type_node));
7978 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
7979 get_identifier ("__vector signed char"),
7980 V16QI_type_node));
7981 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
7982 get_identifier ("__vector __bool char"),
7983 bool_V16QI_type_node));
7984
7985 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
7986 get_identifier ("__vector unsigned short"),
7987 unsigned_V8HI_type_node));
7988 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
7989 get_identifier ("__vector signed short"),
7990 V8HI_type_node));
7991 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
7992 get_identifier ("__vector __bool short"),
7993 bool_V8HI_type_node));
7994
7995 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
7996 get_identifier ("__vector unsigned int"),
7997 unsigned_V4SI_type_node));
7998 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
7999 get_identifier ("__vector signed int"),
8000 V4SI_type_node));
8001 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
8002 get_identifier ("__vector __bool int"),
8003 bool_V4SI_type_node));
8004
8005 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
8006 get_identifier ("__vector float"),
8007 V4SF_type_node));
8008 (*lang_hooks.decls.pushdecl) (build_decl (TYPE_DECL,
8009 get_identifier ("__vector __pixel"),
8010 pixel_V8HI_type_node));
8011
a3170dc6 8012 if (TARGET_SPE)
3fdaa45a 8013 spe_init_builtins ();
0ac081f6
AH
8014 if (TARGET_ALTIVEC)
8015 altivec_init_builtins ();
0559cc77
DE
8016 if (TARGET_ALTIVEC || TARGET_SPE)
8017 rs6000_common_init_builtins ();
69ca3549
DE
8018
8019#if TARGET_XCOFF
8020 /* AIX libm provides clog as __clog. */
8021 if (built_in_decls [BUILT_IN_CLOG])
8022 set_user_assembler_name (built_in_decls [BUILT_IN_CLOG], "__clog");
8023#endif
0ac081f6
AH
8024}
8025
a3170dc6
AH
8026/* Search through a set of builtins and enable the mask bits.
8027 DESC is an array of builtins.
b6d08ca1 8028 SIZE is the total number of builtins.
a3170dc6
AH
8029 START is the builtin enum at which to start.
8030 END is the builtin enum at which to end. */
0ac081f6 8031static void
a2369ed3 8032enable_mask_for_builtins (struct builtin_description *desc, int size,
f676971a 8033 enum rs6000_builtins start,
a2369ed3 8034 enum rs6000_builtins end)
a3170dc6
AH
8035{
8036 int i;
8037
8038 for (i = 0; i < size; ++i)
8039 if (desc[i].code == start)
8040 break;
8041
8042 if (i == size)
8043 return;
8044
8045 for (; i < size; ++i)
8046 {
8047 /* Flip all the bits on. */
8048 desc[i].mask = target_flags;
8049 if (desc[i].code == end)
8050 break;
8051 }
8052}
8053
8054static void
863d938c 8055spe_init_builtins (void)
0ac081f6 8056{
a3170dc6
AH
8057 tree endlink = void_list_node;
8058 tree puint_type_node = build_pointer_type (unsigned_type_node);
8059 tree pushort_type_node = build_pointer_type (short_unsigned_type_node);
ae4b4a02 8060 struct builtin_description *d;
0ac081f6
AH
8061 size_t i;
8062
a3170dc6
AH
8063 tree v2si_ftype_4_v2si
8064 = build_function_type
3fdaa45a
AH
8065 (opaque_V2SI_type_node,
8066 tree_cons (NULL_TREE, opaque_V2SI_type_node,
8067 tree_cons (NULL_TREE, opaque_V2SI_type_node,
8068 tree_cons (NULL_TREE, opaque_V2SI_type_node,
8069 tree_cons (NULL_TREE, opaque_V2SI_type_node,
a3170dc6
AH
8070 endlink)))));
8071
8072 tree v2sf_ftype_4_v2sf
8073 = build_function_type
3fdaa45a
AH
8074 (opaque_V2SF_type_node,
8075 tree_cons (NULL_TREE, opaque_V2SF_type_node,
8076 tree_cons (NULL_TREE, opaque_V2SF_type_node,
8077 tree_cons (NULL_TREE, opaque_V2SF_type_node,
8078 tree_cons (NULL_TREE, opaque_V2SF_type_node,
a3170dc6
AH
8079 endlink)))));
8080
8081 tree int_ftype_int_v2si_v2si
8082 = build_function_type
8083 (integer_type_node,
8084 tree_cons (NULL_TREE, integer_type_node,
3fdaa45a
AH
8085 tree_cons (NULL_TREE, opaque_V2SI_type_node,
8086 tree_cons (NULL_TREE, opaque_V2SI_type_node,
a3170dc6
AH
8087 endlink))));
8088
8089 tree int_ftype_int_v2sf_v2sf
8090 = build_function_type
8091 (integer_type_node,
8092 tree_cons (NULL_TREE, integer_type_node,
3fdaa45a
AH
8093 tree_cons (NULL_TREE, opaque_V2SF_type_node,
8094 tree_cons (NULL_TREE, opaque_V2SF_type_node,
a3170dc6
AH
8095 endlink))));
8096
8097 tree void_ftype_v2si_puint_int
8098 = build_function_type (void_type_node,
3fdaa45a 8099 tree_cons (NULL_TREE, opaque_V2SI_type_node,
a3170dc6
AH
8100 tree_cons (NULL_TREE, puint_type_node,
8101 tree_cons (NULL_TREE,
8102 integer_type_node,
8103 endlink))));
8104
8105 tree void_ftype_v2si_puint_char
8106 = build_function_type (void_type_node,
3fdaa45a 8107 tree_cons (NULL_TREE, opaque_V2SI_type_node,
a3170dc6
AH
8108 tree_cons (NULL_TREE, puint_type_node,
8109 tree_cons (NULL_TREE,
8110 char_type_node,
8111 endlink))));
8112
8113 tree void_ftype_v2si_pv2si_int
8114 = build_function_type (void_type_node,
3fdaa45a 8115 tree_cons (NULL_TREE, opaque_V2SI_type_node,
6035d635 8116 tree_cons (NULL_TREE, opaque_p_V2SI_type_node,
a3170dc6
AH
8117 tree_cons (NULL_TREE,
8118 integer_type_node,
8119 endlink))));
8120
8121 tree void_ftype_v2si_pv2si_char
8122 = build_function_type (void_type_node,
3fdaa45a 8123 tree_cons (NULL_TREE, opaque_V2SI_type_node,
6035d635 8124 tree_cons (NULL_TREE, opaque_p_V2SI_type_node,
a3170dc6
AH
8125 tree_cons (NULL_TREE,
8126 char_type_node,
8127 endlink))));
8128
8129 tree void_ftype_int
8130 = build_function_type (void_type_node,
8131 tree_cons (NULL_TREE, integer_type_node, endlink));
8132
8133 tree int_ftype_void
36e8d515 8134 = build_function_type (integer_type_node, endlink);
a3170dc6
AH
8135
8136 tree v2si_ftype_pv2si_int
3fdaa45a 8137 = build_function_type (opaque_V2SI_type_node,
6035d635 8138 tree_cons (NULL_TREE, opaque_p_V2SI_type_node,
a3170dc6
AH
8139 tree_cons (NULL_TREE, integer_type_node,
8140 endlink)));
8141
8142 tree v2si_ftype_puint_int
3fdaa45a 8143 = build_function_type (opaque_V2SI_type_node,
a3170dc6
AH
8144 tree_cons (NULL_TREE, puint_type_node,
8145 tree_cons (NULL_TREE, integer_type_node,
8146 endlink)));
8147
8148 tree v2si_ftype_pushort_int
3fdaa45a 8149 = build_function_type (opaque_V2SI_type_node,
a3170dc6
AH
8150 tree_cons (NULL_TREE, pushort_type_node,
8151 tree_cons (NULL_TREE, integer_type_node,
8152 endlink)));
8153
00332c9f
AH
8154 tree v2si_ftype_signed_char
8155 = build_function_type (opaque_V2SI_type_node,
8156 tree_cons (NULL_TREE, signed_char_type_node,
8157 endlink));
8158
a3170dc6
AH
8159 /* The initialization of the simple binary and unary builtins is
8160 done in rs6000_common_init_builtins, but we have to enable the
8161 mask bits here manually because we have run out of `target_flags'
8162 bits. We really need to redesign this mask business. */
8163
8164 enable_mask_for_builtins ((struct builtin_description *) bdesc_2arg,
8165 ARRAY_SIZE (bdesc_2arg),
8166 SPE_BUILTIN_EVADDW,
8167 SPE_BUILTIN_EVXOR);
8168 enable_mask_for_builtins ((struct builtin_description *) bdesc_1arg,
8169 ARRAY_SIZE (bdesc_1arg),
8170 SPE_BUILTIN_EVABS,
8171 SPE_BUILTIN_EVSUBFUSIAAW);
8172 enable_mask_for_builtins ((struct builtin_description *) bdesc_spe_predicates,
8173 ARRAY_SIZE (bdesc_spe_predicates),
8174 SPE_BUILTIN_EVCMPEQ,
8175 SPE_BUILTIN_EVFSTSTLT);
8176 enable_mask_for_builtins ((struct builtin_description *) bdesc_spe_evsel,
8177 ARRAY_SIZE (bdesc_spe_evsel),
8178 SPE_BUILTIN_EVSEL_CMPGTS,
8179 SPE_BUILTIN_EVSEL_FSTSTEQ);
8180
36252949
AH
8181 (*lang_hooks.decls.pushdecl)
8182 (build_decl (TYPE_DECL, get_identifier ("__ev64_opaque__"),
8183 opaque_V2SI_type_node));
8184
a3170dc6 8185 /* Initialize irregular SPE builtins. */
f676971a 8186
a3170dc6
AH
8187 def_builtin (target_flags, "__builtin_spe_mtspefscr", void_ftype_int, SPE_BUILTIN_MTSPEFSCR);
8188 def_builtin (target_flags, "__builtin_spe_mfspefscr", int_ftype_void, SPE_BUILTIN_MFSPEFSCR);
8189 def_builtin (target_flags, "__builtin_spe_evstddx", void_ftype_v2si_pv2si_int, SPE_BUILTIN_EVSTDDX);
8190 def_builtin (target_flags, "__builtin_spe_evstdhx", void_ftype_v2si_pv2si_int, SPE_BUILTIN_EVSTDHX);
8191 def_builtin (target_flags, "__builtin_spe_evstdwx", void_ftype_v2si_pv2si_int, SPE_BUILTIN_EVSTDWX);
8192 def_builtin (target_flags, "__builtin_spe_evstwhex", void_ftype_v2si_puint_int, SPE_BUILTIN_EVSTWHEX);
8193 def_builtin (target_flags, "__builtin_spe_evstwhox", void_ftype_v2si_puint_int, SPE_BUILTIN_EVSTWHOX);
8194 def_builtin (target_flags, "__builtin_spe_evstwwex", void_ftype_v2si_puint_int, SPE_BUILTIN_EVSTWWEX);
8195 def_builtin (target_flags, "__builtin_spe_evstwwox", void_ftype_v2si_puint_int, SPE_BUILTIN_EVSTWWOX);
8196 def_builtin (target_flags, "__builtin_spe_evstdd", void_ftype_v2si_pv2si_char, SPE_BUILTIN_EVSTDD);
8197 def_builtin (target_flags, "__builtin_spe_evstdh", void_ftype_v2si_pv2si_char, SPE_BUILTIN_EVSTDH);
8198 def_builtin (target_flags, "__builtin_spe_evstdw", void_ftype_v2si_pv2si_char, SPE_BUILTIN_EVSTDW);
8199 def_builtin (target_flags, "__builtin_spe_evstwhe", void_ftype_v2si_puint_char, SPE_BUILTIN_EVSTWHE);
8200 def_builtin (target_flags, "__builtin_spe_evstwho", void_ftype_v2si_puint_char, SPE_BUILTIN_EVSTWHO);
8201 def_builtin (target_flags, "__builtin_spe_evstwwe", void_ftype_v2si_puint_char, SPE_BUILTIN_EVSTWWE);
8202 def_builtin (target_flags, "__builtin_spe_evstwwo", void_ftype_v2si_puint_char, SPE_BUILTIN_EVSTWWO);
00332c9f
AH
8203 def_builtin (target_flags, "__builtin_spe_evsplatfi", v2si_ftype_signed_char, SPE_BUILTIN_EVSPLATFI);
8204 def_builtin (target_flags, "__builtin_spe_evsplati", v2si_ftype_signed_char, SPE_BUILTIN_EVSPLATI);
a3170dc6
AH
8205
8206 /* Loads. */
8207 def_builtin (target_flags, "__builtin_spe_evlddx", v2si_ftype_pv2si_int, SPE_BUILTIN_EVLDDX);
8208 def_builtin (target_flags, "__builtin_spe_evldwx", v2si_ftype_pv2si_int, SPE_BUILTIN_EVLDWX);
8209 def_builtin (target_flags, "__builtin_spe_evldhx", v2si_ftype_pv2si_int, SPE_BUILTIN_EVLDHX);
8210 def_builtin (target_flags, "__builtin_spe_evlwhex", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHEX);
8211 def_builtin (target_flags, "__builtin_spe_evlwhoux", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHOUX);
8212 def_builtin (target_flags, "__builtin_spe_evlwhosx", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHOSX);
8213 def_builtin (target_flags, "__builtin_spe_evlwwsplatx", v2si_ftype_puint_int, SPE_BUILTIN_EVLWWSPLATX);
8214 def_builtin (target_flags, "__builtin_spe_evlwhsplatx", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHSPLATX);
8215 def_builtin (target_flags, "__builtin_spe_evlhhesplatx", v2si_ftype_pushort_int, SPE_BUILTIN_EVLHHESPLATX);
8216 def_builtin (target_flags, "__builtin_spe_evlhhousplatx", v2si_ftype_pushort_int, SPE_BUILTIN_EVLHHOUSPLATX);
8217 def_builtin (target_flags, "__builtin_spe_evlhhossplatx", v2si_ftype_pushort_int, SPE_BUILTIN_EVLHHOSSPLATX);
8218 def_builtin (target_flags, "__builtin_spe_evldd", v2si_ftype_pv2si_int, SPE_BUILTIN_EVLDD);
8219 def_builtin (target_flags, "__builtin_spe_evldw", v2si_ftype_pv2si_int, SPE_BUILTIN_EVLDW);
8220 def_builtin (target_flags, "__builtin_spe_evldh", v2si_ftype_pv2si_int, SPE_BUILTIN_EVLDH);
8221 def_builtin (target_flags, "__builtin_spe_evlhhesplat", v2si_ftype_pushort_int, SPE_BUILTIN_EVLHHESPLAT);
8222 def_builtin (target_flags, "__builtin_spe_evlhhossplat", v2si_ftype_pushort_int, SPE_BUILTIN_EVLHHOSSPLAT);
8223 def_builtin (target_flags, "__builtin_spe_evlhhousplat", v2si_ftype_pushort_int, SPE_BUILTIN_EVLHHOUSPLAT);
8224 def_builtin (target_flags, "__builtin_spe_evlwhe", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHE);
8225 def_builtin (target_flags, "__builtin_spe_evlwhos", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHOS);
8226 def_builtin (target_flags, "__builtin_spe_evlwhou", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHOU);
8227 def_builtin (target_flags, "__builtin_spe_evlwhsplat", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHSPLAT);
8228 def_builtin (target_flags, "__builtin_spe_evlwwsplat", v2si_ftype_puint_int, SPE_BUILTIN_EVLWWSPLAT);
8229
8230 /* Predicates. */
8231 d = (struct builtin_description *) bdesc_spe_predicates;
8232 for (i = 0; i < ARRAY_SIZE (bdesc_spe_predicates); ++i, d++)
8233 {
8234 tree type;
8235
8236 switch (insn_data[d->icode].operand[1].mode)
8237 {
8238 case V2SImode:
8239 type = int_ftype_int_v2si_v2si;
8240 break;
8241 case V2SFmode:
8242 type = int_ftype_int_v2sf_v2sf;
8243 break;
8244 default:
37409796 8245 gcc_unreachable ();
a3170dc6
AH
8246 }
8247
8248 def_builtin (d->mask, d->name, type, d->code);
8249 }
8250
8251 /* Evsel predicates. */
8252 d = (struct builtin_description *) bdesc_spe_evsel;
8253 for (i = 0; i < ARRAY_SIZE (bdesc_spe_evsel); ++i, d++)
8254 {
8255 tree type;
8256
8257 switch (insn_data[d->icode].operand[1].mode)
8258 {
8259 case V2SImode:
8260 type = v2si_ftype_4_v2si;
8261 break;
8262 case V2SFmode:
8263 type = v2sf_ftype_4_v2sf;
8264 break;
8265 default:
37409796 8266 gcc_unreachable ();
a3170dc6
AH
8267 }
8268
8269 def_builtin (d->mask, d->name, type, d->code);
8270 }
8271}
8272
8273static void
863d938c 8274altivec_init_builtins (void)
a3170dc6
AH
8275{
8276 struct builtin_description *d;
8277 struct builtin_description_predicates *dp;
8278 size_t i;
7a4eca66
DE
8279 tree ftype;
8280
a3170dc6
AH
8281 tree pfloat_type_node = build_pointer_type (float_type_node);
8282 tree pint_type_node = build_pointer_type (integer_type_node);
8283 tree pshort_type_node = build_pointer_type (short_integer_type_node);
8284 tree pchar_type_node = build_pointer_type (char_type_node);
8285
8286 tree pvoid_type_node = build_pointer_type (void_type_node);
8287
0dbc3651
ZW
8288 tree pcfloat_type_node = build_pointer_type (build_qualified_type (float_type_node, TYPE_QUAL_CONST));
8289 tree pcint_type_node = build_pointer_type (build_qualified_type (integer_type_node, TYPE_QUAL_CONST));
8290 tree pcshort_type_node = build_pointer_type (build_qualified_type (short_integer_type_node, TYPE_QUAL_CONST));
8291 tree pcchar_type_node = build_pointer_type (build_qualified_type (char_type_node, TYPE_QUAL_CONST));
8292
8293 tree pcvoid_type_node = build_pointer_type (build_qualified_type (void_type_node, TYPE_QUAL_CONST));
8294
58646b77
PB
8295 tree int_ftype_opaque
8296 = build_function_type_list (integer_type_node,
8297 opaque_V4SI_type_node, NULL_TREE);
8298
8299 tree opaque_ftype_opaque_int
8300 = build_function_type_list (opaque_V4SI_type_node,
8301 opaque_V4SI_type_node, integer_type_node, NULL_TREE);
8302 tree opaque_ftype_opaque_opaque_int
8303 = build_function_type_list (opaque_V4SI_type_node,
8304 opaque_V4SI_type_node, opaque_V4SI_type_node,
8305 integer_type_node, NULL_TREE);
8306 tree int_ftype_int_opaque_opaque
8307 = build_function_type_list (integer_type_node,
8308 integer_type_node, opaque_V4SI_type_node,
8309 opaque_V4SI_type_node, NULL_TREE);
a3170dc6
AH
8310 tree int_ftype_int_v4si_v4si
8311 = build_function_type_list (integer_type_node,
8312 integer_type_node, V4SI_type_node,
8313 V4SI_type_node, NULL_TREE);
0dbc3651
ZW
8314 tree v4sf_ftype_pcfloat
8315 = build_function_type_list (V4SF_type_node, pcfloat_type_node, NULL_TREE);
a3170dc6 8316 tree void_ftype_pfloat_v4sf
b4de2f7d 8317 = build_function_type_list (void_type_node,
a3170dc6 8318 pfloat_type_node, V4SF_type_node, NULL_TREE);
0dbc3651
ZW
8319 tree v4si_ftype_pcint
8320 = build_function_type_list (V4SI_type_node, pcint_type_node, NULL_TREE);
8321 tree void_ftype_pint_v4si
b4de2f7d
AH
8322 = build_function_type_list (void_type_node,
8323 pint_type_node, V4SI_type_node, NULL_TREE);
0dbc3651
ZW
8324 tree v8hi_ftype_pcshort
8325 = build_function_type_list (V8HI_type_node, pcshort_type_node, NULL_TREE);
f18c054f 8326 tree void_ftype_pshort_v8hi
b4de2f7d
AH
8327 = build_function_type_list (void_type_node,
8328 pshort_type_node, V8HI_type_node, NULL_TREE);
0dbc3651
ZW
8329 tree v16qi_ftype_pcchar
8330 = build_function_type_list (V16QI_type_node, pcchar_type_node, NULL_TREE);
f18c054f 8331 tree void_ftype_pchar_v16qi
b4de2f7d
AH
8332 = build_function_type_list (void_type_node,
8333 pchar_type_node, V16QI_type_node, NULL_TREE);
95385cbb 8334 tree void_ftype_v4si
b4de2f7d 8335 = build_function_type_list (void_type_node, V4SI_type_node, NULL_TREE);
a3170dc6
AH
8336 tree v8hi_ftype_void
8337 = build_function_type (V8HI_type_node, void_list_node);
8338 tree void_ftype_void
8339 = build_function_type (void_type_node, void_list_node);
e34b6648
JJ
8340 tree void_ftype_int
8341 = build_function_type_list (void_type_node, integer_type_node, NULL_TREE);
0dbc3651 8342
58646b77
PB
8343 tree opaque_ftype_long_pcvoid
8344 = build_function_type_list (opaque_V4SI_type_node,
8345 long_integer_type_node, pcvoid_type_node, NULL_TREE);
b4a62fa0 8346 tree v16qi_ftype_long_pcvoid
a3170dc6 8347 = build_function_type_list (V16QI_type_node,
b4a62fa0
SB
8348 long_integer_type_node, pcvoid_type_node, NULL_TREE);
8349 tree v8hi_ftype_long_pcvoid
a3170dc6 8350 = build_function_type_list (V8HI_type_node,
b4a62fa0
SB
8351 long_integer_type_node, pcvoid_type_node, NULL_TREE);
8352 tree v4si_ftype_long_pcvoid
a3170dc6 8353 = build_function_type_list (V4SI_type_node,
b4a62fa0 8354 long_integer_type_node, pcvoid_type_node, NULL_TREE);
0dbc3651 8355
58646b77
PB
8356 tree void_ftype_opaque_long_pvoid
8357 = build_function_type_list (void_type_node,
8358 opaque_V4SI_type_node, long_integer_type_node,
8359 pvoid_type_node, NULL_TREE);
b4a62fa0 8360 tree void_ftype_v4si_long_pvoid
b4de2f7d 8361 = build_function_type_list (void_type_node,
b4a62fa0 8362 V4SI_type_node, long_integer_type_node,
b4de2f7d 8363 pvoid_type_node, NULL_TREE);
b4a62fa0 8364 tree void_ftype_v16qi_long_pvoid
b4de2f7d 8365 = build_function_type_list (void_type_node,
b4a62fa0 8366 V16QI_type_node, long_integer_type_node,
b4de2f7d 8367 pvoid_type_node, NULL_TREE);
b4a62fa0 8368 tree void_ftype_v8hi_long_pvoid
b4de2f7d 8369 = build_function_type_list (void_type_node,
b4a62fa0 8370 V8HI_type_node, long_integer_type_node,
b4de2f7d 8371 pvoid_type_node, NULL_TREE);
a3170dc6
AH
8372 tree int_ftype_int_v8hi_v8hi
8373 = build_function_type_list (integer_type_node,
8374 integer_type_node, V8HI_type_node,
8375 V8HI_type_node, NULL_TREE);
8376 tree int_ftype_int_v16qi_v16qi
8377 = build_function_type_list (integer_type_node,
8378 integer_type_node, V16QI_type_node,
8379 V16QI_type_node, NULL_TREE);
8380 tree int_ftype_int_v4sf_v4sf
8381 = build_function_type_list (integer_type_node,
8382 integer_type_node, V4SF_type_node,
8383 V4SF_type_node, NULL_TREE);
8384 tree v4si_ftype_v4si
8385 = build_function_type_list (V4SI_type_node, V4SI_type_node, NULL_TREE);
8386 tree v8hi_ftype_v8hi
8387 = build_function_type_list (V8HI_type_node, V8HI_type_node, NULL_TREE);
8388 tree v16qi_ftype_v16qi
8389 = build_function_type_list (V16QI_type_node, V16QI_type_node, NULL_TREE);
8390 tree v4sf_ftype_v4sf
8391 = build_function_type_list (V4SF_type_node, V4SF_type_node, NULL_TREE);
8bb418a3 8392 tree void_ftype_pcvoid_int_int
a3170dc6 8393 = build_function_type_list (void_type_node,
0dbc3651 8394 pcvoid_type_node, integer_type_node,
8bb418a3 8395 integer_type_node, NULL_TREE);
8bb418a3 8396
0dbc3651
ZW
8397 def_builtin (MASK_ALTIVEC, "__builtin_altivec_ld_internal_4sf", v4sf_ftype_pcfloat,
8398 ALTIVEC_BUILTIN_LD_INTERNAL_4sf);
8399 def_builtin (MASK_ALTIVEC, "__builtin_altivec_st_internal_4sf", void_ftype_pfloat_v4sf,
8400 ALTIVEC_BUILTIN_ST_INTERNAL_4sf);
8401 def_builtin (MASK_ALTIVEC, "__builtin_altivec_ld_internal_4si", v4si_ftype_pcint,
8402 ALTIVEC_BUILTIN_LD_INTERNAL_4si);
8403 def_builtin (MASK_ALTIVEC, "__builtin_altivec_st_internal_4si", void_ftype_pint_v4si,
8404 ALTIVEC_BUILTIN_ST_INTERNAL_4si);
8405 def_builtin (MASK_ALTIVEC, "__builtin_altivec_ld_internal_8hi", v8hi_ftype_pcshort,
8406 ALTIVEC_BUILTIN_LD_INTERNAL_8hi);
8407 def_builtin (MASK_ALTIVEC, "__builtin_altivec_st_internal_8hi", void_ftype_pshort_v8hi,
8408 ALTIVEC_BUILTIN_ST_INTERNAL_8hi);
8409 def_builtin (MASK_ALTIVEC, "__builtin_altivec_ld_internal_16qi", v16qi_ftype_pcchar,
8410 ALTIVEC_BUILTIN_LD_INTERNAL_16qi);
8411 def_builtin (MASK_ALTIVEC, "__builtin_altivec_st_internal_16qi", void_ftype_pchar_v16qi,
8412 ALTIVEC_BUILTIN_ST_INTERNAL_16qi);
a3170dc6
AH
8413 def_builtin (MASK_ALTIVEC, "__builtin_altivec_mtvscr", void_ftype_v4si, ALTIVEC_BUILTIN_MTVSCR);
8414 def_builtin (MASK_ALTIVEC, "__builtin_altivec_mfvscr", v8hi_ftype_void, ALTIVEC_BUILTIN_MFVSCR);
8415 def_builtin (MASK_ALTIVEC, "__builtin_altivec_dssall", void_ftype_void, ALTIVEC_BUILTIN_DSSALL);
e34b6648 8416 def_builtin (MASK_ALTIVEC, "__builtin_altivec_dss", void_ftype_int, ALTIVEC_BUILTIN_DSS);
b4a62fa0
SB
8417 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvsl", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVSL);
8418 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvsr", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVSR);
8419 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvebx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVEBX);
8420 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvehx", v8hi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVEHX);
8421 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvewx", v4si_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVEWX);
8422 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvxl", v4si_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVXL);
8423 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvx", v4si_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVX);
8424 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvx", void_ftype_v4si_long_pvoid, ALTIVEC_BUILTIN_STVX);
8425 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvewx", void_ftype_v4si_long_pvoid, ALTIVEC_BUILTIN_STVEWX);
8426 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvxl", void_ftype_v4si_long_pvoid, ALTIVEC_BUILTIN_STVXL);
8427 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvebx", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_STVEBX);
8428 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvehx", void_ftype_v8hi_long_pvoid, ALTIVEC_BUILTIN_STVEHX);
58646b77
PB
8429 def_builtin (MASK_ALTIVEC, "__builtin_vec_ld", opaque_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LD);
8430 def_builtin (MASK_ALTIVEC, "__builtin_vec_lde", opaque_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LDE);
8431 def_builtin (MASK_ALTIVEC, "__builtin_vec_ldl", opaque_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LDL);
8432 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvsl", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVSL);
8433 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvsr", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVSR);
8434 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvebx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVEBX);
8435 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvehx", v8hi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVEHX);
8436 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvewx", v4si_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVEWX);
8437 def_builtin (MASK_ALTIVEC, "__builtin_vec_st", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_ST);
8438 def_builtin (MASK_ALTIVEC, "__builtin_vec_ste", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_STE);
8439 def_builtin (MASK_ALTIVEC, "__builtin_vec_stl", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_STL);
8440 def_builtin (MASK_ALTIVEC, "__builtin_vec_stvewx", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_STVEWX);
8441 def_builtin (MASK_ALTIVEC, "__builtin_vec_stvebx", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_STVEBX);
8442 def_builtin (MASK_ALTIVEC, "__builtin_vec_stvehx", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_STVEHX);
8443
8444 def_builtin (MASK_ALTIVEC, "__builtin_vec_step", int_ftype_opaque, ALTIVEC_BUILTIN_VEC_STEP);
8445
8446 def_builtin (MASK_ALTIVEC, "__builtin_vec_sld", opaque_ftype_opaque_opaque_int, ALTIVEC_BUILTIN_VEC_SLD);
8447 def_builtin (MASK_ALTIVEC, "__builtin_vec_splat", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_SPLAT);
8448 def_builtin (MASK_ALTIVEC, "__builtin_vec_vspltw", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VSPLTW);
8449 def_builtin (MASK_ALTIVEC, "__builtin_vec_vsplth", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VSPLTH);
8450 def_builtin (MASK_ALTIVEC, "__builtin_vec_vspltb", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VSPLTB);
8451 def_builtin (MASK_ALTIVEC, "__builtin_vec_ctf", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_CTF);
8452 def_builtin (MASK_ALTIVEC, "__builtin_vec_vcfsx", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VCFSX);
8453 def_builtin (MASK_ALTIVEC, "__builtin_vec_vcfux", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VCFUX);
8454 def_builtin (MASK_ALTIVEC, "__builtin_vec_cts", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_CTS);
8455 def_builtin (MASK_ALTIVEC, "__builtin_vec_ctu", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_CTU);
8bb418a3 8456
a3170dc6
AH
8457 /* Add the DST variants. */
8458 d = (struct builtin_description *) bdesc_dst;
8459 for (i = 0; i < ARRAY_SIZE (bdesc_dst); i++, d++)
8bb418a3 8460 def_builtin (d->mask, d->name, void_ftype_pcvoid_int_int, d->code);
a3170dc6
AH
8461
8462 /* Initialize the predicates. */
8463 dp = (struct builtin_description_predicates *) bdesc_altivec_preds;
8464 for (i = 0; i < ARRAY_SIZE (bdesc_altivec_preds); i++, dp++)
8465 {
8466 enum machine_mode mode1;
8467 tree type;
58646b77
PB
8468 bool is_overloaded = dp->code >= ALTIVEC_BUILTIN_OVERLOADED_FIRST
8469 && dp->code <= ALTIVEC_BUILTIN_OVERLOADED_LAST;
a3170dc6 8470
58646b77
PB
8471 if (is_overloaded)
8472 mode1 = VOIDmode;
8473 else
8474 mode1 = insn_data[dp->icode].operand[1].mode;
a3170dc6
AH
8475
8476 switch (mode1)
8477 {
58646b77
PB
8478 case VOIDmode:
8479 type = int_ftype_int_opaque_opaque;
8480 break;
a3170dc6
AH
8481 case V4SImode:
8482 type = int_ftype_int_v4si_v4si;
8483 break;
8484 case V8HImode:
8485 type = int_ftype_int_v8hi_v8hi;
8486 break;
8487 case V16QImode:
8488 type = int_ftype_int_v16qi_v16qi;
8489 break;
8490 case V4SFmode:
8491 type = int_ftype_int_v4sf_v4sf;
8492 break;
8493 default:
37409796 8494 gcc_unreachable ();
a3170dc6 8495 }
f676971a 8496
a3170dc6
AH
8497 def_builtin (dp->mask, dp->name, type, dp->code);
8498 }
8499
8500 /* Initialize the abs* operators. */
8501 d = (struct builtin_description *) bdesc_abs;
8502 for (i = 0; i < ARRAY_SIZE (bdesc_abs); i++, d++)
8503 {
8504 enum machine_mode mode0;
8505 tree type;
8506
8507 mode0 = insn_data[d->icode].operand[0].mode;
8508
8509 switch (mode0)
8510 {
8511 case V4SImode:
8512 type = v4si_ftype_v4si;
8513 break;
8514 case V8HImode:
8515 type = v8hi_ftype_v8hi;
8516 break;
8517 case V16QImode:
8518 type = v16qi_ftype_v16qi;
8519 break;
8520 case V4SFmode:
8521 type = v4sf_ftype_v4sf;
8522 break;
8523 default:
37409796 8524 gcc_unreachable ();
a3170dc6 8525 }
f676971a 8526
a3170dc6
AH
8527 def_builtin (d->mask, d->name, type, d->code);
8528 }
7ccf35ed 8529
13c62176
DN
8530 if (TARGET_ALTIVEC)
8531 {
8532 tree decl;
8533
8534 /* Initialize target builtin that implements
8535 targetm.vectorize.builtin_mask_for_load. */
8536
8537 decl = lang_hooks.builtin_function ("__builtin_altivec_mask_for_load",
8bb46326
DN
8538 v16qi_ftype_long_pcvoid,
8539 ALTIVEC_BUILTIN_MASK_FOR_LOAD,
8540 BUILT_IN_MD, NULL,
8541 tree_cons (get_identifier ("const"),
8542 NULL_TREE, NULL_TREE));
13c62176
DN
8543 /* Record the decl. Will be used by rs6000_builtin_mask_for_load. */
8544 altivec_builtin_mask_for_load = decl;
13c62176 8545 }
7a4eca66
DE
8546
8547 /* Access to the vec_init patterns. */
8548 ftype = build_function_type_list (V4SI_type_node, integer_type_node,
8549 integer_type_node, integer_type_node,
8550 integer_type_node, NULL_TREE);
8551 def_builtin (MASK_ALTIVEC, "__builtin_vec_init_v4si", ftype,
8552 ALTIVEC_BUILTIN_VEC_INIT_V4SI);
8553
8554 ftype = build_function_type_list (V8HI_type_node, short_integer_type_node,
8555 short_integer_type_node,
8556 short_integer_type_node,
8557 short_integer_type_node,
8558 short_integer_type_node,
8559 short_integer_type_node,
8560 short_integer_type_node,
8561 short_integer_type_node, NULL_TREE);
8562 def_builtin (MASK_ALTIVEC, "__builtin_vec_init_v8hi", ftype,
8563 ALTIVEC_BUILTIN_VEC_INIT_V8HI);
8564
8565 ftype = build_function_type_list (V16QI_type_node, char_type_node,
8566 char_type_node, char_type_node,
8567 char_type_node, char_type_node,
8568 char_type_node, char_type_node,
8569 char_type_node, char_type_node,
8570 char_type_node, char_type_node,
8571 char_type_node, char_type_node,
8572 char_type_node, char_type_node,
8573 char_type_node, NULL_TREE);
8574 def_builtin (MASK_ALTIVEC, "__builtin_vec_init_v16qi", ftype,
8575 ALTIVEC_BUILTIN_VEC_INIT_V16QI);
8576
8577 ftype = build_function_type_list (V4SF_type_node, float_type_node,
8578 float_type_node, float_type_node,
8579 float_type_node, NULL_TREE);
8580 def_builtin (MASK_ALTIVEC, "__builtin_vec_init_v4sf", ftype,
8581 ALTIVEC_BUILTIN_VEC_INIT_V4SF);
8582
8583 /* Access to the vec_set patterns. */
8584 ftype = build_function_type_list (V4SI_type_node, V4SI_type_node,
8585 intSI_type_node,
8586 integer_type_node, NULL_TREE);
8587 def_builtin (MASK_ALTIVEC, "__builtin_vec_set_v4si", ftype,
8588 ALTIVEC_BUILTIN_VEC_SET_V4SI);
8589
8590 ftype = build_function_type_list (V8HI_type_node, V8HI_type_node,
8591 intHI_type_node,
8592 integer_type_node, NULL_TREE);
8593 def_builtin (MASK_ALTIVEC, "__builtin_vec_set_v8hi", ftype,
8594 ALTIVEC_BUILTIN_VEC_SET_V8HI);
8595
8596 ftype = build_function_type_list (V8HI_type_node, V16QI_type_node,
8597 intQI_type_node,
8598 integer_type_node, NULL_TREE);
8599 def_builtin (MASK_ALTIVEC, "__builtin_vec_set_v16qi", ftype,
8600 ALTIVEC_BUILTIN_VEC_SET_V16QI);
8601
8602 ftype = build_function_type_list (V4SF_type_node, V4SF_type_node,
8603 float_type_node,
8604 integer_type_node, NULL_TREE);
8605 def_builtin (MASK_ALTIVEC, "__builtin_vec_set_v4sf", ftype,
8606 ALTIVEC_BUILTIN_VEC_SET_V4SF);
8607
8608 /* Access to the vec_extract patterns. */
8609 ftype = build_function_type_list (intSI_type_node, V4SI_type_node,
8610 integer_type_node, NULL_TREE);
8611 def_builtin (MASK_ALTIVEC, "__builtin_vec_ext_v4si", ftype,
8612 ALTIVEC_BUILTIN_VEC_EXT_V4SI);
8613
8614 ftype = build_function_type_list (intHI_type_node, V8HI_type_node,
8615 integer_type_node, NULL_TREE);
8616 def_builtin (MASK_ALTIVEC, "__builtin_vec_ext_v8hi", ftype,
8617 ALTIVEC_BUILTIN_VEC_EXT_V8HI);
8618
8619 ftype = build_function_type_list (intQI_type_node, V16QI_type_node,
8620 integer_type_node, NULL_TREE);
8621 def_builtin (MASK_ALTIVEC, "__builtin_vec_ext_v16qi", ftype,
8622 ALTIVEC_BUILTIN_VEC_EXT_V16QI);
8623
8624 ftype = build_function_type_list (float_type_node, V4SF_type_node,
8625 integer_type_node, NULL_TREE);
8626 def_builtin (MASK_ALTIVEC, "__builtin_vec_ext_v4sf", ftype,
8627 ALTIVEC_BUILTIN_VEC_EXT_V4SF);
a3170dc6
AH
8628}
8629
8630static void
863d938c 8631rs6000_common_init_builtins (void)
a3170dc6
AH
8632{
8633 struct builtin_description *d;
8634 size_t i;
8635
8636 tree v4sf_ftype_v4sf_v4sf_v16qi
8637 = build_function_type_list (V4SF_type_node,
8638 V4SF_type_node, V4SF_type_node,
8639 V16QI_type_node, NULL_TREE);
8640 tree v4si_ftype_v4si_v4si_v16qi
8641 = build_function_type_list (V4SI_type_node,
8642 V4SI_type_node, V4SI_type_node,
8643 V16QI_type_node, NULL_TREE);
8644 tree v8hi_ftype_v8hi_v8hi_v16qi
8645 = build_function_type_list (V8HI_type_node,
8646 V8HI_type_node, V8HI_type_node,
8647 V16QI_type_node, NULL_TREE);
8648 tree v16qi_ftype_v16qi_v16qi_v16qi
8649 = build_function_type_list (V16QI_type_node,
8650 V16QI_type_node, V16QI_type_node,
8651 V16QI_type_node, NULL_TREE);
b9e4e5d1
ZL
8652 tree v4si_ftype_int
8653 = build_function_type_list (V4SI_type_node, integer_type_node, NULL_TREE);
8654 tree v8hi_ftype_int
8655 = build_function_type_list (V8HI_type_node, integer_type_node, NULL_TREE);
8656 tree v16qi_ftype_int
8657 = build_function_type_list (V16QI_type_node, integer_type_node, NULL_TREE);
a3170dc6
AH
8658 tree v8hi_ftype_v16qi
8659 = build_function_type_list (V8HI_type_node, V16QI_type_node, NULL_TREE);
8660 tree v4sf_ftype_v4sf
8661 = build_function_type_list (V4SF_type_node, V4SF_type_node, NULL_TREE);
8662
8663 tree v2si_ftype_v2si_v2si
2abe3e28
AH
8664 = build_function_type_list (opaque_V2SI_type_node,
8665 opaque_V2SI_type_node,
8666 opaque_V2SI_type_node, NULL_TREE);
a3170dc6
AH
8667
8668 tree v2sf_ftype_v2sf_v2sf
2abe3e28
AH
8669 = build_function_type_list (opaque_V2SF_type_node,
8670 opaque_V2SF_type_node,
8671 opaque_V2SF_type_node, NULL_TREE);
a3170dc6
AH
8672
8673 tree v2si_ftype_int_int
2abe3e28 8674 = build_function_type_list (opaque_V2SI_type_node,
a3170dc6
AH
8675 integer_type_node, integer_type_node,
8676 NULL_TREE);
8677
58646b77
PB
8678 tree opaque_ftype_opaque
8679 = build_function_type_list (opaque_V4SI_type_node,
8680 opaque_V4SI_type_node, NULL_TREE);
8681
a3170dc6 8682 tree v2si_ftype_v2si
2abe3e28
AH
8683 = build_function_type_list (opaque_V2SI_type_node,
8684 opaque_V2SI_type_node, NULL_TREE);
a3170dc6
AH
8685
8686 tree v2sf_ftype_v2sf
2abe3e28
AH
8687 = build_function_type_list (opaque_V2SF_type_node,
8688 opaque_V2SF_type_node, NULL_TREE);
f676971a 8689
a3170dc6 8690 tree v2sf_ftype_v2si
2abe3e28
AH
8691 = build_function_type_list (opaque_V2SF_type_node,
8692 opaque_V2SI_type_node, NULL_TREE);
a3170dc6
AH
8693
8694 tree v2si_ftype_v2sf
2abe3e28
AH
8695 = build_function_type_list (opaque_V2SI_type_node,
8696 opaque_V2SF_type_node, NULL_TREE);
a3170dc6
AH
8697
8698 tree v2si_ftype_v2si_char
2abe3e28
AH
8699 = build_function_type_list (opaque_V2SI_type_node,
8700 opaque_V2SI_type_node,
8701 char_type_node, NULL_TREE);
a3170dc6
AH
8702
8703 tree v2si_ftype_int_char
2abe3e28 8704 = build_function_type_list (opaque_V2SI_type_node,
a3170dc6
AH
8705 integer_type_node, char_type_node, NULL_TREE);
8706
8707 tree v2si_ftype_char
2abe3e28
AH
8708 = build_function_type_list (opaque_V2SI_type_node,
8709 char_type_node, NULL_TREE);
a3170dc6
AH
8710
8711 tree int_ftype_int_int
8712 = build_function_type_list (integer_type_node,
8713 integer_type_node, integer_type_node,
8714 NULL_TREE);
95385cbb 8715
58646b77
PB
8716 tree opaque_ftype_opaque_opaque
8717 = build_function_type_list (opaque_V4SI_type_node,
8718 opaque_V4SI_type_node, opaque_V4SI_type_node, NULL_TREE);
0ac081f6 8719 tree v4si_ftype_v4si_v4si
b4de2f7d
AH
8720 = build_function_type_list (V4SI_type_node,
8721 V4SI_type_node, V4SI_type_node, NULL_TREE);
b9e4e5d1 8722 tree v4sf_ftype_v4si_int
b4de2f7d 8723 = build_function_type_list (V4SF_type_node,
b9e4e5d1
ZL
8724 V4SI_type_node, integer_type_node, NULL_TREE);
8725 tree v4si_ftype_v4sf_int
b4de2f7d 8726 = build_function_type_list (V4SI_type_node,
b9e4e5d1
ZL
8727 V4SF_type_node, integer_type_node, NULL_TREE);
8728 tree v4si_ftype_v4si_int
b4de2f7d 8729 = build_function_type_list (V4SI_type_node,
b9e4e5d1
ZL
8730 V4SI_type_node, integer_type_node, NULL_TREE);
8731 tree v8hi_ftype_v8hi_int
b4de2f7d 8732 = build_function_type_list (V8HI_type_node,
b9e4e5d1
ZL
8733 V8HI_type_node, integer_type_node, NULL_TREE);
8734 tree v16qi_ftype_v16qi_int
b4de2f7d 8735 = build_function_type_list (V16QI_type_node,
b9e4e5d1
ZL
8736 V16QI_type_node, integer_type_node, NULL_TREE);
8737 tree v16qi_ftype_v16qi_v16qi_int
b4de2f7d
AH
8738 = build_function_type_list (V16QI_type_node,
8739 V16QI_type_node, V16QI_type_node,
b9e4e5d1
ZL
8740 integer_type_node, NULL_TREE);
8741 tree v8hi_ftype_v8hi_v8hi_int
b4de2f7d
AH
8742 = build_function_type_list (V8HI_type_node,
8743 V8HI_type_node, V8HI_type_node,
b9e4e5d1
ZL
8744 integer_type_node, NULL_TREE);
8745 tree v4si_ftype_v4si_v4si_int
b4de2f7d
AH
8746 = build_function_type_list (V4SI_type_node,
8747 V4SI_type_node, V4SI_type_node,
b9e4e5d1
ZL
8748 integer_type_node, NULL_TREE);
8749 tree v4sf_ftype_v4sf_v4sf_int
b4de2f7d
AH
8750 = build_function_type_list (V4SF_type_node,
8751 V4SF_type_node, V4SF_type_node,
b9e4e5d1 8752 integer_type_node, NULL_TREE);
0ac081f6 8753 tree v4sf_ftype_v4sf_v4sf
b4de2f7d
AH
8754 = build_function_type_list (V4SF_type_node,
8755 V4SF_type_node, V4SF_type_node, NULL_TREE);
58646b77
PB
8756 tree opaque_ftype_opaque_opaque_opaque
8757 = build_function_type_list (opaque_V4SI_type_node,
8758 opaque_V4SI_type_node, opaque_V4SI_type_node,
8759 opaque_V4SI_type_node, NULL_TREE);
617e0e1d 8760 tree v4sf_ftype_v4sf_v4sf_v4si
b4de2f7d
AH
8761 = build_function_type_list (V4SF_type_node,
8762 V4SF_type_node, V4SF_type_node,
8763 V4SI_type_node, NULL_TREE);
2212663f 8764 tree v4sf_ftype_v4sf_v4sf_v4sf
b4de2f7d
AH
8765 = build_function_type_list (V4SF_type_node,
8766 V4SF_type_node, V4SF_type_node,
8767 V4SF_type_node, NULL_TREE);
f676971a 8768 tree v4si_ftype_v4si_v4si_v4si
b4de2f7d
AH
8769 = build_function_type_list (V4SI_type_node,
8770 V4SI_type_node, V4SI_type_node,
8771 V4SI_type_node, NULL_TREE);
0ac081f6 8772 tree v8hi_ftype_v8hi_v8hi
b4de2f7d
AH
8773 = build_function_type_list (V8HI_type_node,
8774 V8HI_type_node, V8HI_type_node, NULL_TREE);
2212663f 8775 tree v8hi_ftype_v8hi_v8hi_v8hi
b4de2f7d
AH
8776 = build_function_type_list (V8HI_type_node,
8777 V8HI_type_node, V8HI_type_node,
8778 V8HI_type_node, NULL_TREE);
c4ad648e 8779 tree v4si_ftype_v8hi_v8hi_v4si
b4de2f7d
AH
8780 = build_function_type_list (V4SI_type_node,
8781 V8HI_type_node, V8HI_type_node,
8782 V4SI_type_node, NULL_TREE);
c4ad648e 8783 tree v4si_ftype_v16qi_v16qi_v4si
b4de2f7d
AH
8784 = build_function_type_list (V4SI_type_node,
8785 V16QI_type_node, V16QI_type_node,
8786 V4SI_type_node, NULL_TREE);
0ac081f6 8787 tree v16qi_ftype_v16qi_v16qi
b4de2f7d
AH
8788 = build_function_type_list (V16QI_type_node,
8789 V16QI_type_node, V16QI_type_node, NULL_TREE);
0ac081f6 8790 tree v4si_ftype_v4sf_v4sf
b4de2f7d
AH
8791 = build_function_type_list (V4SI_type_node,
8792 V4SF_type_node, V4SF_type_node, NULL_TREE);
0ac081f6 8793 tree v8hi_ftype_v16qi_v16qi
b4de2f7d
AH
8794 = build_function_type_list (V8HI_type_node,
8795 V16QI_type_node, V16QI_type_node, NULL_TREE);
0ac081f6 8796 tree v4si_ftype_v8hi_v8hi
b4de2f7d
AH
8797 = build_function_type_list (V4SI_type_node,
8798 V8HI_type_node, V8HI_type_node, NULL_TREE);
0ac081f6 8799 tree v8hi_ftype_v4si_v4si
b4de2f7d
AH
8800 = build_function_type_list (V8HI_type_node,
8801 V4SI_type_node, V4SI_type_node, NULL_TREE);
0ac081f6 8802 tree v16qi_ftype_v8hi_v8hi
b4de2f7d
AH
8803 = build_function_type_list (V16QI_type_node,
8804 V8HI_type_node, V8HI_type_node, NULL_TREE);
0ac081f6 8805 tree v4si_ftype_v16qi_v4si
b4de2f7d
AH
8806 = build_function_type_list (V4SI_type_node,
8807 V16QI_type_node, V4SI_type_node, NULL_TREE);
fa066a23 8808 tree v4si_ftype_v16qi_v16qi
b4de2f7d
AH
8809 = build_function_type_list (V4SI_type_node,
8810 V16QI_type_node, V16QI_type_node, NULL_TREE);
0ac081f6 8811 tree v4si_ftype_v8hi_v4si
b4de2f7d
AH
8812 = build_function_type_list (V4SI_type_node,
8813 V8HI_type_node, V4SI_type_node, NULL_TREE);
a3170dc6
AH
8814 tree v4si_ftype_v8hi
8815 = build_function_type_list (V4SI_type_node, V8HI_type_node, NULL_TREE);
8816 tree int_ftype_v4si_v4si
8817 = build_function_type_list (integer_type_node,
8818 V4SI_type_node, V4SI_type_node, NULL_TREE);
8819 tree int_ftype_v4sf_v4sf
8820 = build_function_type_list (integer_type_node,
8821 V4SF_type_node, V4SF_type_node, NULL_TREE);
8822 tree int_ftype_v16qi_v16qi
8823 = build_function_type_list (integer_type_node,
8824 V16QI_type_node, V16QI_type_node, NULL_TREE);
0ac081f6 8825 tree int_ftype_v8hi_v8hi
b4de2f7d
AH
8826 = build_function_type_list (integer_type_node,
8827 V8HI_type_node, V8HI_type_node, NULL_TREE);
0ac081f6 8828
6f317ef3 8829 /* Add the simple ternary operators. */
2212663f 8830 d = (struct builtin_description *) bdesc_3arg;
ca7558fc 8831 for (i = 0; i < ARRAY_SIZE (bdesc_3arg); i++, d++)
2212663f 8832 {
2212663f
DB
8833 enum machine_mode mode0, mode1, mode2, mode3;
8834 tree type;
58646b77
PB
8835 bool is_overloaded = d->code >= ALTIVEC_BUILTIN_OVERLOADED_FIRST
8836 && d->code <= ALTIVEC_BUILTIN_OVERLOADED_LAST;
2212663f 8837
58646b77
PB
8838 if (is_overloaded)
8839 {
8840 mode0 = VOIDmode;
8841 mode1 = VOIDmode;
8842 mode2 = VOIDmode;
8843 mode3 = VOIDmode;
8844 }
8845 else
8846 {
8847 if (d->name == 0 || d->icode == CODE_FOR_nothing)
8848 continue;
f676971a 8849
58646b77
PB
8850 mode0 = insn_data[d->icode].operand[0].mode;
8851 mode1 = insn_data[d->icode].operand[1].mode;
8852 mode2 = insn_data[d->icode].operand[2].mode;
8853 mode3 = insn_data[d->icode].operand[3].mode;
8854 }
bb8df8a6 8855
2212663f
DB
8856 /* When all four are of the same mode. */
8857 if (mode0 == mode1 && mode1 == mode2 && mode2 == mode3)
8858 {
8859 switch (mode0)
8860 {
58646b77
PB
8861 case VOIDmode:
8862 type = opaque_ftype_opaque_opaque_opaque;
8863 break;
617e0e1d
DB
8864 case V4SImode:
8865 type = v4si_ftype_v4si_v4si_v4si;
8866 break;
2212663f
DB
8867 case V4SFmode:
8868 type = v4sf_ftype_v4sf_v4sf_v4sf;
8869 break;
8870 case V8HImode:
8871 type = v8hi_ftype_v8hi_v8hi_v8hi;
f676971a 8872 break;
2212663f
DB
8873 case V16QImode:
8874 type = v16qi_ftype_v16qi_v16qi_v16qi;
f676971a 8875 break;
2212663f 8876 default:
37409796 8877 gcc_unreachable ();
2212663f
DB
8878 }
8879 }
8880 else if (mode0 == mode1 && mode1 == mode2 && mode3 == V16QImode)
c4ad648e 8881 {
2212663f
DB
8882 switch (mode0)
8883 {
8884 case V4SImode:
8885 type = v4si_ftype_v4si_v4si_v16qi;
8886 break;
8887 case V4SFmode:
8888 type = v4sf_ftype_v4sf_v4sf_v16qi;
8889 break;
8890 case V8HImode:
8891 type = v8hi_ftype_v8hi_v8hi_v16qi;
f676971a 8892 break;
2212663f
DB
8893 case V16QImode:
8894 type = v16qi_ftype_v16qi_v16qi_v16qi;
f676971a 8895 break;
2212663f 8896 default:
37409796 8897 gcc_unreachable ();
2212663f
DB
8898 }
8899 }
f676971a 8900 else if (mode0 == V4SImode && mode1 == V16QImode && mode2 == V16QImode
2212663f 8901 && mode3 == V4SImode)
24408032 8902 type = v4si_ftype_v16qi_v16qi_v4si;
f676971a 8903 else if (mode0 == V4SImode && mode1 == V8HImode && mode2 == V8HImode
2212663f 8904 && mode3 == V4SImode)
24408032 8905 type = v4si_ftype_v8hi_v8hi_v4si;
f676971a 8906 else if (mode0 == V4SFmode && mode1 == V4SFmode && mode2 == V4SFmode
617e0e1d 8907 && mode3 == V4SImode)
24408032
AH
8908 type = v4sf_ftype_v4sf_v4sf_v4si;
8909
8910 /* vchar, vchar, vchar, 4 bit literal. */
8911 else if (mode0 == V16QImode && mode1 == mode0 && mode2 == mode0
8912 && mode3 == QImode)
b9e4e5d1 8913 type = v16qi_ftype_v16qi_v16qi_int;
24408032
AH
8914
8915 /* vshort, vshort, vshort, 4 bit literal. */
8916 else if (mode0 == V8HImode && mode1 == mode0 && mode2 == mode0
8917 && mode3 == QImode)
b9e4e5d1 8918 type = v8hi_ftype_v8hi_v8hi_int;
24408032
AH
8919
8920 /* vint, vint, vint, 4 bit literal. */
8921 else if (mode0 == V4SImode && mode1 == mode0 && mode2 == mode0
8922 && mode3 == QImode)
b9e4e5d1 8923 type = v4si_ftype_v4si_v4si_int;
24408032
AH
8924
8925 /* vfloat, vfloat, vfloat, 4 bit literal. */
8926 else if (mode0 == V4SFmode && mode1 == mode0 && mode2 == mode0
8927 && mode3 == QImode)
b9e4e5d1 8928 type = v4sf_ftype_v4sf_v4sf_int;
24408032 8929
2212663f 8930 else
37409796 8931 gcc_unreachable ();
2212663f
DB
8932
8933 def_builtin (d->mask, d->name, type, d->code);
8934 }
8935
0ac081f6 8936 /* Add the simple binary operators. */
00b960c7 8937 d = (struct builtin_description *) bdesc_2arg;
ca7558fc 8938 for (i = 0; i < ARRAY_SIZE (bdesc_2arg); i++, d++)
0ac081f6
AH
8939 {
8940 enum machine_mode mode0, mode1, mode2;
8941 tree type;
58646b77
PB
8942 bool is_overloaded = d->code >= ALTIVEC_BUILTIN_OVERLOADED_FIRST
8943 && d->code <= ALTIVEC_BUILTIN_OVERLOADED_LAST;
0ac081f6 8944
58646b77
PB
8945 if (is_overloaded)
8946 {
8947 mode0 = VOIDmode;
8948 mode1 = VOIDmode;
8949 mode2 = VOIDmode;
8950 }
8951 else
bb8df8a6 8952 {
58646b77
PB
8953 if (d->name == 0 || d->icode == CODE_FOR_nothing)
8954 continue;
f676971a 8955
58646b77
PB
8956 mode0 = insn_data[d->icode].operand[0].mode;
8957 mode1 = insn_data[d->icode].operand[1].mode;
8958 mode2 = insn_data[d->icode].operand[2].mode;
8959 }
0ac081f6
AH
8960
8961 /* When all three operands are of the same mode. */
8962 if (mode0 == mode1 && mode1 == mode2)
8963 {
8964 switch (mode0)
8965 {
58646b77
PB
8966 case VOIDmode:
8967 type = opaque_ftype_opaque_opaque;
8968 break;
0ac081f6
AH
8969 case V4SFmode:
8970 type = v4sf_ftype_v4sf_v4sf;
8971 break;
8972 case V4SImode:
8973 type = v4si_ftype_v4si_v4si;
8974 break;
8975 case V16QImode:
8976 type = v16qi_ftype_v16qi_v16qi;
8977 break;
8978 case V8HImode:
8979 type = v8hi_ftype_v8hi_v8hi;
8980 break;
a3170dc6
AH
8981 case V2SImode:
8982 type = v2si_ftype_v2si_v2si;
8983 break;
8984 case V2SFmode:
8985 type = v2sf_ftype_v2sf_v2sf;
8986 break;
8987 case SImode:
8988 type = int_ftype_int_int;
8989 break;
0ac081f6 8990 default:
37409796 8991 gcc_unreachable ();
0ac081f6
AH
8992 }
8993 }
8994
8995 /* A few other combos we really don't want to do manually. */
8996
8997 /* vint, vfloat, vfloat. */
8998 else if (mode0 == V4SImode && mode1 == V4SFmode && mode2 == V4SFmode)
8999 type = v4si_ftype_v4sf_v4sf;
9000
9001 /* vshort, vchar, vchar. */
9002 else if (mode0 == V8HImode && mode1 == V16QImode && mode2 == V16QImode)
9003 type = v8hi_ftype_v16qi_v16qi;
9004
9005 /* vint, vshort, vshort. */
9006 else if (mode0 == V4SImode && mode1 == V8HImode && mode2 == V8HImode)
9007 type = v4si_ftype_v8hi_v8hi;
9008
9009 /* vshort, vint, vint. */
9010 else if (mode0 == V8HImode && mode1 == V4SImode && mode2 == V4SImode)
9011 type = v8hi_ftype_v4si_v4si;
9012
9013 /* vchar, vshort, vshort. */
9014 else if (mode0 == V16QImode && mode1 == V8HImode && mode2 == V8HImode)
9015 type = v16qi_ftype_v8hi_v8hi;
9016
9017 /* vint, vchar, vint. */
9018 else if (mode0 == V4SImode && mode1 == V16QImode && mode2 == V4SImode)
9019 type = v4si_ftype_v16qi_v4si;
9020
fa066a23
AH
9021 /* vint, vchar, vchar. */
9022 else if (mode0 == V4SImode && mode1 == V16QImode && mode2 == V16QImode)
9023 type = v4si_ftype_v16qi_v16qi;
9024
0ac081f6
AH
9025 /* vint, vshort, vint. */
9026 else if (mode0 == V4SImode && mode1 == V8HImode && mode2 == V4SImode)
9027 type = v4si_ftype_v8hi_v4si;
f676971a 9028
2212663f
DB
9029 /* vint, vint, 5 bit literal. */
9030 else if (mode0 == V4SImode && mode1 == V4SImode && mode2 == QImode)
b9e4e5d1 9031 type = v4si_ftype_v4si_int;
f676971a 9032
2212663f
DB
9033 /* vshort, vshort, 5 bit literal. */
9034 else if (mode0 == V8HImode && mode1 == V8HImode && mode2 == QImode)
b9e4e5d1 9035 type = v8hi_ftype_v8hi_int;
f676971a 9036
2212663f
DB
9037 /* vchar, vchar, 5 bit literal. */
9038 else if (mode0 == V16QImode && mode1 == V16QImode && mode2 == QImode)
b9e4e5d1 9039 type = v16qi_ftype_v16qi_int;
0ac081f6 9040
617e0e1d
DB
9041 /* vfloat, vint, 5 bit literal. */
9042 else if (mode0 == V4SFmode && mode1 == V4SImode && mode2 == QImode)
b9e4e5d1 9043 type = v4sf_ftype_v4si_int;
f676971a 9044
617e0e1d
DB
9045 /* vint, vfloat, 5 bit literal. */
9046 else if (mode0 == V4SImode && mode1 == V4SFmode && mode2 == QImode)
b9e4e5d1 9047 type = v4si_ftype_v4sf_int;
617e0e1d 9048
a3170dc6
AH
9049 else if (mode0 == V2SImode && mode1 == SImode && mode2 == SImode)
9050 type = v2si_ftype_int_int;
9051
9052 else if (mode0 == V2SImode && mode1 == V2SImode && mode2 == QImode)
9053 type = v2si_ftype_v2si_char;
9054
9055 else if (mode0 == V2SImode && mode1 == SImode && mode2 == QImode)
9056 type = v2si_ftype_int_char;
9057
37409796 9058 else
0ac081f6 9059 {
37409796
NS
9060 /* int, x, x. */
9061 gcc_assert (mode0 == SImode);
0ac081f6
AH
9062 switch (mode1)
9063 {
9064 case V4SImode:
9065 type = int_ftype_v4si_v4si;
9066 break;
9067 case V4SFmode:
9068 type = int_ftype_v4sf_v4sf;
9069 break;
9070 case V16QImode:
9071 type = int_ftype_v16qi_v16qi;
9072 break;
9073 case V8HImode:
9074 type = int_ftype_v8hi_v8hi;
9075 break;
9076 default:
37409796 9077 gcc_unreachable ();
0ac081f6
AH
9078 }
9079 }
9080
2212663f
DB
9081 def_builtin (d->mask, d->name, type, d->code);
9082 }
24408032 9083
2212663f
DB
9084 /* Add the simple unary operators. */
9085 d = (struct builtin_description *) bdesc_1arg;
ca7558fc 9086 for (i = 0; i < ARRAY_SIZE (bdesc_1arg); i++, d++)
2212663f
DB
9087 {
9088 enum machine_mode mode0, mode1;
9089 tree type;
58646b77
PB
9090 bool is_overloaded = d->code >= ALTIVEC_BUILTIN_OVERLOADED_FIRST
9091 && d->code <= ALTIVEC_BUILTIN_OVERLOADED_LAST;
9092
9093 if (is_overloaded)
9094 {
9095 mode0 = VOIDmode;
9096 mode1 = VOIDmode;
9097 }
9098 else
9099 {
9100 if (d->name == 0 || d->icode == CODE_FOR_nothing)
9101 continue;
bb8df8a6 9102
58646b77
PB
9103 mode0 = insn_data[d->icode].operand[0].mode;
9104 mode1 = insn_data[d->icode].operand[1].mode;
9105 }
2212663f
DB
9106
9107 if (mode0 == V4SImode && mode1 == QImode)
c4ad648e 9108 type = v4si_ftype_int;
2212663f 9109 else if (mode0 == V8HImode && mode1 == QImode)
c4ad648e 9110 type = v8hi_ftype_int;
2212663f 9111 else if (mode0 == V16QImode && mode1 == QImode)
c4ad648e 9112 type = v16qi_ftype_int;
58646b77
PB
9113 else if (mode0 == VOIDmode && mode1 == VOIDmode)
9114 type = opaque_ftype_opaque;
617e0e1d
DB
9115 else if (mode0 == V4SFmode && mode1 == V4SFmode)
9116 type = v4sf_ftype_v4sf;
20e26713
AH
9117 else if (mode0 == V8HImode && mode1 == V16QImode)
9118 type = v8hi_ftype_v16qi;
9119 else if (mode0 == V4SImode && mode1 == V8HImode)
9120 type = v4si_ftype_v8hi;
a3170dc6
AH
9121 else if (mode0 == V2SImode && mode1 == V2SImode)
9122 type = v2si_ftype_v2si;
9123 else if (mode0 == V2SFmode && mode1 == V2SFmode)
9124 type = v2sf_ftype_v2sf;
9125 else if (mode0 == V2SFmode && mode1 == V2SImode)
9126 type = v2sf_ftype_v2si;
9127 else if (mode0 == V2SImode && mode1 == V2SFmode)
9128 type = v2si_ftype_v2sf;
9129 else if (mode0 == V2SImode && mode1 == QImode)
9130 type = v2si_ftype_char;
2212663f 9131 else
37409796 9132 gcc_unreachable ();
2212663f 9133
0ac081f6
AH
9134 def_builtin (d->mask, d->name, type, d->code);
9135 }
9136}
9137
c15c90bb
ZW
9138static void
9139rs6000_init_libfuncs (void)
9140{
9141 if (!TARGET_HARD_FLOAT)
9142 return;
9143
602ea4d3
JJ
9144 if (DEFAULT_ABI != ABI_V4 && TARGET_XCOFF
9145 && !TARGET_POWER2 && !TARGET_POWERPC)
c15c90bb 9146 {
602ea4d3
JJ
9147 /* AIX library routines for float->int conversion. */
9148 set_conv_libfunc (sfix_optab, SImode, DFmode, "__itrunc");
9149 set_conv_libfunc (ufix_optab, SImode, DFmode, "__uitrunc");
9150 set_conv_libfunc (sfix_optab, SImode, TFmode, "_qitrunc");
9151 set_conv_libfunc (ufix_optab, SImode, TFmode, "_quitrunc");
9152 }
c15c90bb 9153
602ea4d3 9154 if (!TARGET_IEEEQUAD)
98c41d98 9155 /* AIX/Darwin/64-bit Linux quad floating point routines. */
602ea4d3
JJ
9156 if (!TARGET_XL_COMPAT)
9157 {
9158 set_optab_libfunc (add_optab, TFmode, "__gcc_qadd");
9159 set_optab_libfunc (sub_optab, TFmode, "__gcc_qsub");
9160 set_optab_libfunc (smul_optab, TFmode, "__gcc_qmul");
9161 set_optab_libfunc (sdiv_optab, TFmode, "__gcc_qdiv");
9162 }
9163 else
9164 {
9165 set_optab_libfunc (add_optab, TFmode, "_xlqadd");
9166 set_optab_libfunc (sub_optab, TFmode, "_xlqsub");
9167 set_optab_libfunc (smul_optab, TFmode, "_xlqmul");
9168 set_optab_libfunc (sdiv_optab, TFmode, "_xlqdiv");
9169 }
c9034561 9170 else
c15c90bb 9171 {
c9034561 9172 /* 32-bit SVR4 quad floating point routines. */
c15c90bb
ZW
9173
9174 set_optab_libfunc (add_optab, TFmode, "_q_add");
9175 set_optab_libfunc (sub_optab, TFmode, "_q_sub");
9176 set_optab_libfunc (neg_optab, TFmode, "_q_neg");
9177 set_optab_libfunc (smul_optab, TFmode, "_q_mul");
9178 set_optab_libfunc (sdiv_optab, TFmode, "_q_div");
9179 if (TARGET_PPC_GPOPT || TARGET_POWER2)
9180 set_optab_libfunc (sqrt_optab, TFmode, "_q_sqrt");
9181
c9034561
ZW
9182 set_optab_libfunc (eq_optab, TFmode, "_q_feq");
9183 set_optab_libfunc (ne_optab, TFmode, "_q_fne");
9184 set_optab_libfunc (gt_optab, TFmode, "_q_fgt");
9185 set_optab_libfunc (ge_optab, TFmode, "_q_fge");
9186 set_optab_libfunc (lt_optab, TFmode, "_q_flt");
9187 set_optab_libfunc (le_optab, TFmode, "_q_fle");
9188
85363ca0
ZW
9189 set_conv_libfunc (sext_optab, TFmode, SFmode, "_q_stoq");
9190 set_conv_libfunc (sext_optab, TFmode, DFmode, "_q_dtoq");
9191 set_conv_libfunc (trunc_optab, SFmode, TFmode, "_q_qtos");
9192 set_conv_libfunc (trunc_optab, DFmode, TFmode, "_q_qtod");
9193 set_conv_libfunc (sfix_optab, SImode, TFmode, "_q_qtoi");
9194 set_conv_libfunc (ufix_optab, SImode, TFmode, "_q_qtou");
9195 set_conv_libfunc (sfloat_optab, TFmode, SImode, "_q_itoq");
57904aa7 9196 set_conv_libfunc (ufloat_optab, TFmode, SImode, "_q_utoq");
c15c90bb
ZW
9197 }
9198}
fba73eb1
DE
9199
9200\f
9201/* Expand a block clear operation, and return 1 if successful. Return 0
9202 if we should let the compiler generate normal code.
9203
9204 operands[0] is the destination
9205 operands[1] is the length
57e84f18 9206 operands[3] is the alignment */
fba73eb1
DE
9207
9208int
9209expand_block_clear (rtx operands[])
9210{
9211 rtx orig_dest = operands[0];
9212 rtx bytes_rtx = operands[1];
57e84f18 9213 rtx align_rtx = operands[3];
5514620a
GK
9214 bool constp = (GET_CODE (bytes_rtx) == CONST_INT);
9215 HOST_WIDE_INT align;
9216 HOST_WIDE_INT bytes;
fba73eb1
DE
9217 int offset;
9218 int clear_bytes;
5514620a 9219 int clear_step;
fba73eb1
DE
9220
9221 /* If this is not a fixed size move, just call memcpy */
9222 if (! constp)
9223 return 0;
9224
37409796
NS
9225 /* This must be a fixed size alignment */
9226 gcc_assert (GET_CODE (align_rtx) == CONST_INT);
fba73eb1
DE
9227 align = INTVAL (align_rtx) * BITS_PER_UNIT;
9228
9229 /* Anything to clear? */
9230 bytes = INTVAL (bytes_rtx);
9231 if (bytes <= 0)
9232 return 1;
9233
5514620a
GK
9234 /* Use the builtin memset after a point, to avoid huge code bloat.
9235 When optimize_size, avoid any significant code bloat; calling
9236 memset is about 4 instructions, so allow for one instruction to
9237 load zero and three to do clearing. */
9238 if (TARGET_ALTIVEC && align >= 128)
9239 clear_step = 16;
9240 else if (TARGET_POWERPC64 && align >= 32)
9241 clear_step = 8;
9242 else
9243 clear_step = 4;
fba73eb1 9244
5514620a
GK
9245 if (optimize_size && bytes > 3 * clear_step)
9246 return 0;
9247 if (! optimize_size && bytes > 8 * clear_step)
fba73eb1
DE
9248 return 0;
9249
9250 for (offset = 0; bytes > 0; offset += clear_bytes, bytes -= clear_bytes)
9251 {
fba73eb1
DE
9252 enum machine_mode mode = BLKmode;
9253 rtx dest;
f676971a 9254
5514620a
GK
9255 if (bytes >= 16 && TARGET_ALTIVEC && align >= 128)
9256 {
9257 clear_bytes = 16;
9258 mode = V4SImode;
9259 }
9260 else if (bytes >= 8 && TARGET_POWERPC64
9261 /* 64-bit loads and stores require word-aligned
9262 displacements. */
9263 && (align >= 64 || (!STRICT_ALIGNMENT && align >= 32)))
fba73eb1
DE
9264 {
9265 clear_bytes = 8;
9266 mode = DImode;
fba73eb1 9267 }
5514620a 9268 else if (bytes >= 4 && (align >= 32 || !STRICT_ALIGNMENT))
fba73eb1
DE
9269 { /* move 4 bytes */
9270 clear_bytes = 4;
9271 mode = SImode;
fba73eb1 9272 }
ec53fc93 9273 else if (bytes >= 2 && (align >= 16 || !STRICT_ALIGNMENT))
fba73eb1
DE
9274 { /* move 2 bytes */
9275 clear_bytes = 2;
9276 mode = HImode;
fba73eb1
DE
9277 }
9278 else /* move 1 byte at a time */
9279 {
9280 clear_bytes = 1;
9281 mode = QImode;
fba73eb1 9282 }
f676971a 9283
fba73eb1 9284 dest = adjust_address (orig_dest, mode, offset);
f676971a 9285
5514620a 9286 emit_move_insn (dest, CONST0_RTX (mode));
fba73eb1
DE
9287 }
9288
9289 return 1;
9290}
9291
35aff10b 9292\f
7e69e155
MM
9293/* Expand a block move operation, and return 1 if successful. Return 0
9294 if we should let the compiler generate normal code.
9295
9296 operands[0] is the destination
9297 operands[1] is the source
9298 operands[2] is the length
9299 operands[3] is the alignment */
9300
3933e0e1
MM
9301#define MAX_MOVE_REG 4
9302
7e69e155 9303int
a2369ed3 9304expand_block_move (rtx operands[])
7e69e155 9305{
b6c9286a
MM
9306 rtx orig_dest = operands[0];
9307 rtx orig_src = operands[1];
7e69e155 9308 rtx bytes_rtx = operands[2];
7e69e155 9309 rtx align_rtx = operands[3];
3933e0e1 9310 int constp = (GET_CODE (bytes_rtx) == CONST_INT);
5ee95df6 9311 int align;
3933e0e1
MM
9312 int bytes;
9313 int offset;
7e69e155 9314 int move_bytes;
cabfd258
GK
9315 rtx stores[MAX_MOVE_REG];
9316 int num_reg = 0;
7e69e155 9317
3933e0e1 9318 /* If this is not a fixed size move, just call memcpy */
cc0d9ba8 9319 if (! constp)
3933e0e1
MM
9320 return 0;
9321
37409796
NS
9322 /* This must be a fixed size alignment */
9323 gcc_assert (GET_CODE (align_rtx) == CONST_INT);
fba73eb1 9324 align = INTVAL (align_rtx) * BITS_PER_UNIT;
5ee95df6 9325
7e69e155 9326 /* Anything to move? */
3933e0e1
MM
9327 bytes = INTVAL (bytes_rtx);
9328 if (bytes <= 0)
7e69e155
MM
9329 return 1;
9330
ea9982a8 9331 /* store_one_arg depends on expand_block_move to handle at least the size of
f676971a 9332 reg_parm_stack_space. */
ea9982a8 9333 if (bytes > (TARGET_POWERPC64 ? 64 : 32))
7e69e155
MM
9334 return 0;
9335
cabfd258 9336 for (offset = 0; bytes > 0; offset += move_bytes, bytes -= move_bytes)
7e69e155 9337 {
cabfd258 9338 union {
70128ad9 9339 rtx (*movmemsi) (rtx, rtx, rtx, rtx);
a2369ed3 9340 rtx (*mov) (rtx, rtx);
cabfd258
GK
9341 } gen_func;
9342 enum machine_mode mode = BLKmode;
9343 rtx src, dest;
f676971a 9344
5514620a
GK
9345 /* Altivec first, since it will be faster than a string move
9346 when it applies, and usually not significantly larger. */
9347 if (TARGET_ALTIVEC && bytes >= 16 && align >= 128)
9348 {
9349 move_bytes = 16;
9350 mode = V4SImode;
9351 gen_func.mov = gen_movv4si;
9352 }
9353 else if (TARGET_STRING
cabfd258
GK
9354 && bytes > 24 /* move up to 32 bytes at a time */
9355 && ! fixed_regs[5]
9356 && ! fixed_regs[6]
9357 && ! fixed_regs[7]
9358 && ! fixed_regs[8]
9359 && ! fixed_regs[9]
9360 && ! fixed_regs[10]
9361 && ! fixed_regs[11]
9362 && ! fixed_regs[12])
7e69e155 9363 {
cabfd258 9364 move_bytes = (bytes > 32) ? 32 : bytes;
70128ad9 9365 gen_func.movmemsi = gen_movmemsi_8reg;
cabfd258
GK
9366 }
9367 else if (TARGET_STRING
9368 && bytes > 16 /* move up to 24 bytes at a time */
9369 && ! fixed_regs[5]
9370 && ! fixed_regs[6]
9371 && ! fixed_regs[7]
9372 && ! fixed_regs[8]
9373 && ! fixed_regs[9]
9374 && ! fixed_regs[10])
9375 {
9376 move_bytes = (bytes > 24) ? 24 : bytes;
70128ad9 9377 gen_func.movmemsi = gen_movmemsi_6reg;
cabfd258
GK
9378 }
9379 else if (TARGET_STRING
9380 && bytes > 8 /* move up to 16 bytes at a time */
9381 && ! fixed_regs[5]
9382 && ! fixed_regs[6]
9383 && ! fixed_regs[7]
9384 && ! fixed_regs[8])
9385 {
9386 move_bytes = (bytes > 16) ? 16 : bytes;
70128ad9 9387 gen_func.movmemsi = gen_movmemsi_4reg;
cabfd258
GK
9388 }
9389 else if (bytes >= 8 && TARGET_POWERPC64
9390 /* 64-bit loads and stores require word-aligned
9391 displacements. */
fba73eb1 9392 && (align >= 64 || (!STRICT_ALIGNMENT && align >= 32)))
cabfd258
GK
9393 {
9394 move_bytes = 8;
9395 mode = DImode;
9396 gen_func.mov = gen_movdi;
9397 }
9398 else if (TARGET_STRING && bytes > 4 && !TARGET_POWERPC64)
9399 { /* move up to 8 bytes at a time */
9400 move_bytes = (bytes > 8) ? 8 : bytes;
70128ad9 9401 gen_func.movmemsi = gen_movmemsi_2reg;
cabfd258 9402 }
cd7d9ca4 9403 else if (bytes >= 4 && (align >= 32 || !STRICT_ALIGNMENT))
cabfd258
GK
9404 { /* move 4 bytes */
9405 move_bytes = 4;
9406 mode = SImode;
9407 gen_func.mov = gen_movsi;
9408 }
ec53fc93 9409 else if (bytes >= 2 && (align >= 16 || !STRICT_ALIGNMENT))
cabfd258
GK
9410 { /* move 2 bytes */
9411 move_bytes = 2;
9412 mode = HImode;
9413 gen_func.mov = gen_movhi;
9414 }
9415 else if (TARGET_STRING && bytes > 1)
9416 { /* move up to 4 bytes at a time */
9417 move_bytes = (bytes > 4) ? 4 : bytes;
70128ad9 9418 gen_func.movmemsi = gen_movmemsi_1reg;
cabfd258
GK
9419 }
9420 else /* move 1 byte at a time */
9421 {
9422 move_bytes = 1;
9423 mode = QImode;
9424 gen_func.mov = gen_movqi;
9425 }
f676971a 9426
cabfd258
GK
9427 src = adjust_address (orig_src, mode, offset);
9428 dest = adjust_address (orig_dest, mode, offset);
f676971a
EC
9429
9430 if (mode != BLKmode)
cabfd258
GK
9431 {
9432 rtx tmp_reg = gen_reg_rtx (mode);
f676971a 9433
cabfd258
GK
9434 emit_insn ((*gen_func.mov) (tmp_reg, src));
9435 stores[num_reg++] = (*gen_func.mov) (dest, tmp_reg);
4c64a852 9436 }
3933e0e1 9437
cabfd258
GK
9438 if (mode == BLKmode || num_reg >= MAX_MOVE_REG || bytes == move_bytes)
9439 {
9440 int i;
9441 for (i = 0; i < num_reg; i++)
9442 emit_insn (stores[i]);
9443 num_reg = 0;
9444 }
35aff10b 9445
cabfd258 9446 if (mode == BLKmode)
7e69e155 9447 {
70128ad9 9448 /* Move the address into scratch registers. The movmemsi
cabfd258
GK
9449 patterns require zero offset. */
9450 if (!REG_P (XEXP (src, 0)))
b6c9286a 9451 {
cabfd258
GK
9452 rtx src_reg = copy_addr_to_reg (XEXP (src, 0));
9453 src = replace_equiv_address (src, src_reg);
b6c9286a 9454 }
cabfd258 9455 set_mem_size (src, GEN_INT (move_bytes));
f676971a 9456
cabfd258 9457 if (!REG_P (XEXP (dest, 0)))
3933e0e1 9458 {
cabfd258
GK
9459 rtx dest_reg = copy_addr_to_reg (XEXP (dest, 0));
9460 dest = replace_equiv_address (dest, dest_reg);
7e69e155 9461 }
cabfd258 9462 set_mem_size (dest, GEN_INT (move_bytes));
f676971a 9463
70128ad9 9464 emit_insn ((*gen_func.movmemsi) (dest, src,
cabfd258
GK
9465 GEN_INT (move_bytes & 31),
9466 align_rtx));
7e69e155 9467 }
7e69e155
MM
9468 }
9469
9470 return 1;
9471}
9472
d62294f5 9473\f
9caa3eb2
DE
9474/* Return a string to perform a load_multiple operation.
9475 operands[0] is the vector.
9476 operands[1] is the source address.
9477 operands[2] is the first destination register. */
9478
9479const char *
a2369ed3 9480rs6000_output_load_multiple (rtx operands[3])
9caa3eb2
DE
9481{
9482 /* We have to handle the case where the pseudo used to contain the address
9483 is assigned to one of the output registers. */
9484 int i, j;
9485 int words = XVECLEN (operands[0], 0);
9486 rtx xop[10];
9487
9488 if (XVECLEN (operands[0], 0) == 1)
9489 return "{l|lwz} %2,0(%1)";
9490
9491 for (i = 0; i < words; i++)
9492 if (refers_to_regno_p (REGNO (operands[2]) + i,
9493 REGNO (operands[2]) + i + 1, operands[1], 0))
9494 {
9495 if (i == words-1)
9496 {
9497 xop[0] = GEN_INT (4 * (words-1));
9498 xop[1] = operands[1];
9499 xop[2] = operands[2];
9500 output_asm_insn ("{lsi|lswi} %2,%1,%0\n\t{l|lwz} %1,%0(%1)", xop);
9501 return "";
9502 }
9503 else if (i == 0)
9504 {
9505 xop[0] = GEN_INT (4 * (words-1));
9506 xop[1] = operands[1];
9507 xop[2] = gen_rtx_REG (SImode, REGNO (operands[2]) + 1);
9508 output_asm_insn ("{cal %1,4(%1)|addi %1,%1,4}\n\t{lsi|lswi} %2,%1,%0\n\t{l|lwz} %1,-4(%1)", xop);
9509 return "";
9510 }
9511 else
9512 {
9513 for (j = 0; j < words; j++)
9514 if (j != i)
9515 {
9516 xop[0] = GEN_INT (j * 4);
9517 xop[1] = operands[1];
9518 xop[2] = gen_rtx_REG (SImode, REGNO (operands[2]) + j);
9519 output_asm_insn ("{l|lwz} %2,%0(%1)", xop);
9520 }
9521 xop[0] = GEN_INT (i * 4);
9522 xop[1] = operands[1];
9523 output_asm_insn ("{l|lwz} %1,%0(%1)", xop);
9524 return "";
9525 }
9526 }
9527
9528 return "{lsi|lswi} %2,%1,%N0";
9529}
9530
9878760c 9531\f
a4f6c312
SS
9532/* A validation routine: say whether CODE, a condition code, and MODE
9533 match. The other alternatives either don't make sense or should
9534 never be generated. */
39a10a29 9535
48d72335 9536void
a2369ed3 9537validate_condition_mode (enum rtx_code code, enum machine_mode mode)
39a10a29 9538{
37409796
NS
9539 gcc_assert ((GET_RTX_CLASS (code) == RTX_COMPARE
9540 || GET_RTX_CLASS (code) == RTX_COMM_COMPARE)
9541 && GET_MODE_CLASS (mode) == MODE_CC);
39a10a29
GK
9542
9543 /* These don't make sense. */
37409796
NS
9544 gcc_assert ((code != GT && code != LT && code != GE && code != LE)
9545 || mode != CCUNSmode);
39a10a29 9546
37409796
NS
9547 gcc_assert ((code != GTU && code != LTU && code != GEU && code != LEU)
9548 || mode == CCUNSmode);
39a10a29 9549
37409796
NS
9550 gcc_assert (mode == CCFPmode
9551 || (code != ORDERED && code != UNORDERED
9552 && code != UNEQ && code != LTGT
9553 && code != UNGT && code != UNLT
9554 && code != UNGE && code != UNLE));
f676971a
EC
9555
9556 /* These should never be generated except for
bc9ec0e0 9557 flag_finite_math_only. */
37409796
NS
9558 gcc_assert (mode != CCFPmode
9559 || flag_finite_math_only
9560 || (code != LE && code != GE
9561 && code != UNEQ && code != LTGT
9562 && code != UNGT && code != UNLT));
39a10a29
GK
9563
9564 /* These are invalid; the information is not there. */
37409796 9565 gcc_assert (mode != CCEQmode || code == EQ || code == NE);
39a10a29
GK
9566}
9567
9878760c
RK
9568\f
9569/* Return 1 if ANDOP is a mask that has no bits on that are not in the
9570 mask required to convert the result of a rotate insn into a shift
b1765bde 9571 left insn of SHIFTOP bits. Both are known to be SImode CONST_INT. */
9878760c
RK
9572
9573int
a2369ed3 9574includes_lshift_p (rtx shiftop, rtx andop)
9878760c 9575{
e2c953b6
DE
9576 unsigned HOST_WIDE_INT shift_mask = ~(unsigned HOST_WIDE_INT) 0;
9577
9578 shift_mask <<= INTVAL (shiftop);
9878760c 9579
b1765bde 9580 return (INTVAL (andop) & 0xffffffff & ~shift_mask) == 0;
9878760c
RK
9581}
9582
9583/* Similar, but for right shift. */
9584
9585int
a2369ed3 9586includes_rshift_p (rtx shiftop, rtx andop)
9878760c 9587{
a7653a2c 9588 unsigned HOST_WIDE_INT shift_mask = ~(unsigned HOST_WIDE_INT) 0;
9878760c
RK
9589
9590 shift_mask >>= INTVAL (shiftop);
9591
b1765bde 9592 return (INTVAL (andop) & 0xffffffff & ~shift_mask) == 0;
e2c953b6
DE
9593}
9594
c5059423
AM
9595/* Return 1 if ANDOP is a mask suitable for use with an rldic insn
9596 to perform a left shift. It must have exactly SHIFTOP least
b6d08ca1 9597 significant 0's, then one or more 1's, then zero or more 0's. */
e2c953b6
DE
9598
9599int
a2369ed3 9600includes_rldic_lshift_p (rtx shiftop, rtx andop)
e2c953b6 9601{
c5059423
AM
9602 if (GET_CODE (andop) == CONST_INT)
9603 {
02071907 9604 HOST_WIDE_INT c, lsb, shift_mask;
e2c953b6 9605
c5059423 9606 c = INTVAL (andop);
02071907 9607 if (c == 0 || c == ~0)
c5059423 9608 return 0;
e2c953b6 9609
02071907 9610 shift_mask = ~0;
c5059423
AM
9611 shift_mask <<= INTVAL (shiftop);
9612
b6d08ca1 9613 /* Find the least significant one bit. */
c5059423
AM
9614 lsb = c & -c;
9615
9616 /* It must coincide with the LSB of the shift mask. */
9617 if (-lsb != shift_mask)
9618 return 0;
e2c953b6 9619
c5059423
AM
9620 /* Invert to look for the next transition (if any). */
9621 c = ~c;
9622
9623 /* Remove the low group of ones (originally low group of zeros). */
9624 c &= -lsb;
9625
9626 /* Again find the lsb, and check we have all 1's above. */
9627 lsb = c & -c;
9628 return c == -lsb;
9629 }
9630 else if (GET_CODE (andop) == CONST_DOUBLE
9631 && (GET_MODE (andop) == VOIDmode || GET_MODE (andop) == DImode))
9632 {
02071907
AM
9633 HOST_WIDE_INT low, high, lsb;
9634 HOST_WIDE_INT shift_mask_low, shift_mask_high;
c5059423
AM
9635
9636 low = CONST_DOUBLE_LOW (andop);
9637 if (HOST_BITS_PER_WIDE_INT < 64)
9638 high = CONST_DOUBLE_HIGH (andop);
9639
9640 if ((low == 0 && (HOST_BITS_PER_WIDE_INT >= 64 || high == 0))
02071907 9641 || (low == ~0 && (HOST_BITS_PER_WIDE_INT >= 64 || high == ~0)))
c5059423
AM
9642 return 0;
9643
9644 if (HOST_BITS_PER_WIDE_INT < 64 && low == 0)
9645 {
02071907 9646 shift_mask_high = ~0;
c5059423
AM
9647 if (INTVAL (shiftop) > 32)
9648 shift_mask_high <<= INTVAL (shiftop) - 32;
9649
9650 lsb = high & -high;
9651
9652 if (-lsb != shift_mask_high || INTVAL (shiftop) < 32)
9653 return 0;
9654
9655 high = ~high;
9656 high &= -lsb;
9657
9658 lsb = high & -high;
9659 return high == -lsb;
9660 }
9661
02071907 9662 shift_mask_low = ~0;
c5059423
AM
9663 shift_mask_low <<= INTVAL (shiftop);
9664
9665 lsb = low & -low;
9666
9667 if (-lsb != shift_mask_low)
9668 return 0;
9669
9670 if (HOST_BITS_PER_WIDE_INT < 64)
9671 high = ~high;
9672 low = ~low;
9673 low &= -lsb;
9674
9675 if (HOST_BITS_PER_WIDE_INT < 64 && low == 0)
9676 {
9677 lsb = high & -high;
9678 return high == -lsb;
9679 }
9680
9681 lsb = low & -low;
9682 return low == -lsb && (HOST_BITS_PER_WIDE_INT >= 64 || high == ~0);
9683 }
9684 else
9685 return 0;
9686}
e2c953b6 9687
c5059423
AM
9688/* Return 1 if ANDOP is a mask suitable for use with an rldicr insn
9689 to perform a left shift. It must have SHIFTOP or more least
c1207243 9690 significant 0's, with the remainder of the word 1's. */
e2c953b6 9691
c5059423 9692int
a2369ed3 9693includes_rldicr_lshift_p (rtx shiftop, rtx andop)
c5059423 9694{
e2c953b6 9695 if (GET_CODE (andop) == CONST_INT)
c5059423 9696 {
02071907 9697 HOST_WIDE_INT c, lsb, shift_mask;
c5059423 9698
02071907 9699 shift_mask = ~0;
c5059423
AM
9700 shift_mask <<= INTVAL (shiftop);
9701 c = INTVAL (andop);
9702
c1207243 9703 /* Find the least significant one bit. */
c5059423
AM
9704 lsb = c & -c;
9705
9706 /* It must be covered by the shift mask.
a4f6c312 9707 This test also rejects c == 0. */
c5059423
AM
9708 if ((lsb & shift_mask) == 0)
9709 return 0;
9710
9711 /* Check we have all 1's above the transition, and reject all 1's. */
9712 return c == -lsb && lsb != 1;
9713 }
9714 else if (GET_CODE (andop) == CONST_DOUBLE
9715 && (GET_MODE (andop) == VOIDmode || GET_MODE (andop) == DImode))
9716 {
02071907 9717 HOST_WIDE_INT low, lsb, shift_mask_low;
c5059423
AM
9718
9719 low = CONST_DOUBLE_LOW (andop);
9720
9721 if (HOST_BITS_PER_WIDE_INT < 64)
9722 {
02071907 9723 HOST_WIDE_INT high, shift_mask_high;
c5059423
AM
9724
9725 high = CONST_DOUBLE_HIGH (andop);
9726
9727 if (low == 0)
9728 {
02071907 9729 shift_mask_high = ~0;
c5059423
AM
9730 if (INTVAL (shiftop) > 32)
9731 shift_mask_high <<= INTVAL (shiftop) - 32;
9732
9733 lsb = high & -high;
9734
9735 if ((lsb & shift_mask_high) == 0)
9736 return 0;
9737
9738 return high == -lsb;
9739 }
9740 if (high != ~0)
9741 return 0;
9742 }
9743
02071907 9744 shift_mask_low = ~0;
c5059423
AM
9745 shift_mask_low <<= INTVAL (shiftop);
9746
9747 lsb = low & -low;
9748
9749 if ((lsb & shift_mask_low) == 0)
9750 return 0;
9751
9752 return low == -lsb && lsb != 1;
9753 }
e2c953b6 9754 else
c5059423 9755 return 0;
9878760c 9756}
35068b43 9757
11ac38b2
DE
9758/* Return 1 if operands will generate a valid arguments to rlwimi
9759instruction for insert with right shift in 64-bit mode. The mask may
9760not start on the first bit or stop on the last bit because wrap-around
9761effects of instruction do not correspond to semantics of RTL insn. */
9762
9763int
9764insvdi_rshift_rlwimi_p (rtx sizeop, rtx startop, rtx shiftop)
9765{
9766 if (INTVAL (startop) < 64
9767 && INTVAL (startop) > 32
9768 && (INTVAL (sizeop) + INTVAL (startop) < 64)
9769 && (INTVAL (sizeop) + INTVAL (startop) > 33)
9770 && (INTVAL (sizeop) + INTVAL (startop) + INTVAL (shiftop) < 96)
9771 && (INTVAL (sizeop) + INTVAL (startop) + INTVAL (shiftop) >= 64)
9772 && (64 - (INTVAL (shiftop) & 63)) >= INTVAL (sizeop))
9773 return 1;
9774
9775 return 0;
9776}
9777
35068b43 9778/* Return 1 if REGNO (reg1) == REGNO (reg2) - 1 making them candidates
90f81f99 9779 for lfq and stfq insns iff the registers are hard registers. */
35068b43
RK
9780
9781int
a2369ed3 9782registers_ok_for_quad_peep (rtx reg1, rtx reg2)
35068b43
RK
9783{
9784 /* We might have been passed a SUBREG. */
f676971a 9785 if (GET_CODE (reg1) != REG || GET_CODE (reg2) != REG)
35068b43 9786 return 0;
f676971a 9787
90f81f99
AP
9788 /* We might have been passed non floating point registers. */
9789 if (!FP_REGNO_P (REGNO (reg1))
9790 || !FP_REGNO_P (REGNO (reg2)))
9791 return 0;
35068b43
RK
9792
9793 return (REGNO (reg1) == REGNO (reg2) - 1);
9794}
9795
a4f6c312
SS
9796/* Return 1 if addr1 and addr2 are suitable for lfq or stfq insn.
9797 addr1 and addr2 must be in consecutive memory locations
9798 (addr2 == addr1 + 8). */
35068b43
RK
9799
9800int
90f81f99 9801mems_ok_for_quad_peep (rtx mem1, rtx mem2)
35068b43 9802{
90f81f99 9803 rtx addr1, addr2;
bb8df8a6
EC
9804 unsigned int reg1, reg2;
9805 int offset1, offset2;
35068b43 9806
90f81f99
AP
9807 /* The mems cannot be volatile. */
9808 if (MEM_VOLATILE_P (mem1) || MEM_VOLATILE_P (mem2))
9809 return 0;
f676971a 9810
90f81f99
AP
9811 addr1 = XEXP (mem1, 0);
9812 addr2 = XEXP (mem2, 0);
9813
35068b43
RK
9814 /* Extract an offset (if used) from the first addr. */
9815 if (GET_CODE (addr1) == PLUS)
9816 {
9817 /* If not a REG, return zero. */
9818 if (GET_CODE (XEXP (addr1, 0)) != REG)
9819 return 0;
9820 else
9821 {
c4ad648e 9822 reg1 = REGNO (XEXP (addr1, 0));
35068b43
RK
9823 /* The offset must be constant! */
9824 if (GET_CODE (XEXP (addr1, 1)) != CONST_INT)
c4ad648e
AM
9825 return 0;
9826 offset1 = INTVAL (XEXP (addr1, 1));
35068b43
RK
9827 }
9828 }
9829 else if (GET_CODE (addr1) != REG)
9830 return 0;
9831 else
9832 {
9833 reg1 = REGNO (addr1);
9834 /* This was a simple (mem (reg)) expression. Offset is 0. */
9835 offset1 = 0;
9836 }
9837
bb8df8a6
EC
9838 /* And now for the second addr. */
9839 if (GET_CODE (addr2) == PLUS)
9840 {
9841 /* If not a REG, return zero. */
9842 if (GET_CODE (XEXP (addr2, 0)) != REG)
9843 return 0;
9844 else
9845 {
9846 reg2 = REGNO (XEXP (addr2, 0));
9847 /* The offset must be constant. */
9848 if (GET_CODE (XEXP (addr2, 1)) != CONST_INT)
9849 return 0;
9850 offset2 = INTVAL (XEXP (addr2, 1));
9851 }
9852 }
9853 else if (GET_CODE (addr2) != REG)
35068b43 9854 return 0;
bb8df8a6
EC
9855 else
9856 {
9857 reg2 = REGNO (addr2);
9858 /* This was a simple (mem (reg)) expression. Offset is 0. */
9859 offset2 = 0;
9860 }
35068b43 9861
bb8df8a6
EC
9862 /* Both of these must have the same base register. */
9863 if (reg1 != reg2)
35068b43
RK
9864 return 0;
9865
9866 /* The offset for the second addr must be 8 more than the first addr. */
bb8df8a6 9867 if (offset2 != offset1 + 8)
35068b43
RK
9868 return 0;
9869
9870 /* All the tests passed. addr1 and addr2 are valid for lfq or stfq
9871 instructions. */
9872 return 1;
9873}
9878760c
RK
9874\f
9875/* Return the register class of a scratch register needed to copy IN into
9876 or out of a register in CLASS in MODE. If it can be done directly,
9877 NO_REGS is returned. */
9878
9879enum reg_class
3c4774e0
R
9880rs6000_secondary_reload_class (enum reg_class class,
9881 enum machine_mode mode ATTRIBUTE_UNUSED,
9882 rtx in)
9878760c 9883{
5accd822 9884 int regno;
9878760c 9885
ab82a49f
AP
9886 if (TARGET_ELF || (DEFAULT_ABI == ABI_DARWIN
9887#if TARGET_MACHO
c4ad648e 9888 && MACHOPIC_INDIRECT
ab82a49f 9889#endif
c4ad648e 9890 ))
46fad5b7
DJ
9891 {
9892 /* We cannot copy a symbolic operand directly into anything
c4ad648e
AM
9893 other than BASE_REGS for TARGET_ELF. So indicate that a
9894 register from BASE_REGS is needed as an intermediate
9895 register.
f676971a 9896
46fad5b7
DJ
9897 On Darwin, pic addresses require a load from memory, which
9898 needs a base register. */
9899 if (class != BASE_REGS
c4ad648e
AM
9900 && (GET_CODE (in) == SYMBOL_REF
9901 || GET_CODE (in) == HIGH
9902 || GET_CODE (in) == LABEL_REF
9903 || GET_CODE (in) == CONST))
9904 return BASE_REGS;
46fad5b7 9905 }
e7b7998a 9906
5accd822
DE
9907 if (GET_CODE (in) == REG)
9908 {
9909 regno = REGNO (in);
9910 if (regno >= FIRST_PSEUDO_REGISTER)
9911 {
9912 regno = true_regnum (in);
9913 if (regno >= FIRST_PSEUDO_REGISTER)
9914 regno = -1;
9915 }
9916 }
9917 else if (GET_CODE (in) == SUBREG)
9918 {
9919 regno = true_regnum (in);
9920 if (regno >= FIRST_PSEUDO_REGISTER)
9921 regno = -1;
9922 }
9923 else
9924 regno = -1;
9925
9878760c
RK
9926 /* We can place anything into GENERAL_REGS and can put GENERAL_REGS
9927 into anything. */
9928 if (class == GENERAL_REGS || class == BASE_REGS
9929 || (regno >= 0 && INT_REGNO_P (regno)))
9930 return NO_REGS;
9931
9932 /* Constants, memory, and FP registers can go into FP registers. */
9933 if ((regno == -1 || FP_REGNO_P (regno))
9934 && (class == FLOAT_REGS || class == NON_SPECIAL_REGS))
9935 return NO_REGS;
9936
0ac081f6
AH
9937 /* Memory, and AltiVec registers can go into AltiVec registers. */
9938 if ((regno == -1 || ALTIVEC_REGNO_P (regno))
9939 && class == ALTIVEC_REGS)
9940 return NO_REGS;
9941
9878760c
RK
9942 /* We can copy among the CR registers. */
9943 if ((class == CR_REGS || class == CR0_REGS)
9944 && regno >= 0 && CR_REGNO_P (regno))
9945 return NO_REGS;
9946
9947 /* Otherwise, we need GENERAL_REGS. */
9948 return GENERAL_REGS;
9949}
9950\f
9951/* Given a comparison operation, return the bit number in CCR to test. We
f676971a 9952 know this is a valid comparison.
9878760c
RK
9953
9954 SCC_P is 1 if this is for an scc. That means that %D will have been
9955 used instead of %C, so the bits will be in different places.
9956
b4ac57ab 9957 Return -1 if OP isn't a valid comparison for some reason. */
9878760c
RK
9958
9959int
a2369ed3 9960ccr_bit (rtx op, int scc_p)
9878760c
RK
9961{
9962 enum rtx_code code = GET_CODE (op);
9963 enum machine_mode cc_mode;
9964 int cc_regnum;
9965 int base_bit;
9ebbca7d 9966 rtx reg;
9878760c 9967
ec8e098d 9968 if (!COMPARISON_P (op))
9878760c
RK
9969 return -1;
9970
9ebbca7d
GK
9971 reg = XEXP (op, 0);
9972
37409796 9973 gcc_assert (GET_CODE (reg) == REG && CR_REGNO_P (REGNO (reg)));
9ebbca7d
GK
9974
9975 cc_mode = GET_MODE (reg);
9976 cc_regnum = REGNO (reg);
9977 base_bit = 4 * (cc_regnum - CR0_REGNO);
9878760c 9978
39a10a29 9979 validate_condition_mode (code, cc_mode);
c5defebb 9980
b7053a3f
GK
9981 /* When generating a sCOND operation, only positive conditions are
9982 allowed. */
37409796
NS
9983 gcc_assert (!scc_p
9984 || code == EQ || code == GT || code == LT || code == UNORDERED
9985 || code == GTU || code == LTU);
f676971a 9986
9878760c
RK
9987 switch (code)
9988 {
9989 case NE:
9990 return scc_p ? base_bit + 3 : base_bit + 2;
9991 case EQ:
9992 return base_bit + 2;
1c882ea4 9993 case GT: case GTU: case UNLE:
9878760c 9994 return base_bit + 1;
1c882ea4 9995 case LT: case LTU: case UNGE:
9878760c 9996 return base_bit;
1c882ea4
GK
9997 case ORDERED: case UNORDERED:
9998 return base_bit + 3;
9878760c
RK
9999
10000 case GE: case GEU:
39a10a29 10001 /* If scc, we will have done a cror to put the bit in the
9878760c
RK
10002 unordered position. So test that bit. For integer, this is ! LT
10003 unless this is an scc insn. */
39a10a29 10004 return scc_p ? base_bit + 3 : base_bit;
9878760c
RK
10005
10006 case LE: case LEU:
39a10a29 10007 return scc_p ? base_bit + 3 : base_bit + 1;
1c882ea4 10008
9878760c 10009 default:
37409796 10010 gcc_unreachable ();
9878760c
RK
10011 }
10012}
1ff7789b 10013\f
8d30c4ee 10014/* Return the GOT register. */
1ff7789b 10015
9390387d 10016rtx
a2369ed3 10017rs6000_got_register (rtx value ATTRIBUTE_UNUSED)
1ff7789b 10018{
a4f6c312
SS
10019 /* The second flow pass currently (June 1999) can't update
10020 regs_ever_live without disturbing other parts of the compiler, so
10021 update it here to make the prolog/epilogue code happy. */
1db02437
FS
10022 if (no_new_pseudos && ! regs_ever_live[RS6000_PIC_OFFSET_TABLE_REGNUM])
10023 regs_ever_live[RS6000_PIC_OFFSET_TABLE_REGNUM] = 1;
1ff7789b 10024
8d30c4ee 10025 current_function_uses_pic_offset_table = 1;
3cb999d8 10026
1ff7789b
MM
10027 return pic_offset_table_rtx;
10028}
a7df97e6 10029\f
e2500fed
GK
10030/* Function to init struct machine_function.
10031 This will be called, via a pointer variable,
10032 from push_function_context. */
a7df97e6 10033
e2500fed 10034static struct machine_function *
863d938c 10035rs6000_init_machine_status (void)
a7df97e6 10036{
e2500fed 10037 return ggc_alloc_cleared (sizeof (machine_function));
a7df97e6 10038}
9878760c 10039\f
0ba1b2ff
AM
10040/* These macros test for integers and extract the low-order bits. */
10041#define INT_P(X) \
10042((GET_CODE (X) == CONST_INT || GET_CODE (X) == CONST_DOUBLE) \
10043 && GET_MODE (X) == VOIDmode)
10044
10045#define INT_LOWPART(X) \
10046 (GET_CODE (X) == CONST_INT ? INTVAL (X) : CONST_DOUBLE_LOW (X))
10047
10048int
a2369ed3 10049extract_MB (rtx op)
0ba1b2ff
AM
10050{
10051 int i;
10052 unsigned long val = INT_LOWPART (op);
10053
10054 /* If the high bit is zero, the value is the first 1 bit we find
10055 from the left. */
10056 if ((val & 0x80000000) == 0)
10057 {
37409796 10058 gcc_assert (val & 0xffffffff);
0ba1b2ff
AM
10059
10060 i = 1;
10061 while (((val <<= 1) & 0x80000000) == 0)
10062 ++i;
10063 return i;
10064 }
10065
10066 /* If the high bit is set and the low bit is not, or the mask is all
10067 1's, the value is zero. */
10068 if ((val & 1) == 0 || (val & 0xffffffff) == 0xffffffff)
10069 return 0;
10070
10071 /* Otherwise we have a wrap-around mask. Look for the first 0 bit
10072 from the right. */
10073 i = 31;
10074 while (((val >>= 1) & 1) != 0)
10075 --i;
10076
10077 return i;
10078}
10079
10080int
a2369ed3 10081extract_ME (rtx op)
0ba1b2ff
AM
10082{
10083 int i;
10084 unsigned long val = INT_LOWPART (op);
10085
10086 /* If the low bit is zero, the value is the first 1 bit we find from
10087 the right. */
10088 if ((val & 1) == 0)
10089 {
37409796 10090 gcc_assert (val & 0xffffffff);
0ba1b2ff
AM
10091
10092 i = 30;
10093 while (((val >>= 1) & 1) == 0)
10094 --i;
10095
10096 return i;
10097 }
10098
10099 /* If the low bit is set and the high bit is not, or the mask is all
10100 1's, the value is 31. */
10101 if ((val & 0x80000000) == 0 || (val & 0xffffffff) == 0xffffffff)
10102 return 31;
10103
10104 /* Otherwise we have a wrap-around mask. Look for the first 0 bit
10105 from the left. */
10106 i = 0;
10107 while (((val <<= 1) & 0x80000000) != 0)
10108 ++i;
10109
10110 return i;
10111}
10112
c4501e62
JJ
10113/* Locate some local-dynamic symbol still in use by this function
10114 so that we can print its name in some tls_ld pattern. */
10115
10116static const char *
863d938c 10117rs6000_get_some_local_dynamic_name (void)
c4501e62
JJ
10118{
10119 rtx insn;
10120
10121 if (cfun->machine->some_ld_name)
10122 return cfun->machine->some_ld_name;
10123
10124 for (insn = get_insns (); insn ; insn = NEXT_INSN (insn))
10125 if (INSN_P (insn)
10126 && for_each_rtx (&PATTERN (insn),
10127 rs6000_get_some_local_dynamic_name_1, 0))
10128 return cfun->machine->some_ld_name;
10129
37409796 10130 gcc_unreachable ();
c4501e62
JJ
10131}
10132
10133/* Helper function for rs6000_get_some_local_dynamic_name. */
10134
10135static int
a2369ed3 10136rs6000_get_some_local_dynamic_name_1 (rtx *px, void *data ATTRIBUTE_UNUSED)
c4501e62
JJ
10137{
10138 rtx x = *px;
10139
10140 if (GET_CODE (x) == SYMBOL_REF)
10141 {
10142 const char *str = XSTR (x, 0);
10143 if (SYMBOL_REF_TLS_MODEL (x) == TLS_MODEL_LOCAL_DYNAMIC)
10144 {
10145 cfun->machine->some_ld_name = str;
10146 return 1;
10147 }
10148 }
10149
10150 return 0;
10151}
10152
85b776df
AM
10153/* Write out a function code label. */
10154
10155void
10156rs6000_output_function_entry (FILE *file, const char *fname)
10157{
10158 if (fname[0] != '.')
10159 {
10160 switch (DEFAULT_ABI)
10161 {
10162 default:
37409796 10163 gcc_unreachable ();
85b776df
AM
10164
10165 case ABI_AIX:
10166 if (DOT_SYMBOLS)
10167 putc ('.', file);
10168 else
10169 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (file, "L.");
10170 break;
10171
10172 case ABI_V4:
10173 case ABI_DARWIN:
10174 break;
10175 }
10176 }
10177 if (TARGET_AIX)
10178 RS6000_OUTPUT_BASENAME (file, fname);
10179 else
10180 assemble_name (file, fname);
10181}
10182
9878760c
RK
10183/* Print an operand. Recognize special options, documented below. */
10184
38c1f2d7 10185#if TARGET_ELF
d9407988 10186#define SMALL_DATA_RELOC ((rs6000_sdata == SDATA_EABI) ? "sda21" : "sdarel")
8fbd2dc7 10187#define SMALL_DATA_REG ((rs6000_sdata == SDATA_EABI) ? 0 : 13)
ba5e43aa
MM
10188#else
10189#define SMALL_DATA_RELOC "sda21"
8fbd2dc7 10190#define SMALL_DATA_REG 0
ba5e43aa
MM
10191#endif
10192
9878760c 10193void
a2369ed3 10194print_operand (FILE *file, rtx x, int code)
9878760c
RK
10195{
10196 int i;
a260abc9 10197 HOST_WIDE_INT val;
0ba1b2ff 10198 unsigned HOST_WIDE_INT uval;
9878760c
RK
10199
10200 switch (code)
10201 {
a8b3aeda 10202 case '.':
a85d226b
RK
10203 /* Write out an instruction after the call which may be replaced
10204 with glue code by the loader. This depends on the AIX version. */
10205 asm_fprintf (file, RS6000_CALL_GLUE);
a8b3aeda
RK
10206 return;
10207
81eace42
GK
10208 /* %a is output_address. */
10209
9854d9ed
RK
10210 case 'A':
10211 /* If X is a constant integer whose low-order 5 bits are zero,
10212 write 'l'. Otherwise, write 'r'. This is a kludge to fix a bug
76229ac8 10213 in the AIX assembler where "sri" with a zero shift count
20e26713 10214 writes a trash instruction. */
9854d9ed 10215 if (GET_CODE (x) == CONST_INT && (INTVAL (x) & 31) == 0)
76229ac8 10216 putc ('l', file);
9854d9ed 10217 else
76229ac8 10218 putc ('r', file);
9854d9ed
RK
10219 return;
10220
10221 case 'b':
e2c953b6
DE
10222 /* If constant, low-order 16 bits of constant, unsigned.
10223 Otherwise, write normally. */
10224 if (INT_P (x))
10225 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INT_LOWPART (x) & 0xffff);
10226 else
10227 print_operand (file, x, 0);
cad12a8d
RK
10228 return;
10229
a260abc9
DE
10230 case 'B':
10231 /* If the low-order bit is zero, write 'r'; otherwise, write 'l'
10232 for 64-bit mask direction. */
9390387d 10233 putc (((INT_LOWPART (x) & 1) == 0 ? 'r' : 'l'), file);
a238cd8b 10234 return;
a260abc9 10235
81eace42
GK
10236 /* %c is output_addr_const if a CONSTANT_ADDRESS_P, otherwise
10237 output_operand. */
10238
423c1189
AH
10239 case 'c':
10240 /* X is a CR register. Print the number of the GT bit of the CR. */
10241 if (GET_CODE (x) != REG || ! CR_REGNO_P (REGNO (x)))
10242 output_operand_lossage ("invalid %%E value");
10243 else
10244 fprintf (file, "%d", 4 * (REGNO (x) - CR0_REGNO) + 1);
10245 return;
10246
10247 case 'D':
6b1fedc3 10248 /* Like 'J' but get to the EQ bit. */
37409796 10249 gcc_assert (GET_CODE (x) == REG);
423c1189 10250
6b1fedc3
AH
10251 /* Bit 1 is EQ bit. */
10252 i = 4 * (REGNO (x) - CR0_REGNO) + 2;
423c1189 10253
64022b5d 10254 fprintf (file, "%d", i);
423c1189
AH
10255 return;
10256
9854d9ed 10257 case 'E':
39a10a29 10258 /* X is a CR register. Print the number of the EQ bit of the CR */
9854d9ed
RK
10259 if (GET_CODE (x) != REG || ! CR_REGNO_P (REGNO (x)))
10260 output_operand_lossage ("invalid %%E value");
78fbdbf7 10261 else
39a10a29 10262 fprintf (file, "%d", 4 * (REGNO (x) - CR0_REGNO) + 2);
a85d226b 10263 return;
9854d9ed
RK
10264
10265 case 'f':
10266 /* X is a CR register. Print the shift count needed to move it
10267 to the high-order four bits. */
10268 if (GET_CODE (x) != REG || ! CR_REGNO_P (REGNO (x)))
10269 output_operand_lossage ("invalid %%f value");
10270 else
9ebbca7d 10271 fprintf (file, "%d", 4 * (REGNO (x) - CR0_REGNO));
9854d9ed
RK
10272 return;
10273
10274 case 'F':
10275 /* Similar, but print the count for the rotate in the opposite
10276 direction. */
10277 if (GET_CODE (x) != REG || ! CR_REGNO_P (REGNO (x)))
10278 output_operand_lossage ("invalid %%F value");
10279 else
9ebbca7d 10280 fprintf (file, "%d", 32 - 4 * (REGNO (x) - CR0_REGNO));
9854d9ed
RK
10281 return;
10282
10283 case 'G':
10284 /* X is a constant integer. If it is negative, print "m",
43aa4e05 10285 otherwise print "z". This is to make an aze or ame insn. */
9854d9ed
RK
10286 if (GET_CODE (x) != CONST_INT)
10287 output_operand_lossage ("invalid %%G value");
10288 else if (INTVAL (x) >= 0)
76229ac8 10289 putc ('z', file);
9854d9ed 10290 else
76229ac8 10291 putc ('m', file);
9854d9ed 10292 return;
e2c953b6 10293
9878760c 10294 case 'h':
a4f6c312
SS
10295 /* If constant, output low-order five bits. Otherwise, write
10296 normally. */
9878760c 10297 if (INT_P (x))
5f59ecb7 10298 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INT_LOWPART (x) & 31);
9878760c
RK
10299 else
10300 print_operand (file, x, 0);
10301 return;
10302
64305719 10303 case 'H':
a4f6c312
SS
10304 /* If constant, output low-order six bits. Otherwise, write
10305 normally. */
64305719 10306 if (INT_P (x))
5f59ecb7 10307 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INT_LOWPART (x) & 63);
64305719
DE
10308 else
10309 print_operand (file, x, 0);
10310 return;
10311
9854d9ed
RK
10312 case 'I':
10313 /* Print `i' if this is a constant, else nothing. */
9878760c 10314 if (INT_P (x))
76229ac8 10315 putc ('i', file);
9878760c
RK
10316 return;
10317
9854d9ed
RK
10318 case 'j':
10319 /* Write the bit number in CCR for jump. */
10320 i = ccr_bit (x, 0);
10321 if (i == -1)
10322 output_operand_lossage ("invalid %%j code");
9878760c 10323 else
9854d9ed 10324 fprintf (file, "%d", i);
9878760c
RK
10325 return;
10326
9854d9ed
RK
10327 case 'J':
10328 /* Similar, but add one for shift count in rlinm for scc and pass
10329 scc flag to `ccr_bit'. */
10330 i = ccr_bit (x, 1);
10331 if (i == -1)
10332 output_operand_lossage ("invalid %%J code");
10333 else
a0466a68
RK
10334 /* If we want bit 31, write a shift count of zero, not 32. */
10335 fprintf (file, "%d", i == 31 ? 0 : i + 1);
9878760c
RK
10336 return;
10337
9854d9ed
RK
10338 case 'k':
10339 /* X must be a constant. Write the 1's complement of the
10340 constant. */
9878760c 10341 if (! INT_P (x))
9854d9ed 10342 output_operand_lossage ("invalid %%k value");
e2c953b6
DE
10343 else
10344 fprintf (file, HOST_WIDE_INT_PRINT_DEC, ~ INT_LOWPART (x));
9878760c
RK
10345 return;
10346
81eace42 10347 case 'K':
9ebbca7d
GK
10348 /* X must be a symbolic constant on ELF. Write an
10349 expression suitable for an 'addi' that adds in the low 16
10350 bits of the MEM. */
10351 if (GET_CODE (x) != CONST)
10352 {
10353 print_operand_address (file, x);
10354 fputs ("@l", file);
10355 }
10356 else
10357 {
10358 if (GET_CODE (XEXP (x, 0)) != PLUS
10359 || (GET_CODE (XEXP (XEXP (x, 0), 0)) != SYMBOL_REF
10360 && GET_CODE (XEXP (XEXP (x, 0), 0)) != LABEL_REF)
10361 || GET_CODE (XEXP (XEXP (x, 0), 1)) != CONST_INT)
53cd5d6c 10362 output_operand_lossage ("invalid %%K value");
9ebbca7d
GK
10363 print_operand_address (file, XEXP (XEXP (x, 0), 0));
10364 fputs ("@l", file);
ed8d2920
MM
10365 /* For GNU as, there must be a non-alphanumeric character
10366 between 'l' and the number. The '-' is added by
10367 print_operand() already. */
10368 if (INTVAL (XEXP (XEXP (x, 0), 1)) >= 0)
10369 fputs ("+", file);
9ebbca7d
GK
10370 print_operand (file, XEXP (XEXP (x, 0), 1), 0);
10371 }
81eace42
GK
10372 return;
10373
10374 /* %l is output_asm_label. */
9ebbca7d 10375
9854d9ed
RK
10376 case 'L':
10377 /* Write second word of DImode or DFmode reference. Works on register
10378 or non-indexed memory only. */
10379 if (GET_CODE (x) == REG)
fb5c67a7 10380 fputs (reg_names[REGNO (x) + 1], file);
9854d9ed
RK
10381 else if (GET_CODE (x) == MEM)
10382 {
10383 /* Handle possible auto-increment. Since it is pre-increment and
1427100a 10384 we have already done it, we can just use an offset of word. */
9854d9ed
RK
10385 if (GET_CODE (XEXP (x, 0)) == PRE_INC
10386 || GET_CODE (XEXP (x, 0)) == PRE_DEC)
ed8908e7
RK
10387 output_address (plus_constant (XEXP (XEXP (x, 0), 0),
10388 UNITS_PER_WORD));
9854d9ed 10389 else
d7624dc0
RK
10390 output_address (XEXP (adjust_address_nv (x, SImode,
10391 UNITS_PER_WORD),
10392 0));
ed8908e7 10393
ba5e43aa 10394 if (small_data_operand (x, GET_MODE (x)))
8fbd2dc7
MM
10395 fprintf (file, "@%s(%s)", SMALL_DATA_RELOC,
10396 reg_names[SMALL_DATA_REG]);
9854d9ed 10397 }
9878760c 10398 return;
f676971a 10399
9878760c
RK
10400 case 'm':
10401 /* MB value for a mask operand. */
b1765bde 10402 if (! mask_operand (x, SImode))
9878760c
RK
10403 output_operand_lossage ("invalid %%m value");
10404
0ba1b2ff 10405 fprintf (file, "%d", extract_MB (x));
9878760c
RK
10406 return;
10407
10408 case 'M':
10409 /* ME value for a mask operand. */
b1765bde 10410 if (! mask_operand (x, SImode))
a260abc9 10411 output_operand_lossage ("invalid %%M value");
9878760c 10412
0ba1b2ff 10413 fprintf (file, "%d", extract_ME (x));
9878760c
RK
10414 return;
10415
81eace42
GK
10416 /* %n outputs the negative of its operand. */
10417
9878760c
RK
10418 case 'N':
10419 /* Write the number of elements in the vector times 4. */
10420 if (GET_CODE (x) != PARALLEL)
10421 output_operand_lossage ("invalid %%N value");
e2c953b6
DE
10422 else
10423 fprintf (file, "%d", XVECLEN (x, 0) * 4);
9878760c
RK
10424 return;
10425
10426 case 'O':
10427 /* Similar, but subtract 1 first. */
10428 if (GET_CODE (x) != PARALLEL)
1427100a 10429 output_operand_lossage ("invalid %%O value");
e2c953b6
DE
10430 else
10431 fprintf (file, "%d", (XVECLEN (x, 0) - 1) * 4);
9878760c
RK
10432 return;
10433
9854d9ed
RK
10434 case 'p':
10435 /* X is a CONST_INT that is a power of two. Output the logarithm. */
10436 if (! INT_P (x)
2bfcf297 10437 || INT_LOWPART (x) < 0
9854d9ed
RK
10438 || (i = exact_log2 (INT_LOWPART (x))) < 0)
10439 output_operand_lossage ("invalid %%p value");
e2c953b6
DE
10440 else
10441 fprintf (file, "%d", i);
9854d9ed
RK
10442 return;
10443
9878760c
RK
10444 case 'P':
10445 /* The operand must be an indirect memory reference. The result
8bb418a3 10446 is the register name. */
9878760c
RK
10447 if (GET_CODE (x) != MEM || GET_CODE (XEXP (x, 0)) != REG
10448 || REGNO (XEXP (x, 0)) >= 32)
10449 output_operand_lossage ("invalid %%P value");
e2c953b6 10450 else
fb5c67a7 10451 fputs (reg_names[REGNO (XEXP (x, 0))], file);
9878760c
RK
10452 return;
10453
dfbdccdb
GK
10454 case 'q':
10455 /* This outputs the logical code corresponding to a boolean
10456 expression. The expression may have one or both operands
39a10a29 10457 negated (if one, only the first one). For condition register
c4ad648e
AM
10458 logical operations, it will also treat the negated
10459 CR codes as NOTs, but not handle NOTs of them. */
dfbdccdb 10460 {
63bc1d05 10461 const char *const *t = 0;
dfbdccdb
GK
10462 const char *s;
10463 enum rtx_code code = GET_CODE (x);
10464 static const char * const tbl[3][3] = {
10465 { "and", "andc", "nor" },
10466 { "or", "orc", "nand" },
10467 { "xor", "eqv", "xor" } };
10468
10469 if (code == AND)
10470 t = tbl[0];
10471 else if (code == IOR)
10472 t = tbl[1];
10473 else if (code == XOR)
10474 t = tbl[2];
10475 else
10476 output_operand_lossage ("invalid %%q value");
10477
10478 if (GET_CODE (XEXP (x, 0)) != NOT)
10479 s = t[0];
10480 else
10481 {
10482 if (GET_CODE (XEXP (x, 1)) == NOT)
10483 s = t[2];
10484 else
10485 s = t[1];
10486 }
f676971a 10487
dfbdccdb
GK
10488 fputs (s, file);
10489 }
10490 return;
10491
2c4a9cff
DE
10492 case 'Q':
10493 if (TARGET_MFCRF)
3b6ce0af 10494 fputc (',', file);
5efb1046 10495 /* FALLTHRU */
2c4a9cff
DE
10496 else
10497 return;
10498
9854d9ed
RK
10499 case 'R':
10500 /* X is a CR register. Print the mask for `mtcrf'. */
10501 if (GET_CODE (x) != REG || ! CR_REGNO_P (REGNO (x)))
10502 output_operand_lossage ("invalid %%R value");
10503 else
9ebbca7d 10504 fprintf (file, "%d", 128 >> (REGNO (x) - CR0_REGNO));
9878760c 10505 return;
9854d9ed
RK
10506
10507 case 's':
10508 /* Low 5 bits of 32 - value */
10509 if (! INT_P (x))
10510 output_operand_lossage ("invalid %%s value");
e2c953b6
DE
10511 else
10512 fprintf (file, HOST_WIDE_INT_PRINT_DEC, (32 - INT_LOWPART (x)) & 31);
9878760c 10513 return;
9854d9ed 10514
a260abc9 10515 case 'S':
0ba1b2ff 10516 /* PowerPC64 mask position. All 0's is excluded.
a260abc9
DE
10517 CONST_INT 32-bit mask is considered sign-extended so any
10518 transition must occur within the CONST_INT, not on the boundary. */
1990cd79 10519 if (! mask64_operand (x, DImode))
a260abc9
DE
10520 output_operand_lossage ("invalid %%S value");
10521
0ba1b2ff 10522 uval = INT_LOWPART (x);
a260abc9 10523
0ba1b2ff 10524 if (uval & 1) /* Clear Left */
a260abc9 10525 {
f099d360
GK
10526#if HOST_BITS_PER_WIDE_INT > 64
10527 uval &= ((unsigned HOST_WIDE_INT) 1 << 64) - 1;
10528#endif
0ba1b2ff 10529 i = 64;
a260abc9 10530 }
0ba1b2ff 10531 else /* Clear Right */
a260abc9 10532 {
0ba1b2ff 10533 uval = ~uval;
f099d360
GK
10534#if HOST_BITS_PER_WIDE_INT > 64
10535 uval &= ((unsigned HOST_WIDE_INT) 1 << 64) - 1;
10536#endif
0ba1b2ff 10537 i = 63;
a260abc9 10538 }
0ba1b2ff
AM
10539 while (uval != 0)
10540 --i, uval >>= 1;
37409796 10541 gcc_assert (i >= 0);
0ba1b2ff
AM
10542 fprintf (file, "%d", i);
10543 return;
a260abc9 10544
a3170dc6
AH
10545 case 't':
10546 /* Like 'J' but get to the OVERFLOW/UNORDERED bit. */
37409796 10547 gcc_assert (GET_CODE (x) == REG && GET_MODE (x) == CCmode);
a3170dc6
AH
10548
10549 /* Bit 3 is OV bit. */
10550 i = 4 * (REGNO (x) - CR0_REGNO) + 3;
10551
10552 /* If we want bit 31, write a shift count of zero, not 32. */
10553 fprintf (file, "%d", i == 31 ? 0 : i + 1);
10554 return;
10555
cccf3bdc
DE
10556 case 'T':
10557 /* Print the symbolic name of a branch target register. */
10558 if (GET_CODE (x) != REG || (REGNO (x) != LINK_REGISTER_REGNUM
10559 && REGNO (x) != COUNT_REGISTER_REGNUM))
10560 output_operand_lossage ("invalid %%T value");
e2c953b6 10561 else if (REGNO (x) == LINK_REGISTER_REGNUM)
cccf3bdc
DE
10562 fputs (TARGET_NEW_MNEMONICS ? "lr" : "r", file);
10563 else
10564 fputs ("ctr", file);
10565 return;
10566
9854d9ed 10567 case 'u':
802a0058 10568 /* High-order 16 bits of constant for use in unsigned operand. */
9854d9ed
RK
10569 if (! INT_P (x))
10570 output_operand_lossage ("invalid %%u value");
e2c953b6 10571 else
f676971a 10572 fprintf (file, HOST_WIDE_INT_PRINT_HEX,
e2c953b6 10573 (INT_LOWPART (x) >> 16) & 0xffff);
9878760c
RK
10574 return;
10575
802a0058
MM
10576 case 'v':
10577 /* High-order 16 bits of constant for use in signed operand. */
10578 if (! INT_P (x))
10579 output_operand_lossage ("invalid %%v value");
e2c953b6 10580 else
134c32f6
DE
10581 fprintf (file, HOST_WIDE_INT_PRINT_HEX,
10582 (INT_LOWPART (x) >> 16) & 0xffff);
10583 return;
802a0058 10584
9854d9ed
RK
10585 case 'U':
10586 /* Print `u' if this has an auto-increment or auto-decrement. */
10587 if (GET_CODE (x) == MEM
10588 && (GET_CODE (XEXP (x, 0)) == PRE_INC
10589 || GET_CODE (XEXP (x, 0)) == PRE_DEC))
76229ac8 10590 putc ('u', file);
9854d9ed 10591 return;
9878760c 10592
e0cd0770
JC
10593 case 'V':
10594 /* Print the trap code for this operand. */
10595 switch (GET_CODE (x))
10596 {
10597 case EQ:
10598 fputs ("eq", file); /* 4 */
10599 break;
10600 case NE:
10601 fputs ("ne", file); /* 24 */
10602 break;
10603 case LT:
10604 fputs ("lt", file); /* 16 */
10605 break;
10606 case LE:
10607 fputs ("le", file); /* 20 */
10608 break;
10609 case GT:
10610 fputs ("gt", file); /* 8 */
10611 break;
10612 case GE:
10613 fputs ("ge", file); /* 12 */
10614 break;
10615 case LTU:
10616 fputs ("llt", file); /* 2 */
10617 break;
10618 case LEU:
10619 fputs ("lle", file); /* 6 */
10620 break;
10621 case GTU:
10622 fputs ("lgt", file); /* 1 */
10623 break;
10624 case GEU:
10625 fputs ("lge", file); /* 5 */
10626 break;
10627 default:
37409796 10628 gcc_unreachable ();
e0cd0770
JC
10629 }
10630 break;
10631
9854d9ed
RK
10632 case 'w':
10633 /* If constant, low-order 16 bits of constant, signed. Otherwise, write
10634 normally. */
10635 if (INT_P (x))
f676971a 10636 fprintf (file, HOST_WIDE_INT_PRINT_DEC,
5f59ecb7 10637 ((INT_LOWPART (x) & 0xffff) ^ 0x8000) - 0x8000);
9854d9ed
RK
10638 else
10639 print_operand (file, x, 0);
9878760c
RK
10640 return;
10641
9854d9ed 10642 case 'W':
e2c953b6 10643 /* MB value for a PowerPC64 rldic operand. */
e2c953b6
DE
10644 val = (GET_CODE (x) == CONST_INT
10645 ? INTVAL (x) : CONST_DOUBLE_HIGH (x));
10646
10647 if (val < 0)
10648 i = -1;
9854d9ed 10649 else
e2c953b6
DE
10650 for (i = 0; i < HOST_BITS_PER_WIDE_INT; i++)
10651 if ((val <<= 1) < 0)
10652 break;
10653
10654#if HOST_BITS_PER_WIDE_INT == 32
10655 if (GET_CODE (x) == CONST_INT && i >= 0)
10656 i += 32; /* zero-extend high-part was all 0's */
10657 else if (GET_CODE (x) == CONST_DOUBLE && i == 32)
10658 {
10659 val = CONST_DOUBLE_LOW (x);
10660
37409796
NS
10661 gcc_assert (val);
10662 if (val < 0)
e2c953b6
DE
10663 --i;
10664 else
10665 for ( ; i < 64; i++)
10666 if ((val <<= 1) < 0)
10667 break;
10668 }
10669#endif
10670
10671 fprintf (file, "%d", i + 1);
9854d9ed 10672 return;
9878760c 10673
9854d9ed
RK
10674 case 'X':
10675 if (GET_CODE (x) == MEM
4d588c14 10676 && legitimate_indexed_address_p (XEXP (x, 0), 0))
76229ac8 10677 putc ('x', file);
9854d9ed 10678 return;
9878760c 10679
9854d9ed
RK
10680 case 'Y':
10681 /* Like 'L', for third word of TImode */
10682 if (GET_CODE (x) == REG)
fb5c67a7 10683 fputs (reg_names[REGNO (x) + 2], file);
9854d9ed 10684 else if (GET_CODE (x) == MEM)
9878760c 10685 {
9854d9ed
RK
10686 if (GET_CODE (XEXP (x, 0)) == PRE_INC
10687 || GET_CODE (XEXP (x, 0)) == PRE_DEC)
a54d04b7 10688 output_address (plus_constant (XEXP (XEXP (x, 0), 0), 8));
9854d9ed 10689 else
d7624dc0 10690 output_address (XEXP (adjust_address_nv (x, SImode, 8), 0));
ba5e43aa 10691 if (small_data_operand (x, GET_MODE (x)))
8fbd2dc7
MM
10692 fprintf (file, "@%s(%s)", SMALL_DATA_RELOC,
10693 reg_names[SMALL_DATA_REG]);
9878760c
RK
10694 }
10695 return;
f676971a 10696
9878760c 10697 case 'z':
b4ac57ab
RS
10698 /* X is a SYMBOL_REF. Write out the name preceded by a
10699 period and without any trailing data in brackets. Used for function
4d30c363
MM
10700 names. If we are configured for System V (or the embedded ABI) on
10701 the PowerPC, do not emit the period, since those systems do not use
10702 TOCs and the like. */
37409796 10703 gcc_assert (GET_CODE (x) == SYMBOL_REF);
9878760c 10704
c4ad648e
AM
10705 /* Mark the decl as referenced so that cgraph will output the
10706 function. */
9bf6462a 10707 if (SYMBOL_REF_DECL (x))
c4ad648e 10708 mark_decl_referenced (SYMBOL_REF_DECL (x));
9bf6462a 10709
85b776df 10710 /* For macho, check to see if we need a stub. */
f9da97f0
AP
10711 if (TARGET_MACHO)
10712 {
10713 const char *name = XSTR (x, 0);
a031e781 10714#if TARGET_MACHO
3b48085e 10715 if (MACHOPIC_INDIRECT
11abc112
MM
10716 && machopic_classify_symbol (x) == MACHOPIC_UNDEFINED_FUNCTION)
10717 name = machopic_indirection_name (x, /*stub_p=*/true);
f9da97f0
AP
10718#endif
10719 assemble_name (file, name);
10720 }
85b776df 10721 else if (!DOT_SYMBOLS)
9739c90c 10722 assemble_name (file, XSTR (x, 0));
85b776df
AM
10723 else
10724 rs6000_output_function_entry (file, XSTR (x, 0));
9878760c
RK
10725 return;
10726
9854d9ed
RK
10727 case 'Z':
10728 /* Like 'L', for last word of TImode. */
10729 if (GET_CODE (x) == REG)
fb5c67a7 10730 fputs (reg_names[REGNO (x) + 3], file);
9854d9ed
RK
10731 else if (GET_CODE (x) == MEM)
10732 {
10733 if (GET_CODE (XEXP (x, 0)) == PRE_INC
10734 || GET_CODE (XEXP (x, 0)) == PRE_DEC)
a54d04b7 10735 output_address (plus_constant (XEXP (XEXP (x, 0), 0), 12));
9854d9ed 10736 else
d7624dc0 10737 output_address (XEXP (adjust_address_nv (x, SImode, 12), 0));
ba5e43aa 10738 if (small_data_operand (x, GET_MODE (x)))
8fbd2dc7
MM
10739 fprintf (file, "@%s(%s)", SMALL_DATA_RELOC,
10740 reg_names[SMALL_DATA_REG]);
9854d9ed 10741 }
5c23c401 10742 return;
0ac081f6 10743
a3170dc6 10744 /* Print AltiVec or SPE memory operand. */
0ac081f6
AH
10745 case 'y':
10746 {
10747 rtx tmp;
10748
37409796 10749 gcc_assert (GET_CODE (x) == MEM);
0ac081f6
AH
10750
10751 tmp = XEXP (x, 0);
10752
993f19a8 10753 if (TARGET_E500)
a3170dc6
AH
10754 {
10755 /* Handle [reg]. */
10756 if (GET_CODE (tmp) == REG)
10757 {
10758 fprintf (file, "0(%s)", reg_names[REGNO (tmp)]);
10759 break;
10760 }
10761 /* Handle [reg+UIMM]. */
10762 else if (GET_CODE (tmp) == PLUS &&
10763 GET_CODE (XEXP (tmp, 1)) == CONST_INT)
10764 {
10765 int x;
10766
37409796 10767 gcc_assert (GET_CODE (XEXP (tmp, 0)) == REG);
a3170dc6
AH
10768
10769 x = INTVAL (XEXP (tmp, 1));
10770 fprintf (file, "%d(%s)", x, reg_names[REGNO (XEXP (tmp, 0))]);
10771 break;
10772 }
10773
10774 /* Fall through. Must be [reg+reg]. */
10775 }
850e8d3d
DN
10776 if (TARGET_ALTIVEC
10777 && GET_CODE (tmp) == AND
10778 && GET_CODE (XEXP (tmp, 1)) == CONST_INT
10779 && INTVAL (XEXP (tmp, 1)) == -16)
10780 tmp = XEXP (tmp, 0);
0ac081f6 10781 if (GET_CODE (tmp) == REG)
c62f2db5 10782 fprintf (file, "0,%s", reg_names[REGNO (tmp)]);
37409796 10783 else
0ac081f6 10784 {
37409796 10785 gcc_assert (GET_CODE (tmp) == PLUS
9024f4b8
AM
10786 && REG_P (XEXP (tmp, 0))
10787 && REG_P (XEXP (tmp, 1)));
bb8df8a6 10788
0ac081f6
AH
10789 if (REGNO (XEXP (tmp, 0)) == 0)
10790 fprintf (file, "%s,%s", reg_names[ REGNO (XEXP (tmp, 1)) ],
10791 reg_names[ REGNO (XEXP (tmp, 0)) ]);
10792 else
10793 fprintf (file, "%s,%s", reg_names[ REGNO (XEXP (tmp, 0)) ],
10794 reg_names[ REGNO (XEXP (tmp, 1)) ]);
10795 }
0ac081f6
AH
10796 break;
10797 }
f676971a 10798
9878760c
RK
10799 case 0:
10800 if (GET_CODE (x) == REG)
10801 fprintf (file, "%s", reg_names[REGNO (x)]);
10802 else if (GET_CODE (x) == MEM)
10803 {
10804 /* We need to handle PRE_INC and PRE_DEC here, since we need to
10805 know the width from the mode. */
10806 if (GET_CODE (XEXP (x, 0)) == PRE_INC)
79ba6d34
MM
10807 fprintf (file, "%d(%s)", GET_MODE_SIZE (GET_MODE (x)),
10808 reg_names[REGNO (XEXP (XEXP (x, 0), 0))]);
9878760c 10809 else if (GET_CODE (XEXP (x, 0)) == PRE_DEC)
79ba6d34
MM
10810 fprintf (file, "%d(%s)", - GET_MODE_SIZE (GET_MODE (x)),
10811 reg_names[REGNO (XEXP (XEXP (x, 0), 0))]);
9878760c 10812 else
a54d04b7 10813 output_address (XEXP (x, 0));
9878760c
RK
10814 }
10815 else
a54d04b7 10816 output_addr_const (file, x);
a85d226b 10817 return;
9878760c 10818
c4501e62
JJ
10819 case '&':
10820 assemble_name (file, rs6000_get_some_local_dynamic_name ());
10821 return;
10822
9878760c
RK
10823 default:
10824 output_operand_lossage ("invalid %%xn code");
10825 }
10826}
10827\f
10828/* Print the address of an operand. */
10829
10830void
a2369ed3 10831print_operand_address (FILE *file, rtx x)
9878760c
RK
10832{
10833 if (GET_CODE (x) == REG)
4697a36c 10834 fprintf (file, "0(%s)", reg_names[ REGNO (x) ]);
9ebbca7d
GK
10835 else if (GET_CODE (x) == SYMBOL_REF || GET_CODE (x) == CONST
10836 || GET_CODE (x) == LABEL_REF)
9878760c
RK
10837 {
10838 output_addr_const (file, x);
ba5e43aa 10839 if (small_data_operand (x, GET_MODE (x)))
8fbd2dc7
MM
10840 fprintf (file, "@%s(%s)", SMALL_DATA_RELOC,
10841 reg_names[SMALL_DATA_REG]);
37409796
NS
10842 else
10843 gcc_assert (!TARGET_TOC);
9878760c
RK
10844 }
10845 else if (GET_CODE (x) == PLUS && GET_CODE (XEXP (x, 1)) == REG)
10846 {
9024f4b8 10847 gcc_assert (REG_P (XEXP (x, 0)));
9878760c 10848 if (REGNO (XEXP (x, 0)) == 0)
4697a36c
MM
10849 fprintf (file, "%s,%s", reg_names[ REGNO (XEXP (x, 1)) ],
10850 reg_names[ REGNO (XEXP (x, 0)) ]);
9878760c 10851 else
4697a36c
MM
10852 fprintf (file, "%s,%s", reg_names[ REGNO (XEXP (x, 0)) ],
10853 reg_names[ REGNO (XEXP (x, 1)) ]);
9878760c
RK
10854 }
10855 else if (GET_CODE (x) == PLUS && GET_CODE (XEXP (x, 1)) == CONST_INT)
4a0a75dd
KG
10856 fprintf (file, HOST_WIDE_INT_PRINT_DEC "(%s)",
10857 INTVAL (XEXP (x, 1)), reg_names[ REGNO (XEXP (x, 0)) ]);
3cb999d8
DE
10858#if TARGET_ELF
10859 else if (GET_CODE (x) == LO_SUM && GET_CODE (XEXP (x, 0)) == REG
c4ad648e 10860 && CONSTANT_P (XEXP (x, 1)))
4697a36c
MM
10861 {
10862 output_addr_const (file, XEXP (x, 1));
10863 fprintf (file, "@l(%s)", reg_names[ REGNO (XEXP (x, 0)) ]);
10864 }
c859cda6
DJ
10865#endif
10866#if TARGET_MACHO
10867 else if (GET_CODE (x) == LO_SUM && GET_CODE (XEXP (x, 0)) == REG
c4ad648e 10868 && CONSTANT_P (XEXP (x, 1)))
c859cda6
DJ
10869 {
10870 fprintf (file, "lo16(");
10871 output_addr_const (file, XEXP (x, 1));
10872 fprintf (file, ")(%s)", reg_names[ REGNO (XEXP (x, 0)) ]);
10873 }
3cb999d8 10874#endif
4d588c14 10875 else if (legitimate_constant_pool_address_p (x))
9ebbca7d 10876 {
2bfcf297 10877 if (TARGET_AIX && (!TARGET_ELF || !TARGET_MINIMAL_TOC))
9ebbca7d 10878 {
2bfcf297
DB
10879 rtx contains_minus = XEXP (x, 1);
10880 rtx minus, symref;
10881 const char *name;
f676971a 10882
9ebbca7d 10883 /* Find the (minus (sym) (toc)) buried in X, and temporarily
a4f6c312 10884 turn it into (sym) for output_addr_const. */
9ebbca7d
GK
10885 while (GET_CODE (XEXP (contains_minus, 0)) != MINUS)
10886 contains_minus = XEXP (contains_minus, 0);
10887
2bfcf297
DB
10888 minus = XEXP (contains_minus, 0);
10889 symref = XEXP (minus, 0);
10890 XEXP (contains_minus, 0) = symref;
10891 if (TARGET_ELF)
10892 {
10893 char *newname;
10894
10895 name = XSTR (symref, 0);
10896 newname = alloca (strlen (name) + sizeof ("@toc"));
10897 strcpy (newname, name);
10898 strcat (newname, "@toc");
10899 XSTR (symref, 0) = newname;
10900 }
10901 output_addr_const (file, XEXP (x, 1));
10902 if (TARGET_ELF)
10903 XSTR (symref, 0) = name;
9ebbca7d
GK
10904 XEXP (contains_minus, 0) = minus;
10905 }
10906 else
10907 output_addr_const (file, XEXP (x, 1));
10908
10909 fprintf (file, "(%s)", reg_names[REGNO (XEXP (x, 0))]);
10910 }
9878760c 10911 else
37409796 10912 gcc_unreachable ();
9878760c
RK
10913}
10914\f
88cad84b 10915/* Target hook for assembling integer objects. The PowerPC version has
301d03af
RS
10916 to handle fixup entries for relocatable code if RELOCATABLE_NEEDS_FIXUP
10917 is defined. It also needs to handle DI-mode objects on 64-bit
10918 targets. */
10919
10920static bool
a2369ed3 10921rs6000_assemble_integer (rtx x, unsigned int size, int aligned_p)
301d03af 10922{
f4f4921e 10923#ifdef RELOCATABLE_NEEDS_FIXUP
301d03af 10924 /* Special handling for SI values. */
84dcde01 10925 if (RELOCATABLE_NEEDS_FIXUP && size == 4 && aligned_p)
301d03af 10926 {
301d03af 10927 static int recurse = 0;
f676971a 10928
301d03af
RS
10929 /* For -mrelocatable, we mark all addresses that need to be fixed up
10930 in the .fixup section. */
10931 if (TARGET_RELOCATABLE
d6b5193b
RS
10932 && in_section != toc_section
10933 && in_section != text_section
4325ca90 10934 && !unlikely_text_section_p (in_section)
301d03af
RS
10935 && !recurse
10936 && GET_CODE (x) != CONST_INT
10937 && GET_CODE (x) != CONST_DOUBLE
10938 && CONSTANT_P (x))
10939 {
10940 char buf[256];
10941
10942 recurse = 1;
10943 ASM_GENERATE_INTERNAL_LABEL (buf, "LCP", fixuplabelno);
10944 fixuplabelno++;
10945 ASM_OUTPUT_LABEL (asm_out_file, buf);
10946 fprintf (asm_out_file, "\t.long\t(");
10947 output_addr_const (asm_out_file, x);
10948 fprintf (asm_out_file, ")@fixup\n");
10949 fprintf (asm_out_file, "\t.section\t\".fixup\",\"aw\"\n");
10950 ASM_OUTPUT_ALIGN (asm_out_file, 2);
10951 fprintf (asm_out_file, "\t.long\t");
10952 assemble_name (asm_out_file, buf);
10953 fprintf (asm_out_file, "\n\t.previous\n");
10954 recurse = 0;
10955 return true;
10956 }
10957 /* Remove initial .'s to turn a -mcall-aixdesc function
10958 address into the address of the descriptor, not the function
10959 itself. */
10960 else if (GET_CODE (x) == SYMBOL_REF
10961 && XSTR (x, 0)[0] == '.'
10962 && DEFAULT_ABI == ABI_AIX)
10963 {
10964 const char *name = XSTR (x, 0);
10965 while (*name == '.')
10966 name++;
10967
10968 fprintf (asm_out_file, "\t.long\t%s\n", name);
10969 return true;
10970 }
10971 }
f4f4921e 10972#endif /* RELOCATABLE_NEEDS_FIXUP */
301d03af
RS
10973 return default_assemble_integer (x, size, aligned_p);
10974}
93638d7a
AM
10975
10976#ifdef HAVE_GAS_HIDDEN
10977/* Emit an assembler directive to set symbol visibility for DECL to
10978 VISIBILITY_TYPE. */
10979
5add3202 10980static void
a2369ed3 10981rs6000_assemble_visibility (tree decl, int vis)
93638d7a 10982{
93638d7a
AM
10983 /* Functions need to have their entry point symbol visibility set as
10984 well as their descriptor symbol visibility. */
85b776df
AM
10985 if (DEFAULT_ABI == ABI_AIX
10986 && DOT_SYMBOLS
10987 && TREE_CODE (decl) == FUNCTION_DECL)
93638d7a 10988 {
25fdb4dc 10989 static const char * const visibility_types[] = {
c4ad648e 10990 NULL, "internal", "hidden", "protected"
25fdb4dc
RH
10991 };
10992
10993 const char *name, *type;
93638d7a
AM
10994
10995 name = ((* targetm.strip_name_encoding)
10996 (IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl))));
25fdb4dc 10997 type = visibility_types[vis];
93638d7a 10998
25fdb4dc
RH
10999 fprintf (asm_out_file, "\t.%s\t%s\n", type, name);
11000 fprintf (asm_out_file, "\t.%s\t.%s\n", type, name);
93638d7a 11001 }
25fdb4dc
RH
11002 else
11003 default_assemble_visibility (decl, vis);
93638d7a
AM
11004}
11005#endif
301d03af 11006\f
39a10a29 11007enum rtx_code
a2369ed3 11008rs6000_reverse_condition (enum machine_mode mode, enum rtx_code code)
39a10a29
GK
11009{
11010 /* Reversal of FP compares takes care -- an ordered compare
11011 becomes an unordered compare and vice versa. */
f676971a 11012 if (mode == CCFPmode
bc9ec0e0
GK
11013 && (!flag_finite_math_only
11014 || code == UNLT || code == UNLE || code == UNGT || code == UNGE
11015 || code == UNEQ || code == LTGT))
bab6226b 11016 return reverse_condition_maybe_unordered (code);
39a10a29 11017 else
bab6226b 11018 return reverse_condition (code);
39a10a29
GK
11019}
11020
39a10a29
GK
11021/* Generate a compare for CODE. Return a brand-new rtx that
11022 represents the result of the compare. */
a4f6c312 11023
39a10a29 11024static rtx
a2369ed3 11025rs6000_generate_compare (enum rtx_code code)
39a10a29
GK
11026{
11027 enum machine_mode comp_mode;
11028 rtx compare_result;
11029
11030 if (rs6000_compare_fp_p)
11031 comp_mode = CCFPmode;
11032 else if (code == GTU || code == LTU
c4ad648e 11033 || code == GEU || code == LEU)
39a10a29 11034 comp_mode = CCUNSmode;
60934f9c
NS
11035 else if ((code == EQ || code == NE)
11036 && GET_CODE (rs6000_compare_op0) == SUBREG
11037 && GET_CODE (rs6000_compare_op1) == SUBREG
11038 && SUBREG_PROMOTED_UNSIGNED_P (rs6000_compare_op0)
11039 && SUBREG_PROMOTED_UNSIGNED_P (rs6000_compare_op1))
11040 /* These are unsigned values, perhaps there will be a later
11041 ordering compare that can be shared with this one.
11042 Unfortunately we cannot detect the signedness of the operands
11043 for non-subregs. */
11044 comp_mode = CCUNSmode;
39a10a29
GK
11045 else
11046 comp_mode = CCmode;
11047
11048 /* First, the compare. */
11049 compare_result = gen_reg_rtx (comp_mode);
a3170dc6
AH
11050
11051 /* SPE FP compare instructions on the GPRs. Yuck! */
993f19a8
AH
11052 if ((TARGET_E500 && !TARGET_FPRS && TARGET_HARD_FLOAT)
11053 && rs6000_compare_fp_p)
a3170dc6 11054 {
64022b5d 11055 rtx cmp, or_result, compare_result2;
4d4cbc0e
AH
11056 enum machine_mode op_mode = GET_MODE (rs6000_compare_op0);
11057
11058 if (op_mode == VOIDmode)
11059 op_mode = GET_MODE (rs6000_compare_op1);
a3170dc6 11060
423c1189
AH
11061 /* Note: The E500 comparison instructions set the GT bit (x +
11062 1), on success. This explains the mess. */
11063
a3170dc6
AH
11064 switch (code)
11065 {
423c1189 11066 case EQ: case UNEQ: case NE: case LTGT:
37409796
NS
11067 switch (op_mode)
11068 {
11069 case SFmode:
11070 cmp = flag_unsafe_math_optimizations
11071 ? gen_tstsfeq_gpr (compare_result, rs6000_compare_op0,
11072 rs6000_compare_op1)
11073 : gen_cmpsfeq_gpr (compare_result, rs6000_compare_op0,
11074 rs6000_compare_op1);
11075 break;
11076
11077 case DFmode:
11078 cmp = flag_unsafe_math_optimizations
11079 ? gen_tstdfeq_gpr (compare_result, rs6000_compare_op0,
11080 rs6000_compare_op1)
11081 : gen_cmpdfeq_gpr (compare_result, rs6000_compare_op0,
11082 rs6000_compare_op1);
11083 break;
11084
11085 default:
11086 gcc_unreachable ();
11087 }
a3170dc6 11088 break;
bb8df8a6 11089
423c1189 11090 case GT: case GTU: case UNGT: case UNGE: case GE: case GEU:
37409796
NS
11091 switch (op_mode)
11092 {
11093 case SFmode:
11094 cmp = flag_unsafe_math_optimizations
11095 ? gen_tstsfgt_gpr (compare_result, rs6000_compare_op0,
11096 rs6000_compare_op1)
11097 : gen_cmpsfgt_gpr (compare_result, rs6000_compare_op0,
11098 rs6000_compare_op1);
11099 break;
bb8df8a6 11100
37409796
NS
11101 case DFmode:
11102 cmp = flag_unsafe_math_optimizations
11103 ? gen_tstdfgt_gpr (compare_result, rs6000_compare_op0,
11104 rs6000_compare_op1)
11105 : gen_cmpdfgt_gpr (compare_result, rs6000_compare_op0,
11106 rs6000_compare_op1);
11107 break;
11108
11109 default:
11110 gcc_unreachable ();
11111 }
a3170dc6 11112 break;
bb8df8a6 11113
423c1189 11114 case LT: case LTU: case UNLT: case UNLE: case LE: case LEU:
37409796
NS
11115 switch (op_mode)
11116 {
11117 case SFmode:
11118 cmp = flag_unsafe_math_optimizations
11119 ? gen_tstsflt_gpr (compare_result, rs6000_compare_op0,
11120 rs6000_compare_op1)
11121 : gen_cmpsflt_gpr (compare_result, rs6000_compare_op0,
11122 rs6000_compare_op1);
11123 break;
bb8df8a6 11124
37409796
NS
11125 case DFmode:
11126 cmp = flag_unsafe_math_optimizations
11127 ? gen_tstdflt_gpr (compare_result, rs6000_compare_op0,
11128 rs6000_compare_op1)
11129 : gen_cmpdflt_gpr (compare_result, rs6000_compare_op0,
11130 rs6000_compare_op1);
11131 break;
11132
11133 default:
11134 gcc_unreachable ();
11135 }
a3170dc6 11136 break;
4d4cbc0e 11137 default:
37409796 11138 gcc_unreachable ();
a3170dc6
AH
11139 }
11140
11141 /* Synthesize LE and GE from LT/GT || EQ. */
11142 if (code == LE || code == GE || code == LEU || code == GEU)
11143 {
a3170dc6
AH
11144 emit_insn (cmp);
11145
11146 switch (code)
11147 {
11148 case LE: code = LT; break;
11149 case GE: code = GT; break;
11150 case LEU: code = LT; break;
11151 case GEU: code = GT; break;
37409796 11152 default: gcc_unreachable ();
a3170dc6
AH
11153 }
11154
a3170dc6
AH
11155 compare_result2 = gen_reg_rtx (CCFPmode);
11156
11157 /* Do the EQ. */
37409796
NS
11158 switch (op_mode)
11159 {
11160 case SFmode:
11161 cmp = flag_unsafe_math_optimizations
11162 ? gen_tstsfeq_gpr (compare_result2, rs6000_compare_op0,
11163 rs6000_compare_op1)
11164 : gen_cmpsfeq_gpr (compare_result2, rs6000_compare_op0,
11165 rs6000_compare_op1);
11166 break;
11167
11168 case DFmode:
11169 cmp = flag_unsafe_math_optimizations
11170 ? gen_tstdfeq_gpr (compare_result2, rs6000_compare_op0,
11171 rs6000_compare_op1)
11172 : gen_cmpdfeq_gpr (compare_result2, rs6000_compare_op0,
11173 rs6000_compare_op1);
11174 break;
11175
11176 default:
11177 gcc_unreachable ();
11178 }
a3170dc6
AH
11179 emit_insn (cmp);
11180
a3170dc6 11181 /* OR them together. */
64022b5d
AH
11182 or_result = gen_reg_rtx (CCFPmode);
11183 cmp = gen_e500_cr_ior_compare (or_result, compare_result,
11184 compare_result2);
a3170dc6
AH
11185 compare_result = or_result;
11186 code = EQ;
11187 }
11188 else
11189 {
a3170dc6 11190 if (code == NE || code == LTGT)
a3170dc6 11191 code = NE;
423c1189
AH
11192 else
11193 code = EQ;
a3170dc6
AH
11194 }
11195
11196 emit_insn (cmp);
11197 }
11198 else
de17c25f
DE
11199 {
11200 /* Generate XLC-compatible TFmode compare as PARALLEL with extra
11201 CLOBBERs to match cmptf_internal2 pattern. */
11202 if (comp_mode == CCFPmode && TARGET_XL_COMPAT
11203 && GET_MODE (rs6000_compare_op0) == TFmode
602ea4d3 11204 && !TARGET_IEEEQUAD
de17c25f
DE
11205 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128)
11206 emit_insn (gen_rtx_PARALLEL (VOIDmode,
11207 gen_rtvec (9,
11208 gen_rtx_SET (VOIDmode,
11209 compare_result,
11210 gen_rtx_COMPARE (comp_mode,
11211 rs6000_compare_op0,
11212 rs6000_compare_op1)),
11213 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
11214 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
11215 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
11216 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
11217 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
11218 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
11219 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
11220 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)))));
3aebbe5f
JJ
11221 else if (GET_CODE (rs6000_compare_op1) == UNSPEC
11222 && XINT (rs6000_compare_op1, 1) == UNSPEC_SP_TEST)
11223 {
11224 rtx op1 = XVECEXP (rs6000_compare_op1, 0, 0);
11225 comp_mode = CCEQmode;
11226 compare_result = gen_reg_rtx (CCEQmode);
11227 if (TARGET_64BIT)
11228 emit_insn (gen_stack_protect_testdi (compare_result,
11229 rs6000_compare_op0, op1));
11230 else
11231 emit_insn (gen_stack_protect_testsi (compare_result,
11232 rs6000_compare_op0, op1));
11233 }
de17c25f
DE
11234 else
11235 emit_insn (gen_rtx_SET (VOIDmode, compare_result,
11236 gen_rtx_COMPARE (comp_mode,
11237 rs6000_compare_op0,
11238 rs6000_compare_op1)));
11239 }
f676971a 11240
ca5adc63 11241 /* Some kinds of FP comparisons need an OR operation;
e7108df9 11242 under flag_finite_math_only we don't bother. */
39a10a29 11243 if (rs6000_compare_fp_p
e7108df9
DE
11244 && !flag_finite_math_only
11245 && !(TARGET_HARD_FLOAT && TARGET_E500 && !TARGET_FPRS)
39a10a29
GK
11246 && (code == LE || code == GE
11247 || code == UNEQ || code == LTGT
11248 || code == UNGT || code == UNLT))
11249 {
11250 enum rtx_code or1, or2;
11251 rtx or1_rtx, or2_rtx, compare2_rtx;
11252 rtx or_result = gen_reg_rtx (CCEQmode);
f676971a 11253
39a10a29
GK
11254 switch (code)
11255 {
11256 case LE: or1 = LT; or2 = EQ; break;
11257 case GE: or1 = GT; or2 = EQ; break;
11258 case UNEQ: or1 = UNORDERED; or2 = EQ; break;
11259 case LTGT: or1 = LT; or2 = GT; break;
11260 case UNGT: or1 = UNORDERED; or2 = GT; break;
11261 case UNLT: or1 = UNORDERED; or2 = LT; break;
37409796 11262 default: gcc_unreachable ();
39a10a29
GK
11263 }
11264 validate_condition_mode (or1, comp_mode);
11265 validate_condition_mode (or2, comp_mode);
1c563bed
KH
11266 or1_rtx = gen_rtx_fmt_ee (or1, SImode, compare_result, const0_rtx);
11267 or2_rtx = gen_rtx_fmt_ee (or2, SImode, compare_result, const0_rtx);
39a10a29
GK
11268 compare2_rtx = gen_rtx_COMPARE (CCEQmode,
11269 gen_rtx_IOR (SImode, or1_rtx, or2_rtx),
11270 const_true_rtx);
11271 emit_insn (gen_rtx_SET (VOIDmode, or_result, compare2_rtx));
11272
11273 compare_result = or_result;
11274 code = EQ;
11275 }
11276
11277 validate_condition_mode (code, GET_MODE (compare_result));
f676971a 11278
1c563bed 11279 return gen_rtx_fmt_ee (code, VOIDmode, compare_result, const0_rtx);
39a10a29
GK
11280}
11281
11282
11283/* Emit the RTL for an sCOND pattern. */
11284
11285void
a2369ed3 11286rs6000_emit_sCOND (enum rtx_code code, rtx result)
39a10a29
GK
11287{
11288 rtx condition_rtx;
11289 enum machine_mode op_mode;
b7053a3f 11290 enum rtx_code cond_code;
39a10a29
GK
11291
11292 condition_rtx = rs6000_generate_compare (code);
b7053a3f
GK
11293 cond_code = GET_CODE (condition_rtx);
11294
423c1189
AH
11295 if (TARGET_E500 && rs6000_compare_fp_p
11296 && !TARGET_FPRS && TARGET_HARD_FLOAT)
11297 {
11298 rtx t;
11299
11300 PUT_MODE (condition_rtx, SImode);
11301 t = XEXP (condition_rtx, 0);
11302
37409796 11303 gcc_assert (cond_code == NE || cond_code == EQ);
423c1189
AH
11304
11305 if (cond_code == NE)
64022b5d 11306 emit_insn (gen_e500_flip_gt_bit (t, t));
423c1189 11307
64022b5d 11308 emit_insn (gen_move_from_CR_gt_bit (result, t));
423c1189
AH
11309 return;
11310 }
11311
b7053a3f
GK
11312 if (cond_code == NE
11313 || cond_code == GE || cond_code == LE
11314 || cond_code == GEU || cond_code == LEU
11315 || cond_code == ORDERED || cond_code == UNGE || cond_code == UNLE)
11316 {
11317 rtx not_result = gen_reg_rtx (CCEQmode);
11318 rtx not_op, rev_cond_rtx;
11319 enum machine_mode cc_mode;
f676971a 11320
b7053a3f
GK
11321 cc_mode = GET_MODE (XEXP (condition_rtx, 0));
11322
1c563bed 11323 rev_cond_rtx = gen_rtx_fmt_ee (rs6000_reverse_condition (cc_mode, cond_code),
0f4c242b 11324 SImode, XEXP (condition_rtx, 0), const0_rtx);
b7053a3f
GK
11325 not_op = gen_rtx_COMPARE (CCEQmode, rev_cond_rtx, const0_rtx);
11326 emit_insn (gen_rtx_SET (VOIDmode, not_result, not_op));
11327 condition_rtx = gen_rtx_EQ (VOIDmode, not_result, const0_rtx);
11328 }
39a10a29
GK
11329
11330 op_mode = GET_MODE (rs6000_compare_op0);
11331 if (op_mode == VOIDmode)
11332 op_mode = GET_MODE (rs6000_compare_op1);
11333
11334 if (TARGET_POWERPC64 && (op_mode == DImode || rs6000_compare_fp_p))
11335 {
11336 PUT_MODE (condition_rtx, DImode);
11337 convert_move (result, condition_rtx, 0);
11338 }
11339 else
11340 {
11341 PUT_MODE (condition_rtx, SImode);
11342 emit_insn (gen_rtx_SET (VOIDmode, result, condition_rtx));
11343 }
11344}
11345
39a10a29
GK
11346/* Emit a branch of kind CODE to location LOC. */
11347
11348void
a2369ed3 11349rs6000_emit_cbranch (enum rtx_code code, rtx loc)
39a10a29
GK
11350{
11351 rtx condition_rtx, loc_ref;
11352
11353 condition_rtx = rs6000_generate_compare (code);
11354 loc_ref = gen_rtx_LABEL_REF (VOIDmode, loc);
11355 emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx,
11356 gen_rtx_IF_THEN_ELSE (VOIDmode, condition_rtx,
11357 loc_ref, pc_rtx)));
11358}
11359
12a4e8c5
GK
11360/* Return the string to output a conditional branch to LABEL, which is
11361 the operand number of the label, or -1 if the branch is really a
f676971a 11362 conditional return.
12a4e8c5
GK
11363
11364 OP is the conditional expression. XEXP (OP, 0) is assumed to be a
11365 condition code register and its mode specifies what kind of
11366 comparison we made.
11367
a0ab749a 11368 REVERSED is nonzero if we should reverse the sense of the comparison.
12a4e8c5
GK
11369
11370 INSN is the insn. */
11371
11372char *
a2369ed3 11373output_cbranch (rtx op, const char *label, int reversed, rtx insn)
12a4e8c5
GK
11374{
11375 static char string[64];
11376 enum rtx_code code = GET_CODE (op);
11377 rtx cc_reg = XEXP (op, 0);
11378 enum machine_mode mode = GET_MODE (cc_reg);
11379 int cc_regno = REGNO (cc_reg) - CR0_REGNO;
39a10a29 11380 int need_longbranch = label != NULL && get_attr_length (insn) == 8;
12a4e8c5
GK
11381 int really_reversed = reversed ^ need_longbranch;
11382 char *s = string;
11383 const char *ccode;
11384 const char *pred;
11385 rtx note;
11386
39a10a29
GK
11387 validate_condition_mode (code, mode);
11388
11389 /* Work out which way this really branches. We could use
11390 reverse_condition_maybe_unordered here always but this
11391 makes the resulting assembler clearer. */
12a4e8c5 11392 if (really_reversed)
de40e1df
DJ
11393 {
11394 /* Reversal of FP compares takes care -- an ordered compare
11395 becomes an unordered compare and vice versa. */
11396 if (mode == CCFPmode)
11397 code = reverse_condition_maybe_unordered (code);
11398 else
11399 code = reverse_condition (code);
11400 }
12a4e8c5 11401
993f19a8 11402 if ((TARGET_E500 && !TARGET_FPRS && TARGET_HARD_FLOAT) && mode == CCFPmode)
a3170dc6
AH
11403 {
11404 /* The efscmp/tst* instructions twiddle bit 2, which maps nicely
11405 to the GT bit. */
37409796
NS
11406 switch (code)
11407 {
11408 case EQ:
11409 /* Opposite of GT. */
11410 code = GT;
11411 break;
11412
11413 case NE:
11414 code = UNLE;
11415 break;
11416
11417 default:
11418 gcc_unreachable ();
11419 }
a3170dc6
AH
11420 }
11421
39a10a29 11422 switch (code)
12a4e8c5
GK
11423 {
11424 /* Not all of these are actually distinct opcodes, but
11425 we distinguish them for clarity of the resulting assembler. */
50a0b056
GK
11426 case NE: case LTGT:
11427 ccode = "ne"; break;
11428 case EQ: case UNEQ:
11429 ccode = "eq"; break;
f676971a 11430 case GE: case GEU:
50a0b056 11431 ccode = "ge"; break;
f676971a 11432 case GT: case GTU: case UNGT:
50a0b056 11433 ccode = "gt"; break;
f676971a 11434 case LE: case LEU:
50a0b056 11435 ccode = "le"; break;
f676971a 11436 case LT: case LTU: case UNLT:
50a0b056 11437 ccode = "lt"; break;
12a4e8c5
GK
11438 case UNORDERED: ccode = "un"; break;
11439 case ORDERED: ccode = "nu"; break;
11440 case UNGE: ccode = "nl"; break;
11441 case UNLE: ccode = "ng"; break;
11442 default:
37409796 11443 gcc_unreachable ();
12a4e8c5 11444 }
f676971a
EC
11445
11446 /* Maybe we have a guess as to how likely the branch is.
94a54f47 11447 The old mnemonics don't have a way to specify this information. */
f4857b9b 11448 pred = "";
12a4e8c5
GK
11449 note = find_reg_note (insn, REG_BR_PROB, NULL_RTX);
11450 if (note != NULL_RTX)
11451 {
11452 /* PROB is the difference from 50%. */
11453 int prob = INTVAL (XEXP (note, 0)) - REG_BR_PROB_BASE / 2;
f4857b9b
AM
11454
11455 /* Only hint for highly probable/improbable branches on newer
11456 cpus as static prediction overrides processor dynamic
11457 prediction. For older cpus we may as well always hint, but
11458 assume not taken for branches that are very close to 50% as a
11459 mispredicted taken branch is more expensive than a
f676971a 11460 mispredicted not-taken branch. */
ec507f2d 11461 if (rs6000_always_hint
f4857b9b
AM
11462 || abs (prob) > REG_BR_PROB_BASE / 100 * 48)
11463 {
11464 if (abs (prob) > REG_BR_PROB_BASE / 20
11465 && ((prob > 0) ^ need_longbranch))
c4ad648e 11466 pred = "+";
f4857b9b
AM
11467 else
11468 pred = "-";
11469 }
12a4e8c5 11470 }
12a4e8c5
GK
11471
11472 if (label == NULL)
94a54f47 11473 s += sprintf (s, "{b%sr|b%slr%s} ", ccode, ccode, pred);
12a4e8c5 11474 else
94a54f47 11475 s += sprintf (s, "{b%s|b%s%s} ", ccode, ccode, pred);
12a4e8c5 11476
37c67319 11477 /* We need to escape any '%' characters in the reg_names string.
a3c9585f 11478 Assume they'd only be the first character.... */
37c67319
GK
11479 if (reg_names[cc_regno + CR0_REGNO][0] == '%')
11480 *s++ = '%';
94a54f47 11481 s += sprintf (s, "%s", reg_names[cc_regno + CR0_REGNO]);
12a4e8c5
GK
11482
11483 if (label != NULL)
11484 {
11485 /* If the branch distance was too far, we may have to use an
11486 unconditional branch to go the distance. */
11487 if (need_longbranch)
44518ddd 11488 s += sprintf (s, ",$+8\n\tb %s", label);
12a4e8c5
GK
11489 else
11490 s += sprintf (s, ",%s", label);
11491 }
11492
11493 return string;
11494}
50a0b056 11495
64022b5d 11496/* Return the string to flip the GT bit on a CR. */
423c1189 11497char *
64022b5d 11498output_e500_flip_gt_bit (rtx dst, rtx src)
423c1189
AH
11499{
11500 static char string[64];
11501 int a, b;
11502
37409796
NS
11503 gcc_assert (GET_CODE (dst) == REG && CR_REGNO_P (REGNO (dst))
11504 && GET_CODE (src) == REG && CR_REGNO_P (REGNO (src)));
423c1189 11505
64022b5d
AH
11506 /* GT bit. */
11507 a = 4 * (REGNO (dst) - CR0_REGNO) + 1;
11508 b = 4 * (REGNO (src) - CR0_REGNO) + 1;
423c1189
AH
11509
11510 sprintf (string, "crnot %d,%d", a, b);
11511 return string;
11512}
11513
21213b4c
DP
11514/* Return insn index for the vector compare instruction for given CODE,
11515 and DEST_MODE, OP_MODE. Return INSN_NOT_AVAILABLE if valid insn is
11516 not available. */
11517
11518static int
94ff898d 11519get_vec_cmp_insn (enum rtx_code code,
21213b4c
DP
11520 enum machine_mode dest_mode,
11521 enum machine_mode op_mode)
11522{
11523 if (!TARGET_ALTIVEC)
11524 return INSN_NOT_AVAILABLE;
11525
11526 switch (code)
11527 {
11528 case EQ:
11529 if (dest_mode == V16QImode && op_mode == V16QImode)
11530 return UNSPEC_VCMPEQUB;
11531 if (dest_mode == V8HImode && op_mode == V8HImode)
11532 return UNSPEC_VCMPEQUH;
11533 if (dest_mode == V4SImode && op_mode == V4SImode)
11534 return UNSPEC_VCMPEQUW;
11535 if (dest_mode == V4SImode && op_mode == V4SFmode)
11536 return UNSPEC_VCMPEQFP;
11537 break;
11538 case GE:
11539 if (dest_mode == V4SImode && op_mode == V4SFmode)
11540 return UNSPEC_VCMPGEFP;
11541 case GT:
11542 if (dest_mode == V16QImode && op_mode == V16QImode)
11543 return UNSPEC_VCMPGTSB;
11544 if (dest_mode == V8HImode && op_mode == V8HImode)
11545 return UNSPEC_VCMPGTSH;
11546 if (dest_mode == V4SImode && op_mode == V4SImode)
11547 return UNSPEC_VCMPGTSW;
11548 if (dest_mode == V4SImode && op_mode == V4SFmode)
11549 return UNSPEC_VCMPGTFP;
11550 break;
11551 case GTU:
11552 if (dest_mode == V16QImode && op_mode == V16QImode)
11553 return UNSPEC_VCMPGTUB;
11554 if (dest_mode == V8HImode && op_mode == V8HImode)
11555 return UNSPEC_VCMPGTUH;
11556 if (dest_mode == V4SImode && op_mode == V4SImode)
11557 return UNSPEC_VCMPGTUW;
11558 break;
11559 default:
11560 break;
11561 }
11562 return INSN_NOT_AVAILABLE;
11563}
11564
11565/* Emit vector compare for operands OP0 and OP1 using code RCODE.
11566 DMODE is expected destination mode. This is a recursive function. */
11567
11568static rtx
11569rs6000_emit_vector_compare (enum rtx_code rcode,
11570 rtx op0, rtx op1,
11571 enum machine_mode dmode)
11572{
11573 int vec_cmp_insn;
11574 rtx mask;
11575 enum machine_mode dest_mode;
11576 enum machine_mode op_mode = GET_MODE (op1);
11577
37409796
NS
11578 gcc_assert (TARGET_ALTIVEC);
11579 gcc_assert (GET_MODE (op0) == GET_MODE (op1));
21213b4c
DP
11580
11581 /* Floating point vector compare instructions uses destination V4SImode.
11582 Move destination to appropriate mode later. */
11583 if (dmode == V4SFmode)
11584 dest_mode = V4SImode;
11585 else
11586 dest_mode = dmode;
11587
11588 mask = gen_reg_rtx (dest_mode);
11589 vec_cmp_insn = get_vec_cmp_insn (rcode, dest_mode, op_mode);
11590
11591 if (vec_cmp_insn == INSN_NOT_AVAILABLE)
11592 {
11593 bool swap_operands = false;
11594 bool try_again = false;
11595 switch (rcode)
11596 {
11597 case LT:
11598 rcode = GT;
11599 swap_operands = true;
11600 try_again = true;
11601 break;
11602 case LTU:
11603 rcode = GTU;
11604 swap_operands = true;
11605 try_again = true;
11606 break;
11607 case NE:
11608 /* Treat A != B as ~(A==B). */
11609 {
11610 enum insn_code nor_code;
11611 rtx eq_rtx = rs6000_emit_vector_compare (EQ, op0, op1,
11612 dest_mode);
94ff898d 11613
21213b4c 11614 nor_code = one_cmpl_optab->handlers[(int)dest_mode].insn_code;
37409796 11615 gcc_assert (nor_code != CODE_FOR_nothing);
21213b4c
DP
11616 emit_insn (GEN_FCN (nor_code) (mask, eq_rtx));
11617
11618 if (dmode != dest_mode)
11619 {
11620 rtx temp = gen_reg_rtx (dest_mode);
11621 convert_move (temp, mask, 0);
11622 return temp;
11623 }
11624 return mask;
11625 }
11626 break;
11627 case GE:
11628 case GEU:
11629 case LE:
11630 case LEU:
11631 /* Try GT/GTU/LT/LTU OR EQ */
11632 {
11633 rtx c_rtx, eq_rtx;
11634 enum insn_code ior_code;
11635 enum rtx_code new_code;
11636
37409796
NS
11637 switch (rcode)
11638 {
11639 case GE:
11640 new_code = GT;
11641 break;
11642
11643 case GEU:
11644 new_code = GTU;
11645 break;
11646
11647 case LE:
11648 new_code = LT;
11649 break;
11650
11651 case LEU:
11652 new_code = LTU;
11653 break;
11654
11655 default:
11656 gcc_unreachable ();
11657 }
21213b4c
DP
11658
11659 c_rtx = rs6000_emit_vector_compare (new_code,
11660 op0, op1, dest_mode);
11661 eq_rtx = rs6000_emit_vector_compare (EQ, op0, op1,
11662 dest_mode);
11663
11664 ior_code = ior_optab->handlers[(int)dest_mode].insn_code;
37409796 11665 gcc_assert (ior_code != CODE_FOR_nothing);
21213b4c
DP
11666 emit_insn (GEN_FCN (ior_code) (mask, c_rtx, eq_rtx));
11667 if (dmode != dest_mode)
11668 {
11669 rtx temp = gen_reg_rtx (dest_mode);
11670 convert_move (temp, mask, 0);
11671 return temp;
11672 }
11673 return mask;
11674 }
11675 break;
11676 default:
37409796 11677 gcc_unreachable ();
21213b4c
DP
11678 }
11679
11680 if (try_again)
11681 {
11682 vec_cmp_insn = get_vec_cmp_insn (rcode, dest_mode, op_mode);
37409796
NS
11683 /* You only get two chances. */
11684 gcc_assert (vec_cmp_insn != INSN_NOT_AVAILABLE);
21213b4c
DP
11685 }
11686
11687 if (swap_operands)
11688 {
11689 rtx tmp;
11690 tmp = op0;
11691 op0 = op1;
11692 op1 = tmp;
11693 }
11694 }
11695
915167f5
GK
11696 emit_insn (gen_rtx_SET (VOIDmode, mask,
11697 gen_rtx_UNSPEC (dest_mode,
11698 gen_rtvec (2, op0, op1),
11699 vec_cmp_insn)));
21213b4c
DP
11700 if (dmode != dest_mode)
11701 {
11702 rtx temp = gen_reg_rtx (dest_mode);
11703 convert_move (temp, mask, 0);
11704 return temp;
11705 }
11706 return mask;
11707}
11708
11709/* Return vector select instruction for MODE. Return INSN_NOT_AVAILABLE, if
11710 valid insn doesn exist for given mode. */
11711
11712static int
11713get_vsel_insn (enum machine_mode mode)
11714{
11715 switch (mode)
11716 {
11717 case V4SImode:
11718 return UNSPEC_VSEL4SI;
11719 break;
11720 case V4SFmode:
11721 return UNSPEC_VSEL4SF;
11722 break;
11723 case V8HImode:
11724 return UNSPEC_VSEL8HI;
11725 break;
11726 case V16QImode:
11727 return UNSPEC_VSEL16QI;
11728 break;
11729 default:
11730 return INSN_NOT_AVAILABLE;
11731 break;
11732 }
11733 return INSN_NOT_AVAILABLE;
11734}
11735
11736/* Emit vector select insn where DEST is destination using
11737 operands OP1, OP2 and MASK. */
11738
11739static void
11740rs6000_emit_vector_select (rtx dest, rtx op1, rtx op2, rtx mask)
11741{
11742 rtx t, temp;
11743 enum machine_mode dest_mode = GET_MODE (dest);
11744 int vsel_insn_index = get_vsel_insn (GET_MODE (dest));
11745
11746 temp = gen_reg_rtx (dest_mode);
94ff898d 11747
bb8df8a6 11748 /* For each vector element, select op1 when mask is 1 otherwise
19f1ebc7 11749 select op2. */
915167f5
GK
11750 t = gen_rtx_SET (VOIDmode, temp,
11751 gen_rtx_UNSPEC (dest_mode,
11752 gen_rtvec (3, op2, op1, mask),
11753 vsel_insn_index));
21213b4c
DP
11754 emit_insn (t);
11755 emit_move_insn (dest, temp);
11756 return;
11757}
11758
94ff898d 11759/* Emit vector conditional expression.
21213b4c
DP
11760 DEST is destination. OP1 and OP2 are two VEC_COND_EXPR operands.
11761 CC_OP0 and CC_OP1 are the two operands for the relation operation COND. */
11762
11763int
11764rs6000_emit_vector_cond_expr (rtx dest, rtx op1, rtx op2,
11765 rtx cond, rtx cc_op0, rtx cc_op1)
11766{
11767 enum machine_mode dest_mode = GET_MODE (dest);
11768 enum rtx_code rcode = GET_CODE (cond);
11769 rtx mask;
11770
11771 if (!TARGET_ALTIVEC)
11772 return 0;
11773
11774 /* Get the vector mask for the given relational operations. */
11775 mask = rs6000_emit_vector_compare (rcode, cc_op0, cc_op1, dest_mode);
11776
11777 rs6000_emit_vector_select (dest, op1, op2, mask);
11778
11779 return 1;
11780}
11781
50a0b056
GK
11782/* Emit a conditional move: move TRUE_COND to DEST if OP of the
11783 operands of the last comparison is nonzero/true, FALSE_COND if it
11784 is zero/false. Return 0 if the hardware has no such operation. */
a4f6c312 11785
50a0b056 11786int
a2369ed3 11787rs6000_emit_cmove (rtx dest, rtx op, rtx true_cond, rtx false_cond)
50a0b056
GK
11788{
11789 enum rtx_code code = GET_CODE (op);
11790 rtx op0 = rs6000_compare_op0;
11791 rtx op1 = rs6000_compare_op1;
11792 REAL_VALUE_TYPE c1;
3148ad6d
DJ
11793 enum machine_mode compare_mode = GET_MODE (op0);
11794 enum machine_mode result_mode = GET_MODE (dest);
50a0b056 11795 rtx temp;
add2402e 11796 bool is_against_zero;
50a0b056 11797
a3c9585f 11798 /* These modes should always match. */
a3170dc6
AH
11799 if (GET_MODE (op1) != compare_mode
11800 /* In the isel case however, we can use a compare immediate, so
11801 op1 may be a small constant. */
11802 && (!TARGET_ISEL || !short_cint_operand (op1, VOIDmode)))
3148ad6d 11803 return 0;
178c3eff 11804 if (GET_MODE (true_cond) != result_mode)
3148ad6d 11805 return 0;
178c3eff 11806 if (GET_MODE (false_cond) != result_mode)
3148ad6d
DJ
11807 return 0;
11808
50a0b056 11809 /* First, work out if the hardware can do this at all, or
a3c9585f 11810 if it's too slow.... */
50a0b056 11811 if (! rs6000_compare_fp_p)
a3170dc6
AH
11812 {
11813 if (TARGET_ISEL)
11814 return rs6000_emit_int_cmove (dest, op, true_cond, false_cond);
11815 return 0;
11816 }
fef98bf2 11817 else if (TARGET_E500 && TARGET_HARD_FLOAT && !TARGET_FPRS
ebb109ad 11818 && SCALAR_FLOAT_MODE_P (compare_mode))
fef98bf2 11819 return 0;
50a0b056 11820
add2402e 11821 is_against_zero = op1 == CONST0_RTX (compare_mode);
94ff898d 11822
add2402e
GK
11823 /* A floating-point subtract might overflow, underflow, or produce
11824 an inexact result, thus changing the floating-point flags, so it
11825 can't be generated if we care about that. It's safe if one side
11826 of the construct is zero, since then no subtract will be
11827 generated. */
ebb109ad 11828 if (SCALAR_FLOAT_MODE_P (compare_mode)
add2402e
GK
11829 && flag_trapping_math && ! is_against_zero)
11830 return 0;
11831
50a0b056
GK
11832 /* Eliminate half of the comparisons by switching operands, this
11833 makes the remaining code simpler. */
11834 if (code == UNLT || code == UNGT || code == UNORDERED || code == NE
bc9ec0e0 11835 || code == LTGT || code == LT || code == UNLE)
50a0b056
GK
11836 {
11837 code = reverse_condition_maybe_unordered (code);
11838 temp = true_cond;
11839 true_cond = false_cond;
11840 false_cond = temp;
11841 }
11842
11843 /* UNEQ and LTGT take four instructions for a comparison with zero,
11844 it'll probably be faster to use a branch here too. */
bc9ec0e0 11845 if (code == UNEQ && HONOR_NANS (compare_mode))
50a0b056 11846 return 0;
f676971a 11847
50a0b056
GK
11848 if (GET_CODE (op1) == CONST_DOUBLE)
11849 REAL_VALUE_FROM_CONST_DOUBLE (c1, op1);
f676971a 11850
b6d08ca1 11851 /* We're going to try to implement comparisons by performing
50a0b056
GK
11852 a subtract, then comparing against zero. Unfortunately,
11853 Inf - Inf is NaN which is not zero, and so if we don't
27d30956 11854 know that the operand is finite and the comparison
50a0b056 11855 would treat EQ different to UNORDERED, we can't do it. */
bc9ec0e0 11856 if (HONOR_INFINITIES (compare_mode)
50a0b056 11857 && code != GT && code != UNGE
045572c7 11858 && (GET_CODE (op1) != CONST_DOUBLE || real_isinf (&c1))
50a0b056
GK
11859 /* Constructs of the form (a OP b ? a : b) are safe. */
11860 && ((! rtx_equal_p (op0, false_cond) && ! rtx_equal_p (op1, false_cond))
f676971a 11861 || (! rtx_equal_p (op0, true_cond)
50a0b056
GK
11862 && ! rtx_equal_p (op1, true_cond))))
11863 return 0;
add2402e 11864
50a0b056
GK
11865 /* At this point we know we can use fsel. */
11866
11867 /* Reduce the comparison to a comparison against zero. */
add2402e
GK
11868 if (! is_against_zero)
11869 {
11870 temp = gen_reg_rtx (compare_mode);
11871 emit_insn (gen_rtx_SET (VOIDmode, temp,
11872 gen_rtx_MINUS (compare_mode, op0, op1)));
11873 op0 = temp;
11874 op1 = CONST0_RTX (compare_mode);
11875 }
50a0b056
GK
11876
11877 /* If we don't care about NaNs we can reduce some of the comparisons
11878 down to faster ones. */
bc9ec0e0 11879 if (! HONOR_NANS (compare_mode))
50a0b056
GK
11880 switch (code)
11881 {
11882 case GT:
11883 code = LE;
11884 temp = true_cond;
11885 true_cond = false_cond;
11886 false_cond = temp;
11887 break;
11888 case UNGE:
11889 code = GE;
11890 break;
11891 case UNEQ:
11892 code = EQ;
11893 break;
11894 default:
11895 break;
11896 }
11897
11898 /* Now, reduce everything down to a GE. */
11899 switch (code)
11900 {
11901 case GE:
11902 break;
11903
11904 case LE:
3148ad6d
DJ
11905 temp = gen_reg_rtx (compare_mode);
11906 emit_insn (gen_rtx_SET (VOIDmode, temp, gen_rtx_NEG (compare_mode, op0)));
50a0b056
GK
11907 op0 = temp;
11908 break;
11909
11910 case ORDERED:
3148ad6d
DJ
11911 temp = gen_reg_rtx (compare_mode);
11912 emit_insn (gen_rtx_SET (VOIDmode, temp, gen_rtx_ABS (compare_mode, op0)));
50a0b056
GK
11913 op0 = temp;
11914 break;
11915
11916 case EQ:
3148ad6d 11917 temp = gen_reg_rtx (compare_mode);
f676971a 11918 emit_insn (gen_rtx_SET (VOIDmode, temp,
3148ad6d
DJ
11919 gen_rtx_NEG (compare_mode,
11920 gen_rtx_ABS (compare_mode, op0))));
50a0b056
GK
11921 op0 = temp;
11922 break;
11923
11924 case UNGE:
bc9ec0e0 11925 /* a UNGE 0 <-> (a GE 0 || -a UNLT 0) */
3148ad6d 11926 temp = gen_reg_rtx (result_mode);
50a0b056 11927 emit_insn (gen_rtx_SET (VOIDmode, temp,
3148ad6d 11928 gen_rtx_IF_THEN_ELSE (result_mode,
50a0b056
GK
11929 gen_rtx_GE (VOIDmode,
11930 op0, op1),
11931 true_cond, false_cond)));
bc9ec0e0
GK
11932 false_cond = true_cond;
11933 true_cond = temp;
50a0b056 11934
3148ad6d
DJ
11935 temp = gen_reg_rtx (compare_mode);
11936 emit_insn (gen_rtx_SET (VOIDmode, temp, gen_rtx_NEG (compare_mode, op0)));
50a0b056
GK
11937 op0 = temp;
11938 break;
11939
11940 case GT:
bc9ec0e0 11941 /* a GT 0 <-> (a GE 0 && -a UNLT 0) */
3148ad6d 11942 temp = gen_reg_rtx (result_mode);
50a0b056 11943 emit_insn (gen_rtx_SET (VOIDmode, temp,
f676971a 11944 gen_rtx_IF_THEN_ELSE (result_mode,
50a0b056
GK
11945 gen_rtx_GE (VOIDmode,
11946 op0, op1),
11947 true_cond, false_cond)));
bc9ec0e0
GK
11948 true_cond = false_cond;
11949 false_cond = temp;
50a0b056 11950
3148ad6d
DJ
11951 temp = gen_reg_rtx (compare_mode);
11952 emit_insn (gen_rtx_SET (VOIDmode, temp, gen_rtx_NEG (compare_mode, op0)));
50a0b056
GK
11953 op0 = temp;
11954 break;
11955
11956 default:
37409796 11957 gcc_unreachable ();
50a0b056
GK
11958 }
11959
11960 emit_insn (gen_rtx_SET (VOIDmode, dest,
3148ad6d 11961 gen_rtx_IF_THEN_ELSE (result_mode,
50a0b056
GK
11962 gen_rtx_GE (VOIDmode,
11963 op0, op1),
11964 true_cond, false_cond)));
11965 return 1;
11966}
11967
a3170dc6
AH
11968/* Same as above, but for ints (isel). */
11969
11970static int
a2369ed3 11971rs6000_emit_int_cmove (rtx dest, rtx op, rtx true_cond, rtx false_cond)
a3170dc6
AH
11972{
11973 rtx condition_rtx, cr;
11974
11975 /* All isel implementations thus far are 32-bits. */
11976 if (GET_MODE (rs6000_compare_op0) != SImode)
11977 return 0;
11978
11979 /* We still have to do the compare, because isel doesn't do a
11980 compare, it just looks at the CRx bits set by a previous compare
11981 instruction. */
11982 condition_rtx = rs6000_generate_compare (GET_CODE (op));
11983 cr = XEXP (condition_rtx, 0);
11984
11985 if (GET_MODE (cr) == CCmode)
11986 emit_insn (gen_isel_signed (dest, condition_rtx,
11987 true_cond, false_cond, cr));
11988 else
11989 emit_insn (gen_isel_unsigned (dest, condition_rtx,
11990 true_cond, false_cond, cr));
11991
11992 return 1;
11993}
11994
11995const char *
a2369ed3 11996output_isel (rtx *operands)
a3170dc6
AH
11997{
11998 enum rtx_code code;
11999
12000 code = GET_CODE (operands[1]);
12001 if (code == GE || code == GEU || code == LE || code == LEU || code == NE)
12002 {
12003 PUT_CODE (operands[1], reverse_condition (code));
12004 return "isel %0,%3,%2,%j1";
12005 }
12006 else
12007 return "isel %0,%2,%3,%j1";
12008}
12009
50a0b056 12010void
a2369ed3 12011rs6000_emit_minmax (rtx dest, enum rtx_code code, rtx op0, rtx op1)
50a0b056
GK
12012{
12013 enum machine_mode mode = GET_MODE (op0);
5dc8d536 12014 enum rtx_code c;
50a0b056 12015 rtx target;
5dc8d536
AH
12016
12017 if (code == SMAX || code == SMIN)
12018 c = GE;
12019 else
12020 c = GEU;
12021
50a0b056 12022 if (code == SMAX || code == UMAX)
f676971a 12023 target = emit_conditional_move (dest, c, op0, op1, mode,
50a0b056
GK
12024 op0, op1, mode, 0);
12025 else
f676971a 12026 target = emit_conditional_move (dest, c, op0, op1, mode,
50a0b056 12027 op1, op0, mode, 0);
37409796 12028 gcc_assert (target);
50a0b056
GK
12029 if (target != dest)
12030 emit_move_insn (dest, target);
12031}
46c07df8 12032
915167f5
GK
12033/* Emit instructions to perform a load-reserved/store-conditional operation.
12034 The operation performed is an atomic
12035 (set M (CODE:MODE M OP))
12036 If not NULL, BEFORE is atomically set to M before the operation, and
12037 AFTER is set to M after the operation (that is, (CODE:MODE M OP)).
bb8df8a6 12038 If SYNC_P then a memory barrier is emitted before the operation.
915167f5
GK
12039 Either OP or M may be wrapped in a NOT operation. */
12040
12041void
12042rs6000_emit_sync (enum rtx_code code, enum machine_mode mode,
12043 rtx m, rtx op, rtx before_param, rtx after_param,
12044 bool sync_p)
12045{
12046 enum machine_mode used_mode;
12047 rtx the_op, set_before, set_after, set_atomic, cc_scratch, before, after;
12048 rtx used_m;
12049 rtvec vec;
12050 HOST_WIDE_INT imask = GET_MODE_MASK (mode);
12051 rtx shift = NULL_RTX;
bb8df8a6 12052
915167f5
GK
12053 if (sync_p)
12054 emit_insn (gen_memory_barrier ());
bb8df8a6 12055
915167f5
GK
12056 if (GET_CODE (m) == NOT)
12057 used_m = XEXP (m, 0);
12058 else
12059 used_m = m;
12060
12061 /* If this is smaller than SImode, we'll have to use SImode with
12062 adjustments. */
12063 if (mode == QImode || mode == HImode)
12064 {
12065 rtx newop, oldop;
12066
12067 if (MEM_ALIGN (used_m) >= 32)
12068 {
12069 int ishift = 0;
12070 if (BYTES_BIG_ENDIAN)
12071 ishift = GET_MODE_BITSIZE (SImode) - GET_MODE_BITSIZE (mode);
bb8df8a6 12072
915167f5
GK
12073 shift = GEN_INT (ishift);
12074 }
12075 else
12076 {
12077 rtx addrSI, aligned_addr;
a9c9d3fa 12078 int shift_mask = mode == QImode ? 0x18 : 0x10;
bb8df8a6 12079
915167f5
GK
12080 addrSI = force_reg (SImode, gen_lowpart_common (SImode,
12081 XEXP (used_m, 0)));
12082 shift = gen_reg_rtx (SImode);
12083
12084 emit_insn (gen_rlwinm (shift, addrSI, GEN_INT (3),
a9c9d3fa
GK
12085 GEN_INT (shift_mask)));
12086 emit_insn (gen_xorsi3 (shift, shift, GEN_INT (shift_mask)));
915167f5
GK
12087
12088 aligned_addr = expand_binop (Pmode, and_optab,
12089 XEXP (used_m, 0),
12090 GEN_INT (-4), NULL_RTX,
12091 1, OPTAB_LIB_WIDEN);
12092 used_m = change_address (used_m, SImode, aligned_addr);
12093 set_mem_align (used_m, 32);
12094 /* It's safe to keep the old alias set of USED_M, because
12095 the operation is atomic and only affects the original
12096 USED_M. */
12097 if (GET_CODE (m) == NOT)
12098 m = gen_rtx_NOT (SImode, used_m);
12099 else
12100 m = used_m;
12101 }
12102
12103 if (GET_CODE (op) == NOT)
12104 {
12105 oldop = lowpart_subreg (SImode, XEXP (op, 0), mode);
12106 oldop = gen_rtx_NOT (SImode, oldop);
12107 }
12108 else
12109 oldop = lowpart_subreg (SImode, op, mode);
9f0076e5 12110
915167f5
GK
12111 switch (code)
12112 {
12113 case IOR:
12114 case XOR:
12115 newop = expand_binop (SImode, and_optab,
12116 oldop, GEN_INT (imask), NULL_RTX,
12117 1, OPTAB_LIB_WIDEN);
12118 emit_insn (gen_ashlsi3 (newop, newop, shift));
12119 break;
12120
12121 case AND:
12122 newop = expand_binop (SImode, ior_optab,
12123 oldop, GEN_INT (~imask), NULL_RTX,
12124 1, OPTAB_LIB_WIDEN);
a9c9d3fa 12125 emit_insn (gen_rotlsi3 (newop, newop, shift));
915167f5
GK
12126 break;
12127
12128 case PLUS:
9f0076e5 12129 case MINUS:
915167f5
GK
12130 {
12131 rtx mask;
bb8df8a6 12132
915167f5
GK
12133 newop = expand_binop (SImode, and_optab,
12134 oldop, GEN_INT (imask), NULL_RTX,
12135 1, OPTAB_LIB_WIDEN);
12136 emit_insn (gen_ashlsi3 (newop, newop, shift));
12137
12138 mask = gen_reg_rtx (SImode);
12139 emit_move_insn (mask, GEN_INT (imask));
12140 emit_insn (gen_ashlsi3 (mask, mask, shift));
12141
9f0076e5
DE
12142 if (code == PLUS)
12143 newop = gen_rtx_PLUS (SImode, m, newop);
12144 else
12145 newop = gen_rtx_MINUS (SImode, m, newop);
12146 newop = gen_rtx_AND (SImode, newop, mask);
915167f5
GK
12147 newop = gen_rtx_IOR (SImode, newop,
12148 gen_rtx_AND (SImode,
12149 gen_rtx_NOT (SImode, mask),
12150 m));
12151 break;
12152 }
12153
12154 default:
12155 gcc_unreachable ();
12156 }
12157
a9c9d3fa
GK
12158 if (GET_CODE (m) == NOT)
12159 {
12160 rtx mask, xorm;
12161
12162 mask = gen_reg_rtx (SImode);
12163 emit_move_insn (mask, GEN_INT (imask));
12164 emit_insn (gen_ashlsi3 (mask, mask, shift));
12165
12166 xorm = gen_rtx_XOR (SImode, used_m, mask);
12167 /* Depending on the value of 'op', the XOR or the operation might
12168 be able to be simplified away. */
12169 newop = simplify_gen_binary (code, SImode, xorm, newop);
12170 }
915167f5
GK
12171 op = newop;
12172 used_mode = SImode;
12173 before = gen_reg_rtx (used_mode);
12174 after = gen_reg_rtx (used_mode);
12175 }
12176 else
12177 {
12178 used_mode = mode;
12179 before = before_param;
12180 after = after_param;
12181
12182 if (before == NULL_RTX)
12183 before = gen_reg_rtx (used_mode);
12184 if (after == NULL_RTX)
12185 after = gen_reg_rtx (used_mode);
12186 }
bb8df8a6 12187
9f0076e5
DE
12188 if ((code == PLUS || code == MINUS || GET_CODE (m) == NOT)
12189 && used_mode != mode)
915167f5
GK
12190 the_op = op; /* Computed above. */
12191 else if (GET_CODE (op) == NOT && GET_CODE (m) != NOT)
12192 the_op = gen_rtx_fmt_ee (code, used_mode, op, m);
12193 else
12194 the_op = gen_rtx_fmt_ee (code, used_mode, m, op);
12195
12196 set_after = gen_rtx_SET (VOIDmode, after, the_op);
12197 set_before = gen_rtx_SET (VOIDmode, before, used_m);
12198 set_atomic = gen_rtx_SET (VOIDmode, used_m,
9f0076e5
DE
12199 gen_rtx_UNSPEC (used_mode,
12200 gen_rtvec (1, the_op),
12201 UNSPEC_SYNC_OP));
915167f5
GK
12202 cc_scratch = gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (CCmode));
12203
9f0076e5 12204 if ((code == PLUS || code == MINUS) && used_mode != mode)
915167f5
GK
12205 vec = gen_rtvec (5, set_after, set_before, set_atomic, cc_scratch,
12206 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (SImode)));
12207 else
12208 vec = gen_rtvec (4, set_after, set_before, set_atomic, cc_scratch);
12209 emit_insn (gen_rtx_PARALLEL (VOIDmode, vec));
12210
12211 /* Shift and mask the return values properly. */
12212 if (used_mode != mode && before_param)
12213 {
12214 emit_insn (gen_lshrsi3 (before, before, shift));
12215 convert_move (before_param, before, 1);
12216 }
12217
12218 if (used_mode != mode && after_param)
12219 {
12220 emit_insn (gen_lshrsi3 (after, after, shift));
12221 convert_move (after_param, after, 1);
12222 }
12223
12224 /* The previous sequence will end with a branch that's dependent on
12225 the conditional store, so placing an isync will ensure that no
12226 other instructions (especially, no load or store instructions)
12227 can start before the atomic operation completes. */
12228 if (sync_p)
12229 emit_insn (gen_isync ());
12230}
12231
b52110d4
DE
12232/* A subroutine of the atomic operation splitters. Jump to LABEL if
12233 COND is true. Mark the jump as unlikely to be taken. */
12234
12235static void
12236emit_unlikely_jump (rtx cond, rtx label)
12237{
12238 rtx very_unlikely = GEN_INT (REG_BR_PROB_BASE / 100 - 1);
12239 rtx x;
12240
12241 x = gen_rtx_IF_THEN_ELSE (VOIDmode, cond, label, pc_rtx);
12242 x = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, x));
12243 REG_NOTES (x) = gen_rtx_EXPR_LIST (REG_BR_PROB, very_unlikely, NULL_RTX);
12244}
12245
12246/* A subroutine of the atomic operation splitters. Emit a load-locked
12247 instruction in MODE. */
12248
12249static void
12250emit_load_locked (enum machine_mode mode, rtx reg, rtx mem)
12251{
12252 rtx (*fn) (rtx, rtx) = NULL;
12253 if (mode == SImode)
12254 fn = gen_load_locked_si;
12255 else if (mode == DImode)
12256 fn = gen_load_locked_di;
12257 emit_insn (fn (reg, mem));
12258}
12259
12260/* A subroutine of the atomic operation splitters. Emit a store-conditional
12261 instruction in MODE. */
12262
12263static void
12264emit_store_conditional (enum machine_mode mode, rtx res, rtx mem, rtx val)
12265{
12266 rtx (*fn) (rtx, rtx, rtx) = NULL;
12267 if (mode == SImode)
12268 fn = gen_store_conditional_si;
12269 else if (mode == DImode)
12270 fn = gen_store_conditional_di;
12271
9f0076e5 12272 /* Emit sync before stwcx. to address PPC405 Erratum. */
b52110d4
DE
12273 if (PPC405_ERRATUM77)
12274 emit_insn (gen_memory_barrier ());
12275
12276 emit_insn (fn (res, mem, val));
12277}
12278
9f0076e5 12279/* Expand an an atomic fetch-and-operate pattern. CODE is the binary operation
bb8df8a6 12280 to perform. MEM is the memory on which to operate. VAL is the second
9f0076e5
DE
12281 operand of the binary operator. BEFORE and AFTER are optional locations to
12282 return the value of MEM either before of after the operation. SCRATCH is
12283 a scratch register. */
12284
12285void
12286rs6000_split_atomic_op (enum rtx_code code, rtx mem, rtx val,
12287 rtx before, rtx after, rtx scratch)
12288{
12289 enum machine_mode mode = GET_MODE (mem);
12290 rtx label, x, cond = gen_rtx_REG (CCmode, CR0_REGNO);
12291
12292 emit_insn (gen_memory_barrier ());
12293
12294 label = gen_label_rtx ();
12295 emit_label (label);
12296 label = gen_rtx_LABEL_REF (VOIDmode, label);
12297
12298 if (before == NULL_RTX)
12299 before = scratch;
12300 emit_load_locked (mode, before, mem);
12301
12302 if (code == NOT)
12303 x = gen_rtx_AND (mode, gen_rtx_NOT (mode, before), val);
12304 else if (code == AND)
12305 x = gen_rtx_UNSPEC (mode, gen_rtvec (2, before, val), UNSPEC_AND);
12306 else
12307 x = gen_rtx_fmt_ee (code, mode, before, val);
12308
12309 if (after != NULL_RTX)
12310 emit_insn (gen_rtx_SET (VOIDmode, after, copy_rtx (x)));
12311 emit_insn (gen_rtx_SET (VOIDmode, scratch, x));
12312
12313 emit_store_conditional (mode, cond, mem, scratch);
12314
12315 x = gen_rtx_NE (VOIDmode, cond, const0_rtx);
12316 emit_unlikely_jump (x, label);
12317
12318 emit_insn (gen_isync ());
12319}
12320
b52110d4
DE
12321/* Expand an atomic compare and swap operation. MEM is the memory on which
12322 to operate. OLDVAL is the old value to be compared. NEWVAL is the new
12323 value to be stored. SCRATCH is a scratch GPR. */
12324
12325void
12326rs6000_split_compare_and_swap (rtx retval, rtx mem, rtx oldval, rtx newval,
12327 rtx scratch)
12328{
12329 enum machine_mode mode = GET_MODE (mem);
12330 rtx label1, label2, x, cond = gen_rtx_REG (CCmode, CR0_REGNO);
12331
12332 emit_insn (gen_memory_barrier ());
12333
12334 label1 = gen_rtx_LABEL_REF (VOIDmode, gen_label_rtx ());
12335 label2 = gen_rtx_LABEL_REF (VOIDmode, gen_label_rtx ());
12336 emit_label (XEXP (label1, 0));
12337
12338 emit_load_locked (mode, retval, mem);
12339
12340 x = gen_rtx_COMPARE (CCmode, retval, oldval);
12341 emit_insn (gen_rtx_SET (VOIDmode, cond, x));
12342
12343 x = gen_rtx_NE (VOIDmode, cond, const0_rtx);
12344 emit_unlikely_jump (x, label2);
12345
12346 emit_move_insn (scratch, newval);
12347 emit_store_conditional (mode, cond, mem, scratch);
12348
12349 x = gen_rtx_NE (VOIDmode, cond, const0_rtx);
12350 emit_unlikely_jump (x, label1);
12351
12352 emit_insn (gen_isync ());
12353 emit_label (XEXP (label2, 0));
12354}
12355
12356/* Expand an atomic test and set operation. MEM is the memory on which
12357 to operate. VAL is the value set. SCRATCH is a scratch GPR. */
12358
12359void
12360rs6000_split_lock_test_and_set (rtx retval, rtx mem, rtx val, rtx scratch)
12361{
12362 enum machine_mode mode = GET_MODE (mem);
12363 rtx label, x, cond = gen_rtx_REG (CCmode, CR0_REGNO);
12364
12365 emit_insn (gen_memory_barrier ());
12366
12367 label = gen_rtx_LABEL_REF (VOIDmode, gen_label_rtx ());
12368 emit_label (XEXP (label, 0));
12369
12370 emit_load_locked (mode, retval, mem);
12371 emit_move_insn (scratch, val);
12372 emit_store_conditional (mode, cond, mem, scratch);
12373
12374 x = gen_rtx_NE (VOIDmode, cond, const0_rtx);
12375 emit_unlikely_jump (x, label);
12376
12377 emit_insn (gen_isync ());
12378}
12379
9fc75b97
DE
12380void
12381rs6000_expand_compare_and_swapqhi (rtx dst, rtx mem, rtx oldval, rtx newval)
12382{
12383 enum machine_mode mode = GET_MODE (mem);
12384 rtx addrSI, align, wdst, shift, mask;
12385 HOST_WIDE_INT shift_mask = mode == QImode ? 0x18 : 0x10;
12386 HOST_WIDE_INT imask = GET_MODE_MASK (mode);
12387
12388 /* Shift amount for subword relative to aligned word. */
12389 addrSI = force_reg (SImode, gen_lowpart_common (SImode, XEXP (mem, 0)));
12390 shift = gen_reg_rtx (SImode);
12391 emit_insn (gen_rlwinm (shift, addrSI, GEN_INT (3),
12392 GEN_INT (shift_mask)));
12393 emit_insn (gen_xorsi3 (shift, shift, GEN_INT (shift_mask)));
12394
12395 /* Shift and mask old value into position within word. */
12396 oldval = convert_modes (SImode, mode, oldval, 1);
12397 oldval = expand_binop (SImode, and_optab,
12398 oldval, GEN_INT (imask), NULL_RTX,
12399 1, OPTAB_LIB_WIDEN);
12400 emit_insn (gen_ashlsi3 (oldval, oldval, shift));
12401
12402 /* Shift and mask new value into position within word. */
12403 newval = convert_modes (SImode, mode, newval, 1);
12404 newval = expand_binop (SImode, and_optab,
12405 newval, GEN_INT (imask), NULL_RTX,
12406 1, OPTAB_LIB_WIDEN);
12407 emit_insn (gen_ashlsi3 (newval, newval, shift));
12408
12409 /* Mask for insertion. */
12410 mask = gen_reg_rtx (SImode);
12411 emit_move_insn (mask, GEN_INT (imask));
12412 emit_insn (gen_ashlsi3 (mask, mask, shift));
12413
12414 /* Address of aligned word containing subword. */
12415 align = expand_binop (Pmode, and_optab, XEXP (mem, 0), GEN_INT (-4),
12416 NULL_RTX, 1, OPTAB_LIB_WIDEN);
12417 mem = change_address (mem, SImode, align);
12418 set_mem_align (mem, 32);
12419 MEM_VOLATILE_P (mem) = 1;
12420
12421 wdst = gen_reg_rtx (SImode);
12422 emit_insn (gen_sync_compare_and_swapqhi_internal (wdst, mask,
12423 oldval, newval, mem));
12424
12425 emit_move_insn (dst, gen_lowpart (mode, wdst));
12426}
12427
12428void
12429rs6000_split_compare_and_swapqhi (rtx dest, rtx mask,
12430 rtx oldval, rtx newval, rtx mem,
12431 rtx scratch)
12432{
12433 rtx label1, label2, x, cond = gen_rtx_REG (CCmode, CR0_REGNO);
12434
12435 emit_insn (gen_memory_barrier ());
12436 label1 = gen_rtx_LABEL_REF (VOIDmode, gen_label_rtx ());
12437 label2 = gen_rtx_LABEL_REF (VOIDmode, gen_label_rtx ());
12438 emit_label (XEXP (label1, 0));
12439
12440 emit_load_locked (SImode, scratch, mem);
12441
12442 /* Mask subword within loaded value for comparison with oldval.
12443 Use UNSPEC_AND to avoid clobber.*/
12444 emit_insn (gen_rtx_SET (SImode, dest,
12445 gen_rtx_UNSPEC (SImode,
12446 gen_rtvec (2, scratch, mask),
12447 UNSPEC_AND)));
12448
12449 x = gen_rtx_COMPARE (CCmode, dest, oldval);
12450 emit_insn (gen_rtx_SET (VOIDmode, cond, x));
12451
12452 x = gen_rtx_NE (VOIDmode, cond, const0_rtx);
12453 emit_unlikely_jump (x, label2);
12454
12455 /* Clear subword within loaded value for insertion of new value. */
12456 emit_insn (gen_rtx_SET (SImode, scratch,
12457 gen_rtx_AND (SImode,
12458 gen_rtx_NOT (SImode, mask), scratch)));
12459 emit_insn (gen_iorsi3 (scratch, scratch, newval));
12460 emit_store_conditional (SImode, cond, mem, scratch);
12461
12462 x = gen_rtx_NE (VOIDmode, cond, const0_rtx);
12463 emit_unlikely_jump (x, label1);
12464
12465 emit_insn (gen_isync ());
12466 emit_label (XEXP (label2, 0));
12467}
12468
12469
b52110d4 12470 /* Emit instructions to move SRC to DST. Called by splitters for
a9baceb1
GK
12471 multi-register moves. It will emit at most one instruction for
12472 each register that is accessed; that is, it won't emit li/lis pairs
12473 (or equivalent for 64-bit code). One of SRC or DST must be a hard
12474 register. */
46c07df8 12475
46c07df8 12476void
a9baceb1 12477rs6000_split_multireg_move (rtx dst, rtx src)
46c07df8 12478{
a9baceb1
GK
12479 /* The register number of the first register being moved. */
12480 int reg;
12481 /* The mode that is to be moved. */
12482 enum machine_mode mode;
12483 /* The mode that the move is being done in, and its size. */
12484 enum machine_mode reg_mode;
12485 int reg_mode_size;
12486 /* The number of registers that will be moved. */
12487 int nregs;
12488
12489 reg = REG_P (dst) ? REGNO (dst) : REGNO (src);
12490 mode = GET_MODE (dst);
c8b622ff 12491 nregs = hard_regno_nregs[reg][mode];
a9baceb1
GK
12492 if (FP_REGNO_P (reg))
12493 reg_mode = DFmode;
12494 else if (ALTIVEC_REGNO_P (reg))
12495 reg_mode = V16QImode;
12496 else
12497 reg_mode = word_mode;
12498 reg_mode_size = GET_MODE_SIZE (reg_mode);
f676971a 12499
37409796 12500 gcc_assert (reg_mode_size * nregs == GET_MODE_SIZE (mode));
f676971a 12501
a9baceb1
GK
12502 if (REG_P (src) && REG_P (dst) && (REGNO (src) < REGNO (dst)))
12503 {
12504 /* Move register range backwards, if we might have destructive
12505 overlap. */
12506 int i;
12507 for (i = nregs - 1; i >= 0; i--)
f676971a 12508 emit_insn (gen_rtx_SET (VOIDmode,
a9baceb1
GK
12509 simplify_gen_subreg (reg_mode, dst, mode,
12510 i * reg_mode_size),
12511 simplify_gen_subreg (reg_mode, src, mode,
12512 i * reg_mode_size)));
12513 }
46c07df8
HP
12514 else
12515 {
a9baceb1
GK
12516 int i;
12517 int j = -1;
12518 bool used_update = false;
46c07df8 12519
c1e55850 12520 if (MEM_P (src) && INT_REGNO_P (reg))
c4ad648e
AM
12521 {
12522 rtx breg;
3a1f863f 12523
a9baceb1
GK
12524 if (GET_CODE (XEXP (src, 0)) == PRE_INC
12525 || GET_CODE (XEXP (src, 0)) == PRE_DEC)
3a1f863f
DE
12526 {
12527 rtx delta_rtx;
a9baceb1 12528 breg = XEXP (XEXP (src, 0), 0);
c4ad648e
AM
12529 delta_rtx = (GET_CODE (XEXP (src, 0)) == PRE_INC
12530 ? GEN_INT (GET_MODE_SIZE (GET_MODE (src)))
12531 : GEN_INT (-GET_MODE_SIZE (GET_MODE (src))));
a9baceb1
GK
12532 emit_insn (TARGET_32BIT
12533 ? gen_addsi3 (breg, breg, delta_rtx)
12534 : gen_adddi3 (breg, breg, delta_rtx));
13e2e16e 12535 src = replace_equiv_address (src, breg);
3a1f863f 12536 }
d04b6e6e 12537 else if (! rs6000_offsettable_memref_p (src))
c1e55850 12538 {
13e2e16e 12539 rtx basereg;
c1e55850
GK
12540 basereg = gen_rtx_REG (Pmode, reg);
12541 emit_insn (gen_rtx_SET (VOIDmode, basereg, XEXP (src, 0)));
13e2e16e 12542 src = replace_equiv_address (src, basereg);
c1e55850 12543 }
3a1f863f 12544
0423421f
AM
12545 breg = XEXP (src, 0);
12546 if (GET_CODE (breg) == PLUS || GET_CODE (breg) == LO_SUM)
12547 breg = XEXP (breg, 0);
12548
12549 /* If the base register we are using to address memory is
12550 also a destination reg, then change that register last. */
12551 if (REG_P (breg)
12552 && REGNO (breg) >= REGNO (dst)
3a1f863f
DE
12553 && REGNO (breg) < REGNO (dst) + nregs)
12554 j = REGNO (breg) - REGNO (dst);
c4ad648e 12555 }
46c07df8 12556
a9baceb1 12557 if (GET_CODE (dst) == MEM && INT_REGNO_P (reg))
3a1f863f
DE
12558 {
12559 rtx breg;
12560
a9baceb1
GK
12561 if (GET_CODE (XEXP (dst, 0)) == PRE_INC
12562 || GET_CODE (XEXP (dst, 0)) == PRE_DEC)
3a1f863f
DE
12563 {
12564 rtx delta_rtx;
a9baceb1 12565 breg = XEXP (XEXP (dst, 0), 0);
c4ad648e
AM
12566 delta_rtx = (GET_CODE (XEXP (dst, 0)) == PRE_INC
12567 ? GEN_INT (GET_MODE_SIZE (GET_MODE (dst)))
12568 : GEN_INT (-GET_MODE_SIZE (GET_MODE (dst))));
3a1f863f
DE
12569
12570 /* We have to update the breg before doing the store.
12571 Use store with update, if available. */
12572
12573 if (TARGET_UPDATE)
12574 {
a9baceb1 12575 rtx nsrc = simplify_gen_subreg (reg_mode, src, mode, 0);
c4ad648e
AM
12576 emit_insn (TARGET_32BIT
12577 ? (TARGET_POWERPC64
12578 ? gen_movdi_si_update (breg, breg, delta_rtx, nsrc)
12579 : gen_movsi_update (breg, breg, delta_rtx, nsrc))
12580 : gen_movdi_di_update (breg, breg, delta_rtx, nsrc));
a9baceb1 12581 used_update = true;
3a1f863f
DE
12582 }
12583 else
a9baceb1
GK
12584 emit_insn (TARGET_32BIT
12585 ? gen_addsi3 (breg, breg, delta_rtx)
12586 : gen_adddi3 (breg, breg, delta_rtx));
13e2e16e 12587 dst = replace_equiv_address (dst, breg);
3a1f863f 12588 }
37409796 12589 else
d04b6e6e 12590 gcc_assert (rs6000_offsettable_memref_p (dst));
3a1f863f
DE
12591 }
12592
46c07df8 12593 for (i = 0; i < nregs; i++)
f676971a 12594 {
3a1f863f
DE
12595 /* Calculate index to next subword. */
12596 ++j;
f676971a 12597 if (j == nregs)
3a1f863f 12598 j = 0;
46c07df8 12599
112cdef5 12600 /* If compiler already emitted move of first word by
a9baceb1 12601 store with update, no need to do anything. */
3a1f863f 12602 if (j == 0 && used_update)
a9baceb1 12603 continue;
f676971a 12604
a9baceb1
GK
12605 emit_insn (gen_rtx_SET (VOIDmode,
12606 simplify_gen_subreg (reg_mode, dst, mode,
12607 j * reg_mode_size),
12608 simplify_gen_subreg (reg_mode, src, mode,
12609 j * reg_mode_size)));
3a1f863f 12610 }
46c07df8
HP
12611 }
12612}
12613
12a4e8c5 12614\f
a4f6c312
SS
12615/* This page contains routines that are used to determine what the
12616 function prologue and epilogue code will do and write them out. */
9878760c 12617
a4f6c312
SS
12618/* Return the first fixed-point register that is required to be
12619 saved. 32 if none. */
9878760c
RK
12620
12621int
863d938c 12622first_reg_to_save (void)
9878760c
RK
12623{
12624 int first_reg;
12625
12626 /* Find lowest numbered live register. */
12627 for (first_reg = 13; first_reg <= 31; first_reg++)
f676971a 12628 if (regs_ever_live[first_reg]
a38d360d 12629 && (! call_used_regs[first_reg]
1db02437 12630 || (first_reg == RS6000_PIC_OFFSET_TABLE_REGNUM
14f00213 12631 && ((DEFAULT_ABI == ABI_V4 && flag_pic != 0)
b4db40bf
JJ
12632 || (DEFAULT_ABI == ABI_DARWIN && flag_pic)
12633 || (TARGET_TOC && TARGET_MINIMAL_TOC)))))
9878760c
RK
12634 break;
12635
ee890fe2 12636#if TARGET_MACHO
93638d7a
AM
12637 if (flag_pic
12638 && current_function_uses_pic_offset_table
12639 && first_reg > RS6000_PIC_OFFSET_TABLE_REGNUM)
1db02437 12640 return RS6000_PIC_OFFSET_TABLE_REGNUM;
ee890fe2
SS
12641#endif
12642
9878760c
RK
12643 return first_reg;
12644}
12645
12646/* Similar, for FP regs. */
12647
12648int
863d938c 12649first_fp_reg_to_save (void)
9878760c
RK
12650{
12651 int first_reg;
12652
12653 /* Find lowest numbered live register. */
12654 for (first_reg = 14 + 32; first_reg <= 63; first_reg++)
12655 if (regs_ever_live[first_reg])
12656 break;
12657
12658 return first_reg;
12659}
00b960c7
AH
12660
12661/* Similar, for AltiVec regs. */
12662
12663static int
863d938c 12664first_altivec_reg_to_save (void)
00b960c7
AH
12665{
12666 int i;
12667
12668 /* Stack frame remains as is unless we are in AltiVec ABI. */
12669 if (! TARGET_ALTIVEC_ABI)
12670 return LAST_ALTIVEC_REGNO + 1;
12671
12672 /* Find lowest numbered live register. */
12673 for (i = FIRST_ALTIVEC_REGNO + 20; i <= LAST_ALTIVEC_REGNO; ++i)
12674 if (regs_ever_live[i])
12675 break;
12676
12677 return i;
12678}
12679
12680/* Return a 32-bit mask of the AltiVec registers we need to set in
12681 VRSAVE. Bit n of the return value is 1 if Vn is live. The MSB in
12682 the 32-bit word is 0. */
12683
12684static unsigned int
863d938c 12685compute_vrsave_mask (void)
00b960c7
AH
12686{
12687 unsigned int i, mask = 0;
12688
12689 /* First, find out if we use _any_ altivec registers. */
12690 for (i = FIRST_ALTIVEC_REGNO; i <= LAST_ALTIVEC_REGNO; ++i)
12691 if (regs_ever_live[i])
12692 mask |= ALTIVEC_REG_BIT (i);
12693
12694 if (mask == 0)
12695 return mask;
12696
00b960c7
AH
12697 /* Next, remove the argument registers from the set. These must
12698 be in the VRSAVE mask set by the caller, so we don't need to add
12699 them in again. More importantly, the mask we compute here is
12700 used to generate CLOBBERs in the set_vrsave insn, and we do not
12701 wish the argument registers to die. */
a6cf80f2 12702 for (i = cfun->args_info.vregno - 1; i >= ALTIVEC_ARG_MIN_REG; --i)
00b960c7
AH
12703 mask &= ~ALTIVEC_REG_BIT (i);
12704
12705 /* Similarly, remove the return value from the set. */
12706 {
12707 bool yes = false;
12708 diddle_return_value (is_altivec_return_reg, &yes);
12709 if (yes)
12710 mask &= ~ALTIVEC_REG_BIT (ALTIVEC_ARG_RETURN);
12711 }
12712
12713 return mask;
12714}
12715
d62294f5 12716/* For a very restricted set of circumstances, we can cut down the
f57fe068
AM
12717 size of prologues/epilogues by calling our own save/restore-the-world
12718 routines. */
d62294f5
FJ
12719
12720static void
f57fe068
AM
12721compute_save_world_info (rs6000_stack_t *info_ptr)
12722{
12723 info_ptr->world_save_p = 1;
12724 info_ptr->world_save_p
12725 = (WORLD_SAVE_P (info_ptr)
12726 && DEFAULT_ABI == ABI_DARWIN
12727 && ! (current_function_calls_setjmp && flag_exceptions)
12728 && info_ptr->first_fp_reg_save == FIRST_SAVED_FP_REGNO
12729 && info_ptr->first_gp_reg_save == FIRST_SAVED_GP_REGNO
12730 && info_ptr->first_altivec_reg_save == FIRST_SAVED_ALTIVEC_REGNO
12731 && info_ptr->cr_save_p);
f676971a 12732
d62294f5
FJ
12733 /* This will not work in conjunction with sibcalls. Make sure there
12734 are none. (This check is expensive, but seldom executed.) */
f57fe068 12735 if (WORLD_SAVE_P (info_ptr))
f676971a 12736 {
d62294f5
FJ
12737 rtx insn;
12738 for ( insn = get_last_insn_anywhere (); insn; insn = PREV_INSN (insn))
c4ad648e
AM
12739 if ( GET_CODE (insn) == CALL_INSN
12740 && SIBLING_CALL_P (insn))
12741 {
12742 info_ptr->world_save_p = 0;
12743 break;
12744 }
d62294f5 12745 }
f676971a 12746
f57fe068 12747 if (WORLD_SAVE_P (info_ptr))
d62294f5
FJ
12748 {
12749 /* Even if we're not touching VRsave, make sure there's room on the
12750 stack for it, if it looks like we're calling SAVE_WORLD, which
c4ad648e 12751 will attempt to save it. */
d62294f5
FJ
12752 info_ptr->vrsave_size = 4;
12753
12754 /* "Save" the VRsave register too if we're saving the world. */
12755 if (info_ptr->vrsave_mask == 0)
c4ad648e 12756 info_ptr->vrsave_mask = compute_vrsave_mask ();
d62294f5
FJ
12757
12758 /* Because the Darwin register save/restore routines only handle
c4ad648e 12759 F14 .. F31 and V20 .. V31 as per the ABI, perform a consistency
992d08b1 12760 check. */
37409796
NS
12761 gcc_assert (info_ptr->first_fp_reg_save >= FIRST_SAVED_FP_REGNO
12762 && (info_ptr->first_altivec_reg_save
12763 >= FIRST_SAVED_ALTIVEC_REGNO));
d62294f5 12764 }
f676971a 12765 return;
d62294f5
FJ
12766}
12767
12768
00b960c7 12769static void
a2369ed3 12770is_altivec_return_reg (rtx reg, void *xyes)
00b960c7
AH
12771{
12772 bool *yes = (bool *) xyes;
12773 if (REGNO (reg) == ALTIVEC_ARG_RETURN)
12774 *yes = true;
12775}
12776
4697a36c
MM
12777\f
12778/* Calculate the stack information for the current function. This is
12779 complicated by having two separate calling sequences, the AIX calling
12780 sequence and the V.4 calling sequence.
12781
592696dd 12782 AIX (and Darwin/Mac OS X) stack frames look like:
a260abc9 12783 32-bit 64-bit
4697a36c 12784 SP----> +---------------------------------------+
a260abc9 12785 | back chain to caller | 0 0
4697a36c 12786 +---------------------------------------+
a260abc9 12787 | saved CR | 4 8 (8-11)
4697a36c 12788 +---------------------------------------+
a260abc9 12789 | saved LR | 8 16
4697a36c 12790 +---------------------------------------+
a260abc9 12791 | reserved for compilers | 12 24
4697a36c 12792 +---------------------------------------+
a260abc9 12793 | reserved for binders | 16 32
4697a36c 12794 +---------------------------------------+
a260abc9 12795 | saved TOC pointer | 20 40
4697a36c 12796 +---------------------------------------+
a260abc9 12797 | Parameter save area (P) | 24 48
4697a36c 12798 +---------------------------------------+
a260abc9 12799 | Alloca space (A) | 24+P etc.
802a0058 12800 +---------------------------------------+
a7df97e6 12801 | Local variable space (L) | 24+P+A
4697a36c 12802 +---------------------------------------+
a7df97e6 12803 | Float/int conversion temporary (X) | 24+P+A+L
4697a36c 12804 +---------------------------------------+
00b960c7
AH
12805 | Save area for AltiVec registers (W) | 24+P+A+L+X
12806 +---------------------------------------+
12807 | AltiVec alignment padding (Y) | 24+P+A+L+X+W
12808 +---------------------------------------+
12809 | Save area for VRSAVE register (Z) | 24+P+A+L+X+W+Y
4697a36c 12810 +---------------------------------------+
00b960c7
AH
12811 | Save area for GP registers (G) | 24+P+A+X+L+X+W+Y+Z
12812 +---------------------------------------+
12813 | Save area for FP registers (F) | 24+P+A+X+L+X+W+Y+Z+G
4697a36c
MM
12814 +---------------------------------------+
12815 old SP->| back chain to caller's caller |
12816 +---------------------------------------+
12817
5376a30c
KR
12818 The required alignment for AIX configurations is two words (i.e., 8
12819 or 16 bytes).
12820
12821
4697a36c
MM
12822 V.4 stack frames look like:
12823
12824 SP----> +---------------------------------------+
12825 | back chain to caller | 0
12826 +---------------------------------------+
5eb387b8 12827 | caller's saved LR | 4
4697a36c
MM
12828 +---------------------------------------+
12829 | Parameter save area (P) | 8
12830 +---------------------------------------+
a7df97e6 12831 | Alloca space (A) | 8+P
f676971a 12832 +---------------------------------------+
a7df97e6 12833 | Varargs save area (V) | 8+P+A
f676971a 12834 +---------------------------------------+
a7df97e6 12835 | Local variable space (L) | 8+P+A+V
f676971a 12836 +---------------------------------------+
a7df97e6 12837 | Float/int conversion temporary (X) | 8+P+A+V+L
4697a36c 12838 +---------------------------------------+
00b960c7
AH
12839 | Save area for AltiVec registers (W) | 8+P+A+V+L+X
12840 +---------------------------------------+
12841 | AltiVec alignment padding (Y) | 8+P+A+V+L+X+W
12842 +---------------------------------------+
12843 | Save area for VRSAVE register (Z) | 8+P+A+V+L+X+W+Y
12844 +---------------------------------------+
c4ad648e
AM
12845 | SPE: area for 64-bit GP registers |
12846 +---------------------------------------+
12847 | SPE alignment padding |
12848 +---------------------------------------+
00b960c7 12849 | saved CR (C) | 8+P+A+V+L+X+W+Y+Z
f676971a 12850 +---------------------------------------+
00b960c7 12851 | Save area for GP registers (G) | 8+P+A+V+L+X+W+Y+Z+C
f676971a 12852 +---------------------------------------+
00b960c7 12853 | Save area for FP registers (F) | 8+P+A+V+L+X+W+Y+Z+C+G
4697a36c
MM
12854 +---------------------------------------+
12855 old SP->| back chain to caller's caller |
12856 +---------------------------------------+
b6c9286a 12857
5376a30c
KR
12858 The required alignment for V.4 is 16 bytes, or 8 bytes if -meabi is
12859 given. (But note below and in sysv4.h that we require only 8 and
12860 may round up the size of our stack frame anyways. The historical
12861 reason is early versions of powerpc-linux which didn't properly
12862 align the stack at program startup. A happy side-effect is that
12863 -mno-eabi libraries can be used with -meabi programs.)
12864
50d440bc 12865 The EABI configuration defaults to the V.4 layout. However,
5376a30c
KR
12866 the stack alignment requirements may differ. If -mno-eabi is not
12867 given, the required stack alignment is 8 bytes; if -mno-eabi is
12868 given, the required alignment is 16 bytes. (But see V.4 comment
12869 above.) */
4697a36c 12870
61b2fbe7
MM
12871#ifndef ABI_STACK_BOUNDARY
12872#define ABI_STACK_BOUNDARY STACK_BOUNDARY
12873#endif
12874
d1d0c603 12875static rs6000_stack_t *
863d938c 12876rs6000_stack_info (void)
4697a36c 12877{
022123e6 12878 static rs6000_stack_t info;
4697a36c 12879 rs6000_stack_t *info_ptr = &info;
327e5343 12880 int reg_size = TARGET_32BIT ? 4 : 8;
83720594 12881 int ehrd_size;
64045029 12882 int save_align;
44688022 12883 HOST_WIDE_INT non_fixed_size;
4697a36c 12884
022123e6 12885 memset (&info, 0, sizeof (info));
4697a36c 12886
c19de7aa
AH
12887 if (TARGET_SPE)
12888 {
12889 /* Cache value so we don't rescan instruction chain over and over. */
9b7b447f 12890 if (cfun->machine->insn_chain_scanned_p == 0)
b5a5beb9
AH
12891 cfun->machine->insn_chain_scanned_p
12892 = spe_func_has_64bit_regs_p () + 1;
12893 info_ptr->spe_64bit_regs_used = cfun->machine->insn_chain_scanned_p - 1;
c19de7aa
AH
12894 }
12895
a4f6c312 12896 /* Select which calling sequence. */
178274da 12897 info_ptr->abi = DEFAULT_ABI;
9878760c 12898
a4f6c312 12899 /* Calculate which registers need to be saved & save area size. */
4697a36c 12900 info_ptr->first_gp_reg_save = first_reg_to_save ();
f676971a 12901 /* Assume that we will have to save RS6000_PIC_OFFSET_TABLE_REGNUM,
906fb125 12902 even if it currently looks like we won't. */
2bfcf297 12903 if (((TARGET_TOC && TARGET_MINIMAL_TOC)
178274da
AM
12904 || (flag_pic == 1 && DEFAULT_ABI == ABI_V4)
12905 || (flag_pic && DEFAULT_ABI == ABI_DARWIN))
1db02437
FS
12906 && info_ptr->first_gp_reg_save > RS6000_PIC_OFFSET_TABLE_REGNUM)
12907 info_ptr->gp_size = reg_size * (32 - RS6000_PIC_OFFSET_TABLE_REGNUM);
906fb125
GK
12908 else
12909 info_ptr->gp_size = reg_size * (32 - info_ptr->first_gp_reg_save);
4697a36c 12910
a3170dc6
AH
12911 /* For the SPE, we have an additional upper 32-bits on each GPR.
12912 Ideally we should save the entire 64-bits only when the upper
12913 half is used in SIMD instructions. Since we only record
12914 registers live (not the size they are used in), this proves
12915 difficult because we'd have to traverse the instruction chain at
12916 the right time, taking reload into account. This is a real pain,
c19de7aa
AH
12917 so we opt to save the GPRs in 64-bits always if but one register
12918 gets used in 64-bits. Otherwise, all the registers in the frame
12919 get saved in 32-bits.
a3170dc6 12920
c19de7aa 12921 So... since when we save all GPRs (except the SP) in 64-bits, the
a3170dc6 12922 traditional GP save area will be empty. */
c19de7aa 12923 if (TARGET_SPE_ABI && info_ptr->spe_64bit_regs_used != 0)
a3170dc6
AH
12924 info_ptr->gp_size = 0;
12925
4697a36c
MM
12926 info_ptr->first_fp_reg_save = first_fp_reg_to_save ();
12927 info_ptr->fp_size = 8 * (64 - info_ptr->first_fp_reg_save);
12928
00b960c7
AH
12929 info_ptr->first_altivec_reg_save = first_altivec_reg_to_save ();
12930 info_ptr->altivec_size = 16 * (LAST_ALTIVEC_REGNO + 1
12931 - info_ptr->first_altivec_reg_save);
12932
592696dd 12933 /* Does this function call anything? */
71f123ca
FS
12934 info_ptr->calls_p = (! current_function_is_leaf
12935 || cfun->machine->ra_needs_full_frame);
b6c9286a 12936
a4f6c312 12937 /* Determine if we need to save the link register. */
022123e6
AM
12938 if ((DEFAULT_ABI == ABI_AIX
12939 && current_function_profile
12940 && !TARGET_PROFILE_KERNEL)
4697a36c
MM
12941#ifdef TARGET_RELOCATABLE
12942 || (TARGET_RELOCATABLE && (get_pool_size () != 0))
12943#endif
12944 || (info_ptr->first_fp_reg_save != 64
12945 && !FP_SAVE_INLINE (info_ptr->first_fp_reg_save))
00b960c7 12946 || info_ptr->first_altivec_reg_save <= LAST_ALTIVEC_REGNO
178274da 12947 || (DEFAULT_ABI == ABI_V4 && current_function_calls_alloca)
022123e6
AM
12948 || info_ptr->calls_p
12949 || rs6000_ra_ever_killed ())
4697a36c
MM
12950 {
12951 info_ptr->lr_save_p = 1;
9ebbca7d 12952 regs_ever_live[LINK_REGISTER_REGNUM] = 1;
4697a36c
MM
12953 }
12954
9ebbca7d 12955 /* Determine if we need to save the condition code registers. */
f676971a 12956 if (regs_ever_live[CR2_REGNO]
9ebbca7d
GK
12957 || regs_ever_live[CR3_REGNO]
12958 || regs_ever_live[CR4_REGNO])
4697a36c
MM
12959 {
12960 info_ptr->cr_save_p = 1;
178274da 12961 if (DEFAULT_ABI == ABI_V4)
4697a36c
MM
12962 info_ptr->cr_size = reg_size;
12963 }
12964
83720594
RH
12965 /* If the current function calls __builtin_eh_return, then we need
12966 to allocate stack space for registers that will hold data for
12967 the exception handler. */
12968 if (current_function_calls_eh_return)
12969 {
12970 unsigned int i;
12971 for (i = 0; EH_RETURN_DATA_REGNO (i) != INVALID_REGNUM; ++i)
12972 continue;
a3170dc6
AH
12973
12974 /* SPE saves EH registers in 64-bits. */
c19de7aa
AH
12975 ehrd_size = i * (TARGET_SPE_ABI
12976 && info_ptr->spe_64bit_regs_used != 0
12977 ? UNITS_PER_SPE_WORD : UNITS_PER_WORD);
83720594
RH
12978 }
12979 else
12980 ehrd_size = 0;
12981
592696dd 12982 /* Determine various sizes. */
4697a36c
MM
12983 info_ptr->reg_size = reg_size;
12984 info_ptr->fixed_size = RS6000_SAVE_AREA;
189e03e3 12985 info_ptr->vars_size = RS6000_ALIGN (get_frame_size (), 8);
a4f6c312 12986 info_ptr->parm_size = RS6000_ALIGN (current_function_outgoing_args_size,
03e007d7 12987 TARGET_ALTIVEC ? 16 : 8);
7d5175e1
JJ
12988 if (FRAME_GROWS_DOWNWARD)
12989 info_ptr->vars_size
5b667039
JJ
12990 += RS6000_ALIGN (info_ptr->fixed_size + info_ptr->vars_size
12991 + info_ptr->parm_size,
7d5175e1 12992 ABI_STACK_BOUNDARY / BITS_PER_UNIT)
5b667039
JJ
12993 - (info_ptr->fixed_size + info_ptr->vars_size
12994 + info_ptr->parm_size);
00b960c7 12995
c19de7aa 12996 if (TARGET_SPE_ABI && info_ptr->spe_64bit_regs_used != 0)
a3170dc6
AH
12997 info_ptr->spe_gp_size = 8 * (32 - info_ptr->first_gp_reg_save);
12998 else
12999 info_ptr->spe_gp_size = 0;
13000
4d774ff8
HP
13001 if (TARGET_ALTIVEC_ABI)
13002 info_ptr->vrsave_mask = compute_vrsave_mask ();
00b960c7 13003 else
4d774ff8
HP
13004 info_ptr->vrsave_mask = 0;
13005
13006 if (TARGET_ALTIVEC_VRSAVE && info_ptr->vrsave_mask)
13007 info_ptr->vrsave_size = 4;
13008 else
13009 info_ptr->vrsave_size = 0;
b6c9286a 13010
d62294f5
FJ
13011 compute_save_world_info (info_ptr);
13012
592696dd 13013 /* Calculate the offsets. */
178274da 13014 switch (DEFAULT_ABI)
4697a36c 13015 {
b6c9286a 13016 case ABI_NONE:
24d304eb 13017 default:
37409796 13018 gcc_unreachable ();
b6c9286a
MM
13019
13020 case ABI_AIX:
ee890fe2 13021 case ABI_DARWIN:
b6c9286a
MM
13022 info_ptr->fp_save_offset = - info_ptr->fp_size;
13023 info_ptr->gp_save_offset = info_ptr->fp_save_offset - info_ptr->gp_size;
00b960c7
AH
13024
13025 if (TARGET_ALTIVEC_ABI)
13026 {
13027 info_ptr->vrsave_save_offset
13028 = info_ptr->gp_save_offset - info_ptr->vrsave_size;
13029
13030 /* Align stack so vector save area is on a quadword boundary. */
13031 if (info_ptr->altivec_size != 0)
13032 info_ptr->altivec_padding_size
13033 = 16 - (-info_ptr->vrsave_save_offset % 16);
13034 else
13035 info_ptr->altivec_padding_size = 0;
13036
13037 info_ptr->altivec_save_offset
13038 = info_ptr->vrsave_save_offset
13039 - info_ptr->altivec_padding_size
13040 - info_ptr->altivec_size;
13041
13042 /* Adjust for AltiVec case. */
13043 info_ptr->ehrd_offset = info_ptr->altivec_save_offset - ehrd_size;
13044 }
13045 else
13046 info_ptr->ehrd_offset = info_ptr->gp_save_offset - ehrd_size;
a260abc9
DE
13047 info_ptr->cr_save_offset = reg_size; /* first word when 64-bit. */
13048 info_ptr->lr_save_offset = 2*reg_size;
24d304eb
RK
13049 break;
13050
13051 case ABI_V4:
b6c9286a
MM
13052 info_ptr->fp_save_offset = - info_ptr->fp_size;
13053 info_ptr->gp_save_offset = info_ptr->fp_save_offset - info_ptr->gp_size;
a7df97e6 13054 info_ptr->cr_save_offset = info_ptr->gp_save_offset - info_ptr->cr_size;
00b960c7 13055
c19de7aa 13056 if (TARGET_SPE_ABI && info_ptr->spe_64bit_regs_used != 0)
c4ad648e
AM
13057 {
13058 /* Align stack so SPE GPR save area is aligned on a
13059 double-word boundary. */
13060 if (info_ptr->spe_gp_size != 0)
13061 info_ptr->spe_padding_size
13062 = 8 - (-info_ptr->cr_save_offset % 8);
13063 else
13064 info_ptr->spe_padding_size = 0;
13065
13066 info_ptr->spe_gp_save_offset
13067 = info_ptr->cr_save_offset
13068 - info_ptr->spe_padding_size
13069 - info_ptr->spe_gp_size;
13070
13071 /* Adjust for SPE case. */
022123e6 13072 info_ptr->ehrd_offset = info_ptr->spe_gp_save_offset;
c4ad648e 13073 }
a3170dc6 13074 else if (TARGET_ALTIVEC_ABI)
00b960c7
AH
13075 {
13076 info_ptr->vrsave_save_offset
13077 = info_ptr->cr_save_offset - info_ptr->vrsave_size;
13078
13079 /* Align stack so vector save area is on a quadword boundary. */
13080 if (info_ptr->altivec_size != 0)
13081 info_ptr->altivec_padding_size
13082 = 16 - (-info_ptr->vrsave_save_offset % 16);
13083 else
13084 info_ptr->altivec_padding_size = 0;
13085
13086 info_ptr->altivec_save_offset
13087 = info_ptr->vrsave_save_offset
13088 - info_ptr->altivec_padding_size
13089 - info_ptr->altivec_size;
13090
13091 /* Adjust for AltiVec case. */
022123e6 13092 info_ptr->ehrd_offset = info_ptr->altivec_save_offset;
00b960c7
AH
13093 }
13094 else
022123e6
AM
13095 info_ptr->ehrd_offset = info_ptr->cr_save_offset;
13096 info_ptr->ehrd_offset -= ehrd_size;
b6c9286a
MM
13097 info_ptr->lr_save_offset = reg_size;
13098 break;
4697a36c
MM
13099 }
13100
64045029 13101 save_align = (TARGET_ALTIVEC_ABI || DEFAULT_ABI == ABI_DARWIN) ? 16 : 8;
00b960c7
AH
13102 info_ptr->save_size = RS6000_ALIGN (info_ptr->fp_size
13103 + info_ptr->gp_size
13104 + info_ptr->altivec_size
13105 + info_ptr->altivec_padding_size
a3170dc6
AH
13106 + info_ptr->spe_gp_size
13107 + info_ptr->spe_padding_size
00b960c7
AH
13108 + ehrd_size
13109 + info_ptr->cr_size
022123e6 13110 + info_ptr->vrsave_size,
64045029 13111 save_align);
00b960c7 13112
44688022 13113 non_fixed_size = (info_ptr->vars_size
ff381587 13114 + info_ptr->parm_size
5b667039 13115 + info_ptr->save_size);
ff381587 13116
44688022
AM
13117 info_ptr->total_size = RS6000_ALIGN (non_fixed_size + info_ptr->fixed_size,
13118 ABI_STACK_BOUNDARY / BITS_PER_UNIT);
ff381587
MM
13119
13120 /* Determine if we need to allocate any stack frame:
13121
a4f6c312
SS
13122 For AIX we need to push the stack if a frame pointer is needed
13123 (because the stack might be dynamically adjusted), if we are
13124 debugging, if we make calls, or if the sum of fp_save, gp_save,
13125 and local variables are more than the space needed to save all
13126 non-volatile registers: 32-bit: 18*8 + 19*4 = 220 or 64-bit: 18*8
13127 + 18*8 = 288 (GPR13 reserved).
ff381587 13128
a4f6c312
SS
13129 For V.4 we don't have the stack cushion that AIX uses, but assume
13130 that the debugger can handle stackless frames. */
ff381587
MM
13131
13132 if (info_ptr->calls_p)
13133 info_ptr->push_p = 1;
13134
178274da 13135 else if (DEFAULT_ABI == ABI_V4)
44688022 13136 info_ptr->push_p = non_fixed_size != 0;
ff381587 13137
178274da
AM
13138 else if (frame_pointer_needed)
13139 info_ptr->push_p = 1;
13140
13141 else if (TARGET_XCOFF && write_symbols != NO_DEBUG)
13142 info_ptr->push_p = 1;
13143
ff381587 13144 else
44688022 13145 info_ptr->push_p = non_fixed_size > (TARGET_32BIT ? 220 : 288);
ff381587 13146
a4f6c312 13147 /* Zero offsets if we're not saving those registers. */
8dda1a21 13148 if (info_ptr->fp_size == 0)
4697a36c
MM
13149 info_ptr->fp_save_offset = 0;
13150
8dda1a21 13151 if (info_ptr->gp_size == 0)
4697a36c
MM
13152 info_ptr->gp_save_offset = 0;
13153
00b960c7
AH
13154 if (! TARGET_ALTIVEC_ABI || info_ptr->altivec_size == 0)
13155 info_ptr->altivec_save_offset = 0;
13156
13157 if (! TARGET_ALTIVEC_ABI || info_ptr->vrsave_mask == 0)
13158 info_ptr->vrsave_save_offset = 0;
13159
c19de7aa
AH
13160 if (! TARGET_SPE_ABI
13161 || info_ptr->spe_64bit_regs_used == 0
13162 || info_ptr->spe_gp_size == 0)
a3170dc6
AH
13163 info_ptr->spe_gp_save_offset = 0;
13164
c81fc13e 13165 if (! info_ptr->lr_save_p)
4697a36c
MM
13166 info_ptr->lr_save_offset = 0;
13167
c81fc13e 13168 if (! info_ptr->cr_save_p)
4697a36c
MM
13169 info_ptr->cr_save_offset = 0;
13170
13171 return info_ptr;
13172}
13173
c19de7aa
AH
13174/* Return true if the current function uses any GPRs in 64-bit SIMD
13175 mode. */
13176
13177static bool
863d938c 13178spe_func_has_64bit_regs_p (void)
c19de7aa
AH
13179{
13180 rtx insns, insn;
13181
13182 /* Functions that save and restore all the call-saved registers will
13183 need to save/restore the registers in 64-bits. */
13184 if (current_function_calls_eh_return
13185 || current_function_calls_setjmp
13186 || current_function_has_nonlocal_goto)
13187 return true;
13188
13189 insns = get_insns ();
13190
13191 for (insn = NEXT_INSN (insns); insn != NULL_RTX; insn = NEXT_INSN (insn))
13192 {
13193 if (INSN_P (insn))
13194 {
13195 rtx i;
13196
b5a5beb9
AH
13197 /* FIXME: This should be implemented with attributes...
13198
13199 (set_attr "spe64" "true")....then,
13200 if (get_spe64(insn)) return true;
13201
13202 It's the only reliable way to do the stuff below. */
13203
c19de7aa 13204 i = PATTERN (insn);
f82f556d
AH
13205 if (GET_CODE (i) == SET)
13206 {
13207 enum machine_mode mode = GET_MODE (SET_SRC (i));
13208
13209 if (SPE_VECTOR_MODE (mode))
13210 return true;
13211 if (TARGET_E500_DOUBLE && mode == DFmode)
13212 return true;
13213 }
c19de7aa
AH
13214 }
13215 }
13216
13217 return false;
13218}
13219
d1d0c603 13220static void
a2369ed3 13221debug_stack_info (rs6000_stack_t *info)
9878760c 13222{
d330fd93 13223 const char *abi_string;
24d304eb 13224
c81fc13e 13225 if (! info)
4697a36c
MM
13226 info = rs6000_stack_info ();
13227
13228 fprintf (stderr, "\nStack information for function %s:\n",
13229 ((current_function_decl && DECL_NAME (current_function_decl))
13230 ? IDENTIFIER_POINTER (DECL_NAME (current_function_decl))
13231 : "<unknown>"));
13232
24d304eb
RK
13233 switch (info->abi)
13234 {
b6c9286a
MM
13235 default: abi_string = "Unknown"; break;
13236 case ABI_NONE: abi_string = "NONE"; break;
50d440bc 13237 case ABI_AIX: abi_string = "AIX"; break;
ee890fe2 13238 case ABI_DARWIN: abi_string = "Darwin"; break;
b6c9286a 13239 case ABI_V4: abi_string = "V.4"; break;
24d304eb
RK
13240 }
13241
13242 fprintf (stderr, "\tABI = %5s\n", abi_string);
13243
00b960c7
AH
13244 if (TARGET_ALTIVEC_ABI)
13245 fprintf (stderr, "\tALTIVEC ABI extensions enabled.\n");
13246
a3170dc6
AH
13247 if (TARGET_SPE_ABI)
13248 fprintf (stderr, "\tSPE ABI extensions enabled.\n");
13249
4697a36c
MM
13250 if (info->first_gp_reg_save != 32)
13251 fprintf (stderr, "\tfirst_gp_reg_save = %5d\n", info->first_gp_reg_save);
13252
13253 if (info->first_fp_reg_save != 64)
13254 fprintf (stderr, "\tfirst_fp_reg_save = %5d\n", info->first_fp_reg_save);
9878760c 13255
00b960c7
AH
13256 if (info->first_altivec_reg_save <= LAST_ALTIVEC_REGNO)
13257 fprintf (stderr, "\tfirst_altivec_reg_save = %5d\n",
13258 info->first_altivec_reg_save);
13259
4697a36c
MM
13260 if (info->lr_save_p)
13261 fprintf (stderr, "\tlr_save_p = %5d\n", info->lr_save_p);
9878760c 13262
4697a36c
MM
13263 if (info->cr_save_p)
13264 fprintf (stderr, "\tcr_save_p = %5d\n", info->cr_save_p);
13265
00b960c7
AH
13266 if (info->vrsave_mask)
13267 fprintf (stderr, "\tvrsave_mask = 0x%x\n", info->vrsave_mask);
13268
4697a36c
MM
13269 if (info->push_p)
13270 fprintf (stderr, "\tpush_p = %5d\n", info->push_p);
13271
13272 if (info->calls_p)
13273 fprintf (stderr, "\tcalls_p = %5d\n", info->calls_p);
13274
4697a36c
MM
13275 if (info->gp_save_offset)
13276 fprintf (stderr, "\tgp_save_offset = %5d\n", info->gp_save_offset);
13277
13278 if (info->fp_save_offset)
13279 fprintf (stderr, "\tfp_save_offset = %5d\n", info->fp_save_offset);
13280
00b960c7
AH
13281 if (info->altivec_save_offset)
13282 fprintf (stderr, "\taltivec_save_offset = %5d\n",
13283 info->altivec_save_offset);
13284
a3170dc6
AH
13285 if (info->spe_gp_save_offset)
13286 fprintf (stderr, "\tspe_gp_save_offset = %5d\n",
13287 info->spe_gp_save_offset);
13288
00b960c7
AH
13289 if (info->vrsave_save_offset)
13290 fprintf (stderr, "\tvrsave_save_offset = %5d\n",
13291 info->vrsave_save_offset);
13292
4697a36c
MM
13293 if (info->lr_save_offset)
13294 fprintf (stderr, "\tlr_save_offset = %5d\n", info->lr_save_offset);
13295
13296 if (info->cr_save_offset)
13297 fprintf (stderr, "\tcr_save_offset = %5d\n", info->cr_save_offset);
13298
13299 if (info->varargs_save_offset)
13300 fprintf (stderr, "\tvarargs_save_offset = %5d\n", info->varargs_save_offset);
13301
13302 if (info->total_size)
d1d0c603
JJ
13303 fprintf (stderr, "\ttotal_size = "HOST_WIDE_INT_PRINT_DEC"\n",
13304 info->total_size);
4697a36c 13305
4697a36c 13306 if (info->vars_size)
d1d0c603
JJ
13307 fprintf (stderr, "\tvars_size = "HOST_WIDE_INT_PRINT_DEC"\n",
13308 info->vars_size);
4697a36c
MM
13309
13310 if (info->parm_size)
13311 fprintf (stderr, "\tparm_size = %5d\n", info->parm_size);
13312
13313 if (info->fixed_size)
13314 fprintf (stderr, "\tfixed_size = %5d\n", info->fixed_size);
13315
13316 if (info->gp_size)
13317 fprintf (stderr, "\tgp_size = %5d\n", info->gp_size);
13318
a3170dc6
AH
13319 if (info->spe_gp_size)
13320 fprintf (stderr, "\tspe_gp_size = %5d\n", info->spe_gp_size);
13321
4697a36c
MM
13322 if (info->fp_size)
13323 fprintf (stderr, "\tfp_size = %5d\n", info->fp_size);
13324
00b960c7
AH
13325 if (info->altivec_size)
13326 fprintf (stderr, "\taltivec_size = %5d\n", info->altivec_size);
13327
13328 if (info->vrsave_size)
13329 fprintf (stderr, "\tvrsave_size = %5d\n", info->vrsave_size);
13330
13331 if (info->altivec_padding_size)
13332 fprintf (stderr, "\taltivec_padding_size= %5d\n",
13333 info->altivec_padding_size);
13334
a3170dc6
AH
13335 if (info->spe_padding_size)
13336 fprintf (stderr, "\tspe_padding_size = %5d\n",
13337 info->spe_padding_size);
13338
4697a36c
MM
13339 if (info->cr_size)
13340 fprintf (stderr, "\tcr_size = %5d\n", info->cr_size);
13341
13342 if (info->save_size)
13343 fprintf (stderr, "\tsave_size = %5d\n", info->save_size);
13344
13345 if (info->reg_size != 4)
13346 fprintf (stderr, "\treg_size = %5d\n", info->reg_size);
13347
13348 fprintf (stderr, "\n");
9878760c 13349}
71f123ca
FS
13350
13351rtx
a2369ed3 13352rs6000_return_addr (int count, rtx frame)
71f123ca 13353{
a4f6c312
SS
13354 /* Currently we don't optimize very well between prolog and body
13355 code and for PIC code the code can be actually quite bad, so
13356 don't try to be too clever here. */
f1384257 13357 if (count != 0 || (DEFAULT_ABI != ABI_AIX && flag_pic))
71f123ca
FS
13358 {
13359 cfun->machine->ra_needs_full_frame = 1;
8ac61af7
RK
13360
13361 return
13362 gen_rtx_MEM
13363 (Pmode,
13364 memory_address
13365 (Pmode,
13366 plus_constant (copy_to_reg
13367 (gen_rtx_MEM (Pmode,
13368 memory_address (Pmode, frame))),
13369 RETURN_ADDRESS_OFFSET)));
71f123ca
FS
13370 }
13371
8c29550d 13372 cfun->machine->ra_need_lr = 1;
9e2f7ec7 13373 return get_hard_reg_initial_val (Pmode, LINK_REGISTER_REGNUM);
71f123ca
FS
13374}
13375
5e1bf043
DJ
13376/* Say whether a function is a candidate for sibcall handling or not.
13377 We do not allow indirect calls to be optimized into sibling calls.
13378 Also, we can't do it if there are any vector parameters; there's
13379 nowhere to put the VRsave code so it works; note that functions with
13380 vector parameters are required to have a prototype, so the argument
13381 type info must be available here. (The tail recursion case can work
13382 with vector parameters, but there's no way to distinguish here.) */
4977bab6 13383static bool
a2369ed3 13384rs6000_function_ok_for_sibcall (tree decl, tree exp ATTRIBUTE_UNUSED)
5e1bf043
DJ
13385{
13386 tree type;
4977bab6 13387 if (decl)
5e1bf043
DJ
13388 {
13389 if (TARGET_ALTIVEC_VRSAVE)
c4ad648e 13390 {
4977bab6 13391 for (type = TYPE_ARG_TYPES (TREE_TYPE (decl));
5e1bf043
DJ
13392 type; type = TREE_CHAIN (type))
13393 {
c15b529f 13394 if (TREE_CODE (TREE_VALUE (type)) == VECTOR_TYPE)
4977bab6 13395 return false;
5e1bf043 13396 }
c4ad648e 13397 }
5e1bf043 13398 if (DEFAULT_ABI == ABI_DARWIN
4977bab6 13399 || (*targetm.binds_local_p) (decl))
2bcc50d0 13400 {
4977bab6 13401 tree attr_list = TYPE_ATTRIBUTES (TREE_TYPE (decl));
2bcc50d0
AM
13402
13403 if (!lookup_attribute ("longcall", attr_list)
13404 || lookup_attribute ("shortcall", attr_list))
4977bab6 13405 return true;
2bcc50d0 13406 }
5e1bf043 13407 }
4977bab6 13408 return false;
5e1bf043
DJ
13409}
13410
e7e64a25
AS
13411/* NULL if INSN insn is valid within a low-overhead loop.
13412 Otherwise return why doloop cannot be applied.
9419649c
DE
13413 PowerPC uses the COUNT register for branch on table instructions. */
13414
e7e64a25
AS
13415static const char *
13416rs6000_invalid_within_doloop (rtx insn)
9419649c
DE
13417{
13418 if (CALL_P (insn))
e7e64a25 13419 return "Function call in the loop.";
9419649c
DE
13420
13421 if (JUMP_P (insn)
13422 && (GET_CODE (PATTERN (insn)) == ADDR_DIFF_VEC
13423 || GET_CODE (PATTERN (insn)) == ADDR_VEC))
e7e64a25 13424 return "Computed branch in the loop.";
9419649c 13425
e7e64a25 13426 return NULL;
9419649c
DE
13427}
13428
71f123ca 13429static int
863d938c 13430rs6000_ra_ever_killed (void)
71f123ca
FS
13431{
13432 rtx top;
5e1bf043
DJ
13433 rtx reg;
13434 rtx insn;
71f123ca 13435
dd292d0a 13436 if (current_function_is_thunk)
71f123ca 13437 return 0;
eb0424da 13438
36f7e964
AH
13439 /* regs_ever_live has LR marked as used if any sibcalls are present,
13440 but this should not force saving and restoring in the
13441 pro/epilogue. Likewise, reg_set_between_p thinks a sibcall
a3c9585f 13442 clobbers LR, so that is inappropriate. */
36f7e964 13443
5e1bf043
DJ
13444 /* Also, the prologue can generate a store into LR that
13445 doesn't really count, like this:
36f7e964 13446
5e1bf043
DJ
13447 move LR->R0
13448 bcl to set PIC register
13449 move LR->R31
13450 move R0->LR
36f7e964
AH
13451
13452 When we're called from the epilogue, we need to avoid counting
13453 this as a store. */
f676971a 13454
71f123ca
FS
13455 push_topmost_sequence ();
13456 top = get_insns ();
13457 pop_topmost_sequence ();
5e1bf043 13458 reg = gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM);
71f123ca 13459
5e1bf043
DJ
13460 for (insn = NEXT_INSN (top); insn != NULL_RTX; insn = NEXT_INSN (insn))
13461 {
13462 if (INSN_P (insn))
13463 {
022123e6
AM
13464 if (CALL_P (insn))
13465 {
13466 if (!SIBLING_CALL_P (insn))
13467 return 1;
13468 }
13469 else if (find_regno_note (insn, REG_INC, LINK_REGISTER_REGNUM))
5e1bf043 13470 return 1;
36f7e964
AH
13471 else if (set_of (reg, insn) != NULL_RTX
13472 && !prologue_epilogue_contains (insn))
5e1bf043
DJ
13473 return 1;
13474 }
13475 }
13476 return 0;
71f123ca 13477}
4697a36c 13478\f
8cd8f856
GK
13479/* Add a REG_MAYBE_DEAD note to the insn. */
13480static void
a2369ed3 13481rs6000_maybe_dead (rtx insn)
8cd8f856
GK
13482{
13483 REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_MAYBE_DEAD,
13484 const0_rtx,
13485 REG_NOTES (insn));
13486}
13487
9ebbca7d 13488/* Emit instructions needed to load the TOC register.
c7ca610e 13489 This is only needed when TARGET_TOC, TARGET_MINIMAL_TOC, and there is
9ebbca7d 13490 a constant pool; or for SVR4 -fpic. */
c7ca610e
RK
13491
13492void
a2369ed3 13493rs6000_emit_load_toc_table (int fromprolog)
c7ca610e 13494{
027fbf43 13495 rtx dest, insn;
1db02437 13496 dest = gen_rtx_REG (Pmode, RS6000_PIC_OFFSET_TABLE_REGNUM);
c7ca610e 13497
7f970b70 13498 if (TARGET_ELF && TARGET_SECURE_PLT && DEFAULT_ABI != ABI_AIX && flag_pic)
20b71b17 13499 {
7f970b70
AM
13500 char buf[30];
13501 rtx lab, tmp1, tmp2, got, tempLR;
13502
13503 ASM_GENERATE_INTERNAL_LABEL (buf, "LCF", rs6000_pic_labelno);
13504 lab = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (buf));
13505 if (flag_pic == 2)
13506 got = gen_rtx_SYMBOL_REF (Pmode, toc_label_name);
13507 else
13508 got = rs6000_got_sym ();
13509 tmp1 = tmp2 = dest;
13510 if (!fromprolog)
13511 {
13512 tmp1 = gen_reg_rtx (Pmode);
13513 tmp2 = gen_reg_rtx (Pmode);
13514 }
13515 tempLR = (fromprolog
13516 ? gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM)
13517 : gen_reg_rtx (Pmode));
13518 insn = emit_insn (gen_load_toc_v4_PIC_1 (tempLR, lab));
13519 if (fromprolog)
13520 rs6000_maybe_dead (insn);
13521 insn = emit_move_insn (tmp1, tempLR);
13522 if (fromprolog)
13523 rs6000_maybe_dead (insn);
13524 insn = emit_insn (gen_load_toc_v4_PIC_3b (tmp2, tmp1, got, lab));
13525 if (fromprolog)
13526 rs6000_maybe_dead (insn);
13527 insn = emit_insn (gen_load_toc_v4_PIC_3c (dest, tmp2, got, lab));
13528 if (fromprolog)
13529 rs6000_maybe_dead (insn);
13530 }
13531 else if (TARGET_ELF && DEFAULT_ABI == ABI_V4 && flag_pic == 1)
13532 {
13533 rtx tempLR = (fromprolog
13534 ? gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM)
13535 : gen_reg_rtx (Pmode));
13536
13537 insn = emit_insn (gen_load_toc_v4_pic_si (tempLR));
027fbf43
JJ
13538 if (fromprolog)
13539 rs6000_maybe_dead (insn);
7f970b70 13540 insn = emit_move_insn (dest, tempLR);
027fbf43
JJ
13541 if (fromprolog)
13542 rs6000_maybe_dead (insn);
20b71b17
AM
13543 }
13544 else if (TARGET_ELF && DEFAULT_ABI != ABI_AIX && flag_pic == 2)
13545 {
13546 char buf[30];
13547 rtx tempLR = (fromprolog
13548 ? gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM)
13549 : gen_reg_rtx (Pmode));
13550 rtx temp0 = (fromprolog
13551 ? gen_rtx_REG (Pmode, 0)
13552 : gen_reg_rtx (Pmode));
20b71b17 13553
20b71b17
AM
13554 if (fromprolog)
13555 {
ccbca5e4 13556 rtx symF, symL;
38c1f2d7 13557
20b71b17
AM
13558 ASM_GENERATE_INTERNAL_LABEL (buf, "LCF", rs6000_pic_labelno);
13559 symF = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (buf));
9ebbca7d 13560
20b71b17
AM
13561 ASM_GENERATE_INTERNAL_LABEL (buf, "LCL", rs6000_pic_labelno);
13562 symL = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (buf));
13563
13564 rs6000_maybe_dead (emit_insn (gen_load_toc_v4_PIC_1 (tempLR,
13565 symF)));
13566 rs6000_maybe_dead (emit_move_insn (dest, tempLR));
13567 rs6000_maybe_dead (emit_insn (gen_load_toc_v4_PIC_2 (temp0, dest,
13568 symL,
13569 symF)));
9ebbca7d
GK
13570 }
13571 else
20b71b17
AM
13572 {
13573 rtx tocsym;
20b71b17
AM
13574
13575 tocsym = gen_rtx_SYMBOL_REF (Pmode, toc_label_name);
ccbca5e4 13576 emit_insn (gen_load_toc_v4_PIC_1b (tempLR, tocsym));
027fbf43
JJ
13577 emit_move_insn (dest, tempLR);
13578 emit_move_insn (temp0, gen_rtx_MEM (Pmode, dest));
20b71b17 13579 }
027fbf43
JJ
13580 insn = emit_insn (gen_addsi3 (dest, temp0, dest));
13581 if (fromprolog)
13582 rs6000_maybe_dead (insn);
9ebbca7d 13583 }
20b71b17
AM
13584 else if (TARGET_ELF && !TARGET_AIX && flag_pic == 0 && TARGET_MINIMAL_TOC)
13585 {
13586 /* This is for AIX code running in non-PIC ELF32. */
13587 char buf[30];
13588 rtx realsym;
13589 ASM_GENERATE_INTERNAL_LABEL (buf, "LCTOC", 1);
13590 realsym = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (buf));
13591
027fbf43
JJ
13592 insn = emit_insn (gen_elf_high (dest, realsym));
13593 if (fromprolog)
13594 rs6000_maybe_dead (insn);
13595 insn = emit_insn (gen_elf_low (dest, dest, realsym));
13596 if (fromprolog)
13597 rs6000_maybe_dead (insn);
20b71b17 13598 }
37409796 13599 else
9ebbca7d 13600 {
37409796 13601 gcc_assert (DEFAULT_ABI == ABI_AIX);
bb8df8a6 13602
9ebbca7d 13603 if (TARGET_32BIT)
027fbf43 13604 insn = emit_insn (gen_load_toc_aix_si (dest));
9ebbca7d 13605 else
027fbf43
JJ
13606 insn = emit_insn (gen_load_toc_aix_di (dest));
13607 if (fromprolog)
13608 rs6000_maybe_dead (insn);
9ebbca7d
GK
13609 }
13610}
13611
d1d0c603
JJ
13612/* Emit instructions to restore the link register after determining where
13613 its value has been stored. */
13614
13615void
13616rs6000_emit_eh_reg_restore (rtx source, rtx scratch)
13617{
13618 rs6000_stack_t *info = rs6000_stack_info ();
13619 rtx operands[2];
13620
13621 operands[0] = source;
13622 operands[1] = scratch;
13623
13624 if (info->lr_save_p)
13625 {
13626 rtx frame_rtx = stack_pointer_rtx;
13627 HOST_WIDE_INT sp_offset = 0;
13628 rtx tmp;
13629
13630 if (frame_pointer_needed
13631 || current_function_calls_alloca
13632 || info->total_size > 32767)
13633 {
0be76840 13634 tmp = gen_frame_mem (Pmode, frame_rtx);
8308679f 13635 emit_move_insn (operands[1], tmp);
d1d0c603
JJ
13636 frame_rtx = operands[1];
13637 }
13638 else if (info->push_p)
13639 sp_offset = info->total_size;
13640
13641 tmp = plus_constant (frame_rtx, info->lr_save_offset + sp_offset);
0be76840 13642 tmp = gen_frame_mem (Pmode, tmp);
d1d0c603
JJ
13643 emit_move_insn (tmp, operands[0]);
13644 }
13645 else
13646 emit_move_insn (gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM), operands[0]);
13647}
13648
f103e34d
GK
13649static GTY(()) int set = -1;
13650
f676971a 13651int
863d938c 13652get_TOC_alias_set (void)
9ebbca7d 13653{
f103e34d
GK
13654 if (set == -1)
13655 set = new_alias_set ();
13656 return set;
f676971a 13657}
9ebbca7d 13658
c1207243 13659/* This returns nonzero if the current function uses the TOC. This is
3c9eb5f4
AM
13660 determined by the presence of (use (unspec ... UNSPEC_TOC)), which
13661 is generated by the ABI_V4 load_toc_* patterns. */
c954844a 13662#if TARGET_ELF
3c9eb5f4 13663static int
f676971a 13664uses_TOC (void)
9ebbca7d 13665{
c4501e62 13666 rtx insn;
38c1f2d7 13667
c4501e62
JJ
13668 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
13669 if (INSN_P (insn))
13670 {
13671 rtx pat = PATTERN (insn);
13672 int i;
9ebbca7d 13673
f676971a 13674 if (GET_CODE (pat) == PARALLEL)
c4501e62
JJ
13675 for (i = 0; i < XVECLEN (pat, 0); i++)
13676 {
13677 rtx sub = XVECEXP (pat, 0, i);
13678 if (GET_CODE (sub) == USE)
13679 {
13680 sub = XEXP (sub, 0);
13681 if (GET_CODE (sub) == UNSPEC
13682 && XINT (sub, 1) == UNSPEC_TOC)
13683 return 1;
13684 }
13685 }
13686 }
13687 return 0;
9ebbca7d 13688}
c954844a 13689#endif
38c1f2d7 13690
9ebbca7d 13691rtx
f676971a 13692create_TOC_reference (rtx symbol)
9ebbca7d 13693{
b69542f7
AM
13694 if (no_new_pseudos)
13695 regs_ever_live[TOC_REGISTER] = 1;
f676971a 13696 return gen_rtx_PLUS (Pmode,
a8a05998 13697 gen_rtx_REG (Pmode, TOC_REGISTER),
f676971a
EC
13698 gen_rtx_CONST (Pmode,
13699 gen_rtx_MINUS (Pmode, symbol,
b999aaeb 13700 gen_rtx_SYMBOL_REF (Pmode, toc_label_name))));
9ebbca7d 13701}
38c1f2d7 13702
fc4767bb
JJ
13703/* If _Unwind_* has been called from within the same module,
13704 toc register is not guaranteed to be saved to 40(1) on function
13705 entry. Save it there in that case. */
c7ca610e 13706
9ebbca7d 13707void
863d938c 13708rs6000_aix_emit_builtin_unwind_init (void)
9ebbca7d
GK
13709{
13710 rtx mem;
13711 rtx stack_top = gen_reg_rtx (Pmode);
13712 rtx opcode_addr = gen_reg_rtx (Pmode);
fc4767bb
JJ
13713 rtx opcode = gen_reg_rtx (SImode);
13714 rtx tocompare = gen_reg_rtx (SImode);
13715 rtx no_toc_save_needed = gen_label_rtx ();
9ebbca7d 13716
8308679f 13717 mem = gen_frame_mem (Pmode, hard_frame_pointer_rtx);
9ebbca7d
GK
13718 emit_move_insn (stack_top, mem);
13719
8308679f
DE
13720 mem = gen_frame_mem (Pmode,
13721 gen_rtx_PLUS (Pmode, stack_top,
13722 GEN_INT (2 * GET_MODE_SIZE (Pmode))));
9ebbca7d 13723 emit_move_insn (opcode_addr, mem);
fc4767bb
JJ
13724 emit_move_insn (opcode, gen_rtx_MEM (SImode, opcode_addr));
13725 emit_move_insn (tocompare, gen_int_mode (TARGET_32BIT ? 0x80410014
2496c7bd 13726 : 0xE8410028, SImode));
9ebbca7d 13727
fc4767bb 13728 do_compare_rtx_and_jump (opcode, tocompare, EQ, 1,
06f4e019 13729 SImode, NULL_RTX, NULL_RTX,
fc4767bb 13730 no_toc_save_needed);
9ebbca7d 13731
8308679f
DE
13732 mem = gen_frame_mem (Pmode,
13733 gen_rtx_PLUS (Pmode, stack_top,
13734 GEN_INT (5 * GET_MODE_SIZE (Pmode))));
fc4767bb
JJ
13735 emit_move_insn (mem, gen_rtx_REG (Pmode, 2));
13736 emit_label (no_toc_save_needed);
9ebbca7d 13737}
38c1f2d7 13738\f
0be76840
DE
13739/* This ties together stack memory (MEM with an alias set of frame_alias_set)
13740 and the change to the stack pointer. */
ba4828e0 13741
9ebbca7d 13742static void
863d938c 13743rs6000_emit_stack_tie (void)
9ebbca7d 13744{
0be76840
DE
13745 rtx mem = gen_frame_mem (BLKmode,
13746 gen_rtx_REG (Pmode, STACK_POINTER_REGNUM));
ba4828e0 13747
9ebbca7d
GK
13748 emit_insn (gen_stack_tie (mem));
13749}
38c1f2d7 13750
9ebbca7d
GK
13751/* Emit the correct code for allocating stack space, as insns.
13752 If COPY_R12, make sure a copy of the old frame is left in r12.
13753 The generated code may use hard register 0 as a temporary. */
13754
13755static void
a2369ed3 13756rs6000_emit_allocate_stack (HOST_WIDE_INT size, int copy_r12)
38c1f2d7 13757{
9ebbca7d
GK
13758 rtx insn;
13759 rtx stack_reg = gen_rtx_REG (Pmode, STACK_POINTER_REGNUM);
13760 rtx tmp_reg = gen_rtx_REG (Pmode, 0);
61168ff1
RS
13761 rtx todec = gen_int_mode (-size, Pmode);
13762
13763 if (INTVAL (todec) != -size)
13764 {
d4ee4d25 13765 warning (0, "stack frame too large");
61168ff1
RS
13766 emit_insn (gen_trap ());
13767 return;
13768 }
a157febd
GK
13769
13770 if (current_function_limit_stack)
13771 {
13772 if (REG_P (stack_limit_rtx)
f676971a 13773 && REGNO (stack_limit_rtx) > 1
a157febd
GK
13774 && REGNO (stack_limit_rtx) <= 31)
13775 {
5b71a4e7 13776 emit_insn (TARGET_32BIT
9ebbca7d
GK
13777 ? gen_addsi3 (tmp_reg,
13778 stack_limit_rtx,
13779 GEN_INT (size))
13780 : gen_adddi3 (tmp_reg,
13781 stack_limit_rtx,
13782 GEN_INT (size)));
5b71a4e7 13783
9ebbca7d
GK
13784 emit_insn (gen_cond_trap (LTU, stack_reg, tmp_reg,
13785 const0_rtx));
a157febd
GK
13786 }
13787 else if (GET_CODE (stack_limit_rtx) == SYMBOL_REF
9ebbca7d 13788 && TARGET_32BIT
f607bc57 13789 && DEFAULT_ABI == ABI_V4)
a157febd 13790 {
9ebbca7d 13791 rtx toload = gen_rtx_CONST (VOIDmode,
f676971a
EC
13792 gen_rtx_PLUS (Pmode,
13793 stack_limit_rtx,
9ebbca7d 13794 GEN_INT (size)));
5b71a4e7 13795
9ebbca7d
GK
13796 emit_insn (gen_elf_high (tmp_reg, toload));
13797 emit_insn (gen_elf_low (tmp_reg, tmp_reg, toload));
13798 emit_insn (gen_cond_trap (LTU, stack_reg, tmp_reg,
13799 const0_rtx));
a157febd
GK
13800 }
13801 else
d4ee4d25 13802 warning (0, "stack limit expression is not supported");
a157febd
GK
13803 }
13804
9ebbca7d
GK
13805 if (copy_r12 || ! TARGET_UPDATE)
13806 emit_move_insn (gen_rtx_REG (Pmode, 12), stack_reg);
13807
38c1f2d7
MM
13808 if (TARGET_UPDATE)
13809 {
9ebbca7d 13810 if (size > 32767)
38c1f2d7 13811 {
9ebbca7d 13812 /* Need a note here so that try_split doesn't get confused. */
9390387d 13813 if (get_last_insn () == NULL_RTX)
2e040219 13814 emit_note (NOTE_INSN_DELETED);
9ebbca7d
GK
13815 insn = emit_move_insn (tmp_reg, todec);
13816 try_split (PATTERN (insn), insn, 0);
13817 todec = tmp_reg;
38c1f2d7 13818 }
5b71a4e7
DE
13819
13820 insn = emit_insn (TARGET_32BIT
13821 ? gen_movsi_update (stack_reg, stack_reg,
13822 todec, stack_reg)
c4ad648e 13823 : gen_movdi_di_update (stack_reg, stack_reg,
9ebbca7d 13824 todec, stack_reg));
38c1f2d7
MM
13825 }
13826 else
13827 {
5b71a4e7
DE
13828 insn = emit_insn (TARGET_32BIT
13829 ? gen_addsi3 (stack_reg, stack_reg, todec)
13830 : gen_adddi3 (stack_reg, stack_reg, todec));
9ebbca7d
GK
13831 emit_move_insn (gen_rtx_MEM (Pmode, stack_reg),
13832 gen_rtx_REG (Pmode, 12));
13833 }
f676971a 13834
9ebbca7d 13835 RTX_FRAME_RELATED_P (insn) = 1;
f676971a 13836 REG_NOTES (insn) =
9ebbca7d 13837 gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
f676971a 13838 gen_rtx_SET (VOIDmode, stack_reg,
9ebbca7d
GK
13839 gen_rtx_PLUS (Pmode, stack_reg,
13840 GEN_INT (-size))),
13841 REG_NOTES (insn));
13842}
13843
a4f6c312
SS
13844/* Add to 'insn' a note which is PATTERN (INSN) but with REG replaced
13845 with (plus:P (reg 1) VAL), and with REG2 replaced with RREG if REG2
13846 is not NULL. It would be nice if dwarf2out_frame_debug_expr could
13847 deduce these equivalences by itself so it wasn't necessary to hold
13848 its hand so much. */
9ebbca7d
GK
13849
13850static void
f676971a 13851rs6000_frame_related (rtx insn, rtx reg, HOST_WIDE_INT val,
a2369ed3 13852 rtx reg2, rtx rreg)
9ebbca7d
GK
13853{
13854 rtx real, temp;
13855
e56c4463
JL
13856 /* copy_rtx will not make unique copies of registers, so we need to
13857 ensure we don't have unwanted sharing here. */
13858 if (reg == reg2)
13859 reg = gen_raw_REG (GET_MODE (reg), REGNO (reg));
13860
13861 if (reg == rreg)
13862 reg = gen_raw_REG (GET_MODE (reg), REGNO (reg));
13863
9ebbca7d
GK
13864 real = copy_rtx (PATTERN (insn));
13865
89e7058f
AH
13866 if (reg2 != NULL_RTX)
13867 real = replace_rtx (real, reg2, rreg);
f676971a
EC
13868
13869 real = replace_rtx (real, reg,
9ebbca7d
GK
13870 gen_rtx_PLUS (Pmode, gen_rtx_REG (Pmode,
13871 STACK_POINTER_REGNUM),
13872 GEN_INT (val)));
f676971a 13873
9ebbca7d
GK
13874 /* We expect that 'real' is either a SET or a PARALLEL containing
13875 SETs (and possibly other stuff). In a PARALLEL, all the SETs
13876 are important so they all have to be marked RTX_FRAME_RELATED_P. */
13877
13878 if (GET_CODE (real) == SET)
13879 {
13880 rtx set = real;
f676971a 13881
9ebbca7d
GK
13882 temp = simplify_rtx (SET_SRC (set));
13883 if (temp)
13884 SET_SRC (set) = temp;
13885 temp = simplify_rtx (SET_DEST (set));
13886 if (temp)
13887 SET_DEST (set) = temp;
13888 if (GET_CODE (SET_DEST (set)) == MEM)
38c1f2d7 13889 {
9ebbca7d
GK
13890 temp = simplify_rtx (XEXP (SET_DEST (set), 0));
13891 if (temp)
13892 XEXP (SET_DEST (set), 0) = temp;
38c1f2d7 13893 }
38c1f2d7 13894 }
37409796 13895 else
9ebbca7d
GK
13896 {
13897 int i;
37409796
NS
13898
13899 gcc_assert (GET_CODE (real) == PARALLEL);
9ebbca7d
GK
13900 for (i = 0; i < XVECLEN (real, 0); i++)
13901 if (GET_CODE (XVECEXP (real, 0, i)) == SET)
13902 {
13903 rtx set = XVECEXP (real, 0, i);
f676971a 13904
9ebbca7d
GK
13905 temp = simplify_rtx (SET_SRC (set));
13906 if (temp)
13907 SET_SRC (set) = temp;
13908 temp = simplify_rtx (SET_DEST (set));
13909 if (temp)
13910 SET_DEST (set) = temp;
13911 if (GET_CODE (SET_DEST (set)) == MEM)
13912 {
13913 temp = simplify_rtx (XEXP (SET_DEST (set), 0));
13914 if (temp)
13915 XEXP (SET_DEST (set), 0) = temp;
13916 }
13917 RTX_FRAME_RELATED_P (set) = 1;
13918 }
13919 }
c19de7aa
AH
13920
13921 if (TARGET_SPE)
13922 real = spe_synthesize_frame_save (real);
13923
9ebbca7d
GK
13924 RTX_FRAME_RELATED_P (insn) = 1;
13925 REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
13926 real,
13927 REG_NOTES (insn));
38c1f2d7
MM
13928}
13929
c19de7aa
AH
13930/* Given an SPE frame note, return a PARALLEL of SETs with the
13931 original note, plus a synthetic register save. */
13932
13933static rtx
a2369ed3 13934spe_synthesize_frame_save (rtx real)
c19de7aa
AH
13935{
13936 rtx synth, offset, reg, real2;
13937
13938 if (GET_CODE (real) != SET
13939 || GET_MODE (SET_SRC (real)) != V2SImode)
13940 return real;
13941
13942 /* For the SPE, registers saved in 64-bits, get a PARALLEL for their
13943 frame related note. The parallel contains a set of the register
41f3a930 13944 being saved, and another set to a synthetic register (n+1200).
c19de7aa
AH
13945 This is so we can differentiate between 64-bit and 32-bit saves.
13946 Words cannot describe this nastiness. */
13947
37409796
NS
13948 gcc_assert (GET_CODE (SET_DEST (real)) == MEM
13949 && GET_CODE (XEXP (SET_DEST (real), 0)) == PLUS
13950 && GET_CODE (SET_SRC (real)) == REG);
c19de7aa
AH
13951
13952 /* Transform:
13953 (set (mem (plus (reg x) (const y)))
13954 (reg z))
13955 into:
13956 (set (mem (plus (reg x) (const y+4)))
41f3a930 13957 (reg z+1200))
c19de7aa
AH
13958 */
13959
13960 real2 = copy_rtx (real);
13961 PUT_MODE (SET_DEST (real2), SImode);
13962 reg = SET_SRC (real2);
13963 real2 = replace_rtx (real2, reg, gen_rtx_REG (SImode, REGNO (reg)));
13964 synth = copy_rtx (real2);
13965
13966 if (BYTES_BIG_ENDIAN)
13967 {
13968 offset = XEXP (XEXP (SET_DEST (real2), 0), 1);
13969 real2 = replace_rtx (real2, offset, GEN_INT (INTVAL (offset) + 4));
13970 }
13971
13972 reg = SET_SRC (synth);
41f3a930 13973
c19de7aa 13974 synth = replace_rtx (synth, reg,
41f3a930 13975 gen_rtx_REG (SImode, REGNO (reg) + 1200));
c19de7aa
AH
13976
13977 offset = XEXP (XEXP (SET_DEST (synth), 0), 1);
13978 synth = replace_rtx (synth, offset,
13979 GEN_INT (INTVAL (offset)
13980 + (BYTES_BIG_ENDIAN ? 0 : 4)));
13981
13982 RTX_FRAME_RELATED_P (synth) = 1;
13983 RTX_FRAME_RELATED_P (real2) = 1;
13984 if (BYTES_BIG_ENDIAN)
13985 real = gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, synth, real2));
13986 else
13987 real = gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, real2, synth));
13988
13989 return real;
13990}
13991
00b960c7
AH
13992/* Returns an insn that has a vrsave set operation with the
13993 appropriate CLOBBERs. */
13994
13995static rtx
a2369ed3 13996generate_set_vrsave (rtx reg, rs6000_stack_t *info, int epiloguep)
00b960c7
AH
13997{
13998 int nclobs, i;
13999 rtx insn, clobs[TOTAL_ALTIVEC_REGS + 1];
a004eb82 14000 rtx vrsave = gen_rtx_REG (SImode, VRSAVE_REGNO);
00b960c7 14001
a004eb82
AH
14002 clobs[0]
14003 = gen_rtx_SET (VOIDmode,
14004 vrsave,
14005 gen_rtx_UNSPEC_VOLATILE (SImode,
14006 gen_rtvec (2, reg, vrsave),
3aca4bff 14007 UNSPECV_SET_VRSAVE));
00b960c7
AH
14008
14009 nclobs = 1;
14010
9aa86737
AH
14011 /* We need to clobber the registers in the mask so the scheduler
14012 does not move sets to VRSAVE before sets of AltiVec registers.
14013
14014 However, if the function receives nonlocal gotos, reload will set
14015 all call saved registers live. We will end up with:
14016
14017 (set (reg 999) (mem))
14018 (parallel [ (set (reg vrsave) (unspec blah))
14019 (clobber (reg 999))])
14020
14021 The clobber will cause the store into reg 999 to be dead, and
14022 flow will attempt to delete an epilogue insn. In this case, we
14023 need an unspec use/set of the register. */
00b960c7
AH
14024
14025 for (i = FIRST_ALTIVEC_REGNO; i <= LAST_ALTIVEC_REGNO; ++i)
44688022 14026 if (info->vrsave_mask & ALTIVEC_REG_BIT (i))
9aa86737
AH
14027 {
14028 if (!epiloguep || call_used_regs [i])
14029 clobs[nclobs++] = gen_rtx_CLOBBER (VOIDmode,
14030 gen_rtx_REG (V4SImode, i));
14031 else
14032 {
14033 rtx reg = gen_rtx_REG (V4SImode, i);
9aa86737
AH
14034
14035 clobs[nclobs++]
a004eb82
AH
14036 = gen_rtx_SET (VOIDmode,
14037 reg,
14038 gen_rtx_UNSPEC (V4SImode,
14039 gen_rtvec (1, reg), 27));
9aa86737
AH
14040 }
14041 }
00b960c7
AH
14042
14043 insn = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (nclobs));
14044
14045 for (i = 0; i < nclobs; ++i)
14046 XVECEXP (insn, 0, i) = clobs[i];
14047
14048 return insn;
14049}
14050
89e7058f
AH
14051/* Save a register into the frame, and emit RTX_FRAME_RELATED_P notes.
14052 Save REGNO into [FRAME_REG + OFFSET] in mode MODE. */
14053
14054static void
f676971a 14055emit_frame_save (rtx frame_reg, rtx frame_ptr, enum machine_mode mode,
d1d0c603 14056 unsigned int regno, int offset, HOST_WIDE_INT total_size)
89e7058f
AH
14057{
14058 rtx reg, offset_rtx, insn, mem, addr, int_rtx;
14059 rtx replacea, replaceb;
14060
14061 int_rtx = GEN_INT (offset);
14062
14063 /* Some cases that need register indexed addressing. */
14064 if ((TARGET_ALTIVEC_ABI && ALTIVEC_VECTOR_MODE (mode))
4d4cbc0e 14065 || (TARGET_E500_DOUBLE && mode == DFmode)
a3170dc6
AH
14066 || (TARGET_SPE_ABI
14067 && SPE_VECTOR_MODE (mode)
14068 && !SPE_CONST_OFFSET_OK (offset)))
89e7058f
AH
14069 {
14070 /* Whomever calls us must make sure r11 is available in the
c4ad648e 14071 flow path of instructions in the prologue. */
89e7058f
AH
14072 offset_rtx = gen_rtx_REG (Pmode, 11);
14073 emit_move_insn (offset_rtx, int_rtx);
14074
14075 replacea = offset_rtx;
14076 replaceb = int_rtx;
14077 }
14078 else
14079 {
14080 offset_rtx = int_rtx;
14081 replacea = NULL_RTX;
14082 replaceb = NULL_RTX;
14083 }
14084
14085 reg = gen_rtx_REG (mode, regno);
14086 addr = gen_rtx_PLUS (Pmode, frame_reg, offset_rtx);
0be76840 14087 mem = gen_frame_mem (mode, addr);
89e7058f
AH
14088
14089 insn = emit_move_insn (mem, reg);
14090
14091 rs6000_frame_related (insn, frame_ptr, total_size, replacea, replaceb);
14092}
14093
a3170dc6
AH
14094/* Emit an offset memory reference suitable for a frame store, while
14095 converting to a valid addressing mode. */
14096
14097static rtx
a2369ed3 14098gen_frame_mem_offset (enum machine_mode mode, rtx reg, int offset)
a3170dc6
AH
14099{
14100 rtx int_rtx, offset_rtx;
14101
14102 int_rtx = GEN_INT (offset);
14103
4d4cbc0e
AH
14104 if ((TARGET_SPE_ABI && SPE_VECTOR_MODE (mode))
14105 || (TARGET_E500_DOUBLE && mode == DFmode))
a3170dc6
AH
14106 {
14107 offset_rtx = gen_rtx_REG (Pmode, FIXED_SCRATCH);
14108 emit_move_insn (offset_rtx, int_rtx);
14109 }
14110 else
14111 offset_rtx = int_rtx;
14112
0be76840 14113 return gen_frame_mem (mode, gen_rtx_PLUS (Pmode, reg, offset_rtx));
a3170dc6
AH
14114}
14115
6d0a8091
DJ
14116/* Look for user-defined global regs. We should not save and restore these,
14117 and cannot use stmw/lmw if there are any in its range. */
14118
14119static bool
14120no_global_regs_above (int first_greg)
14121{
14122 int i;
14123 for (i = 0; i < 32 - first_greg; i++)
14124 if (global_regs[first_greg + i])
14125 return false;
14126 return true;
14127}
14128
699c914a
MS
14129#ifndef TARGET_FIX_AND_CONTINUE
14130#define TARGET_FIX_AND_CONTINUE 0
14131#endif
14132
9ebbca7d
GK
14133/* Emit function prologue as insns. */
14134
9878760c 14135void
863d938c 14136rs6000_emit_prologue (void)
9878760c 14137{
4697a36c 14138 rs6000_stack_t *info = rs6000_stack_info ();
0e67400a 14139 enum machine_mode reg_mode = Pmode;
327e5343 14140 int reg_size = TARGET_32BIT ? 4 : 8;
9ebbca7d
GK
14141 rtx sp_reg_rtx = gen_rtx_REG (Pmode, STACK_POINTER_REGNUM);
14142 rtx frame_ptr_rtx = gen_rtx_REG (Pmode, 12);
14143 rtx frame_reg_rtx = sp_reg_rtx;
b78d48dd 14144 rtx cr_save_rtx = NULL_RTX;
9ebbca7d
GK
14145 rtx insn;
14146 int saving_FPRs_inline;
14147 int using_store_multiple;
14148 HOST_WIDE_INT sp_offset = 0;
f676971a 14149
699c914a
MS
14150 if (TARGET_FIX_AND_CONTINUE)
14151 {
14152 /* gdb on darwin arranges to forward a function from the old
de2ab0ca 14153 address by modifying the first 5 instructions of the function
699c914a
MS
14154 to branch to the overriding function. This is necessary to
14155 permit function pointers that point to the old function to
14156 actually forward to the new function. */
14157 emit_insn (gen_nop ());
14158 emit_insn (gen_nop ());
de2ab0ca 14159 emit_insn (gen_nop ());
699c914a
MS
14160 emit_insn (gen_nop ());
14161 emit_insn (gen_nop ());
14162 }
14163
14164 if (TARGET_SPE_ABI && info->spe_64bit_regs_used != 0)
14165 {
14166 reg_mode = V2SImode;
14167 reg_size = 8;
14168 }
a3170dc6 14169
9ebbca7d 14170 using_store_multiple = (TARGET_MULTIPLE && ! TARGET_POWERPC64
c19de7aa
AH
14171 && (!TARGET_SPE_ABI
14172 || info->spe_64bit_regs_used == 0)
6d0a8091
DJ
14173 && info->first_gp_reg_save < 31
14174 && no_global_regs_above (info->first_gp_reg_save));
9ebbca7d 14175 saving_FPRs_inline = (info->first_fp_reg_save == 64
8c29550d 14176 || FP_SAVE_INLINE (info->first_fp_reg_save)
acd0b319 14177 || current_function_calls_eh_return
8c29550d 14178 || cfun->machine->ra_need_lr);
9ebbca7d
GK
14179
14180 /* For V.4, update stack before we do any saving and set back pointer. */
fc4767bb 14181 if (info->push_p
acd0b319
AM
14182 && (DEFAULT_ABI == ABI_V4
14183 || current_function_calls_eh_return))
9ebbca7d
GK
14184 {
14185 if (info->total_size < 32767)
14186 sp_offset = info->total_size;
14187 else
14188 frame_reg_rtx = frame_ptr_rtx;
f676971a 14189 rs6000_emit_allocate_stack (info->total_size,
9ebbca7d
GK
14190 (frame_reg_rtx != sp_reg_rtx
14191 && (info->cr_save_p
14192 || info->lr_save_p
14193 || info->first_fp_reg_save < 64
14194 || info->first_gp_reg_save < 32
14195 )));
14196 if (frame_reg_rtx != sp_reg_rtx)
14197 rs6000_emit_stack_tie ();
14198 }
14199
d62294f5 14200 /* Handle world saves specially here. */
f57fe068 14201 if (WORLD_SAVE_P (info))
d62294f5
FJ
14202 {
14203 int i, j, sz;
14204 rtx treg;
14205 rtvec p;
14206
14207 /* save_world expects lr in r0. */
14208 if (info->lr_save_p)
c4ad648e
AM
14209 {
14210 insn = emit_move_insn (gen_rtx_REG (Pmode, 0),
14211 gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM));
14212 RTX_FRAME_RELATED_P (insn) = 1;
14213 }
d62294f5
FJ
14214
14215 /* The SAVE_WORLD and RESTORE_WORLD routines make a number of
c4ad648e 14216 assumptions about the offsets of various bits of the stack
992d08b1 14217 frame. */
37409796
NS
14218 gcc_assert (info->gp_save_offset == -220
14219 && info->fp_save_offset == -144
14220 && info->lr_save_offset == 8
14221 && info->cr_save_offset == 4
14222 && info->push_p
14223 && info->lr_save_p
14224 && (!current_function_calls_eh_return
14225 || info->ehrd_offset == -432)
14226 && info->vrsave_save_offset == -224
14227 && info->altivec_save_offset == (-224 -16 -192));
d62294f5
FJ
14228
14229 treg = gen_rtx_REG (SImode, 11);
14230 emit_move_insn (treg, GEN_INT (-info->total_size));
14231
14232 /* SAVE_WORLD takes the caller's LR in R0 and the frame size
c4ad648e 14233 in R11. It also clobbers R12, so beware! */
d62294f5
FJ
14234
14235 /* Preserve CR2 for save_world prologues */
14236 sz = 6;
14237 sz += 32 - info->first_gp_reg_save;
14238 sz += 64 - info->first_fp_reg_save;
14239 sz += LAST_ALTIVEC_REGNO - info->first_altivec_reg_save + 1;
14240 p = rtvec_alloc (sz);
14241 j = 0;
14242 RTVEC_ELT (p, j++) = gen_rtx_CLOBBER (VOIDmode,
c4ad648e
AM
14243 gen_rtx_REG (Pmode,
14244 LINK_REGISTER_REGNUM));
d62294f5 14245 RTVEC_ELT (p, j++) = gen_rtx_USE (VOIDmode,
c4ad648e
AM
14246 gen_rtx_SYMBOL_REF (Pmode,
14247 "*save_world"));
d62294f5 14248 /* We do floats first so that the instruction pattern matches
c4ad648e
AM
14249 properly. */
14250 for (i = 0; i < 64 - info->first_fp_reg_save; i++)
14251 {
14252 rtx reg = gen_rtx_REG (DFmode, info->first_fp_reg_save + i);
14253 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14254 GEN_INT (info->fp_save_offset
14255 + sp_offset + 8 * i));
0be76840 14256 rtx mem = gen_frame_mem (DFmode, addr);
c4ad648e
AM
14257
14258 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, mem, reg);
14259 }
d62294f5 14260 for (i = 0; info->first_altivec_reg_save + i <= LAST_ALTIVEC_REGNO; i++)
c4ad648e
AM
14261 {
14262 rtx reg = gen_rtx_REG (V4SImode, info->first_altivec_reg_save + i);
14263 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14264 GEN_INT (info->altivec_save_offset
14265 + sp_offset + 16 * i));
0be76840 14266 rtx mem = gen_frame_mem (V4SImode, addr);
c4ad648e
AM
14267
14268 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, mem, reg);
14269 }
d62294f5 14270 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
c4ad648e
AM
14271 {
14272 rtx reg = gen_rtx_REG (reg_mode, info->first_gp_reg_save + i);
14273 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14274 GEN_INT (info->gp_save_offset
14275 + sp_offset + reg_size * i));
0be76840 14276 rtx mem = gen_frame_mem (reg_mode, addr);
c4ad648e
AM
14277
14278 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, mem, reg);
14279 }
14280
14281 {
14282 /* CR register traditionally saved as CR2. */
14283 rtx reg = gen_rtx_REG (reg_mode, CR2_REGNO);
14284 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14285 GEN_INT (info->cr_save_offset
14286 + sp_offset));
0be76840 14287 rtx mem = gen_frame_mem (reg_mode, addr);
c4ad648e
AM
14288
14289 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, mem, reg);
14290 }
d62294f5
FJ
14291 /* Prevent any attempt to delete the setting of r0 and treg! */
14292 RTVEC_ELT (p, j++) = gen_rtx_USE (VOIDmode, gen_rtx_REG (Pmode, 0));
14293 RTVEC_ELT (p, j++) = gen_rtx_USE (VOIDmode, treg);
14294 RTVEC_ELT (p, j++) = gen_rtx_CLOBBER (VOIDmode, sp_reg_rtx);
14295
14296 insn = emit_insn (gen_rtx_PARALLEL (VOIDmode, p));
14297 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
c4ad648e 14298 NULL_RTX, NULL_RTX);
d62294f5
FJ
14299
14300 if (current_function_calls_eh_return)
c4ad648e
AM
14301 {
14302 unsigned int i;
14303 for (i = 0; ; ++i)
14304 {
14305 unsigned int regno = EH_RETURN_DATA_REGNO (i);
14306 if (regno == INVALID_REGNUM)
14307 break;
14308 emit_frame_save (frame_reg_rtx, frame_ptr_rtx, reg_mode, regno,
14309 info->ehrd_offset + sp_offset
14310 + reg_size * (int) i,
14311 info->total_size);
14312 }
14313 }
d62294f5
FJ
14314 }
14315
9aa86737 14316 /* Save AltiVec registers if needed. */
f57fe068 14317 if (!WORLD_SAVE_P (info) && TARGET_ALTIVEC_ABI && info->altivec_size != 0)
9aa86737
AH
14318 {
14319 int i;
14320
14321 /* There should be a non inline version of this, for when we
14322 are saving lots of vector registers. */
14323 for (i = info->first_altivec_reg_save; i <= LAST_ALTIVEC_REGNO; ++i)
14324 if (info->vrsave_mask & ALTIVEC_REG_BIT (i))
14325 {
14326 rtx areg, savereg, mem;
14327 int offset;
14328
14329 offset = info->altivec_save_offset + sp_offset
14330 + 16 * (i - info->first_altivec_reg_save);
14331
14332 savereg = gen_rtx_REG (V4SImode, i);
14333
14334 areg = gen_rtx_REG (Pmode, 0);
14335 emit_move_insn (areg, GEN_INT (offset));
14336
14337 /* AltiVec addressing mode is [reg+reg]. */
0be76840
DE
14338 mem = gen_frame_mem (V4SImode,
14339 gen_rtx_PLUS (Pmode, frame_reg_rtx, areg));
9aa86737
AH
14340
14341 insn = emit_move_insn (mem, savereg);
14342
5c242421
SB
14343 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
14344 areg, GEN_INT (offset));
9aa86737
AH
14345 }
14346 }
14347
14348 /* VRSAVE is a bit vector representing which AltiVec registers
14349 are used. The OS uses this to determine which vector
14350 registers to save on a context switch. We need to save
14351 VRSAVE on the stack frame, add whatever AltiVec registers we
14352 used in this function, and do the corresponding magic in the
14353 epilogue. */
14354
4d774ff8 14355 if (TARGET_ALTIVEC && TARGET_ALTIVEC_VRSAVE
bcb604b6 14356 && info->vrsave_mask != 0)
9aa86737 14357 {
a004eb82 14358 rtx reg, mem, vrsave;
9aa86737
AH
14359 int offset;
14360
eab97e44
AM
14361 /* Get VRSAVE onto a GPR. Note that ABI_V4 might be using r12
14362 as frame_reg_rtx and r11 as the static chain pointer for
14363 nested functions. */
14364 reg = gen_rtx_REG (SImode, 0);
a004eb82 14365 vrsave = gen_rtx_REG (SImode, VRSAVE_REGNO);
b188f760
AH
14366 if (TARGET_MACHO)
14367 emit_insn (gen_get_vrsave_internal (reg));
14368 else
14369 emit_insn (gen_rtx_SET (VOIDmode, reg, vrsave));
9aa86737 14370
bcb604b6
FJ
14371 if (!WORLD_SAVE_P (info))
14372 {
14373 /* Save VRSAVE. */
14374 offset = info->vrsave_save_offset + sp_offset;
0be76840
DE
14375 mem = gen_frame_mem (SImode,
14376 gen_rtx_PLUS (Pmode, frame_reg_rtx,
14377 GEN_INT (offset)));
bcb604b6
FJ
14378 insn = emit_move_insn (mem, reg);
14379 }
9aa86737
AH
14380
14381 /* Include the registers in the mask. */
14382 emit_insn (gen_iorsi3 (reg, reg, GEN_INT ((int) info->vrsave_mask)));
14383
14384 insn = emit_insn (generate_set_vrsave (reg, info, 0));
14385 }
14386
9ebbca7d 14387 /* If we use the link register, get it into r0. */
f57fe068 14388 if (!WORLD_SAVE_P (info) && info->lr_save_p)
f8a57be8
GK
14389 {
14390 insn = emit_move_insn (gen_rtx_REG (Pmode, 0),
14391 gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM));
14392 RTX_FRAME_RELATED_P (insn) = 1;
14393 }
9ebbca7d
GK
14394
14395 /* If we need to save CR, put it into r12. */
f57fe068 14396 if (!WORLD_SAVE_P (info) && info->cr_save_p && frame_reg_rtx != frame_ptr_rtx)
9ebbca7d 14397 {
f8a57be8 14398 rtx set;
f676971a 14399
9ebbca7d 14400 cr_save_rtx = gen_rtx_REG (SImode, 12);
f8a57be8
GK
14401 insn = emit_insn (gen_movesi_from_cr (cr_save_rtx));
14402 RTX_FRAME_RELATED_P (insn) = 1;
14403 /* Now, there's no way that dwarf2out_frame_debug_expr is going
14404 to understand '(unspec:SI [(reg:CC 68) ...] UNSPEC_MOVESI_FROM_CR)'.
14405 But that's OK. All we have to do is specify that _one_ condition
14406 code register is saved in this stack slot. The thrower's epilogue
14407 will then restore all the call-saved registers.
14408 We use CR2_REGNO (70) to be compatible with gcc-2.95 on Linux. */
14409 set = gen_rtx_SET (VOIDmode, cr_save_rtx,
14410 gen_rtx_REG (SImode, CR2_REGNO));
14411 REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
14412 set,
14413 REG_NOTES (insn));
9ebbca7d
GK
14414 }
14415
a4f6c312
SS
14416 /* Do any required saving of fpr's. If only one or two to save, do
14417 it ourselves. Otherwise, call function. */
f57fe068 14418 if (!WORLD_SAVE_P (info) && saving_FPRs_inline)
9ebbca7d
GK
14419 {
14420 int i;
14421 for (i = 0; i < 64 - info->first_fp_reg_save; i++)
f676971a 14422 if ((regs_ever_live[info->first_fp_reg_save+i]
9ebbca7d 14423 && ! call_used_regs[info->first_fp_reg_save+i]))
89e7058f
AH
14424 emit_frame_save (frame_reg_rtx, frame_ptr_rtx, DFmode,
14425 info->first_fp_reg_save + i,
14426 info->fp_save_offset + sp_offset + 8 * i,
14427 info->total_size);
9ebbca7d 14428 }
f57fe068 14429 else if (!WORLD_SAVE_P (info) && info->first_fp_reg_save != 64)
9ebbca7d
GK
14430 {
14431 int i;
14432 char rname[30];
520a57c8 14433 const char *alloc_rname;
9ebbca7d
GK
14434 rtvec p;
14435 p = rtvec_alloc (2 + 64 - info->first_fp_reg_save);
f676971a
EC
14436
14437 RTVEC_ELT (p, 0) = gen_rtx_CLOBBER (VOIDmode,
14438 gen_rtx_REG (Pmode,
9ebbca7d
GK
14439 LINK_REGISTER_REGNUM));
14440 sprintf (rname, "%s%d%s", SAVE_FP_PREFIX,
14441 info->first_fp_reg_save - 32, SAVE_FP_SUFFIX);
a8a05998 14442 alloc_rname = ggc_strdup (rname);
9ebbca7d
GK
14443 RTVEC_ELT (p, 1) = gen_rtx_USE (VOIDmode,
14444 gen_rtx_SYMBOL_REF (Pmode,
14445 alloc_rname));
14446 for (i = 0; i < 64 - info->first_fp_reg_save; i++)
14447 {
14448 rtx addr, reg, mem;
14449 reg = gen_rtx_REG (DFmode, info->first_fp_reg_save + i);
14450 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
f676971a 14451 GEN_INT (info->fp_save_offset
9ebbca7d 14452 + sp_offset + 8*i));
0be76840 14453 mem = gen_frame_mem (DFmode, addr);
9ebbca7d
GK
14454
14455 RTVEC_ELT (p, i + 2) = gen_rtx_SET (VOIDmode, mem, reg);
14456 }
14457 insn = emit_insn (gen_rtx_PARALLEL (VOIDmode, p));
f676971a 14458 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
9ebbca7d
GK
14459 NULL_RTX, NULL_RTX);
14460 }
b6c9286a 14461
9ebbca7d
GK
14462 /* Save GPRs. This is done as a PARALLEL if we are using
14463 the store-multiple instructions. */
f57fe068 14464 if (!WORLD_SAVE_P (info) && using_store_multiple)
b6c9286a 14465 {
308c142a 14466 rtvec p;
9ebbca7d
GK
14467 int i;
14468 p = rtvec_alloc (32 - info->first_gp_reg_save);
9ebbca7d
GK
14469 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
14470 {
14471 rtx addr, reg, mem;
14472 reg = gen_rtx_REG (reg_mode, info->first_gp_reg_save + i);
f676971a
EC
14473 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14474 GEN_INT (info->gp_save_offset
14475 + sp_offset
9ebbca7d 14476 + reg_size * i));
0be76840 14477 mem = gen_frame_mem (reg_mode, addr);
9ebbca7d
GK
14478
14479 RTVEC_ELT (p, i) = gen_rtx_SET (VOIDmode, mem, reg);
14480 }
14481 insn = emit_insn (gen_rtx_PARALLEL (VOIDmode, p));
f676971a 14482 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
9ebbca7d 14483 NULL_RTX, NULL_RTX);
b6c9286a 14484 }
f57fe068 14485 else if (!WORLD_SAVE_P (info))
b6c9286a 14486 {
9ebbca7d
GK
14487 int i;
14488 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
6d0a8091
DJ
14489 if ((regs_ever_live[info->first_gp_reg_save + i]
14490 && (!call_used_regs[info->first_gp_reg_save + i]
14491 || (i + info->first_gp_reg_save
b4db40bf
JJ
14492 == RS6000_PIC_OFFSET_TABLE_REGNUM
14493 && TARGET_TOC && TARGET_MINIMAL_TOC)))
6d0a8091 14494 || (i + info->first_gp_reg_save == RS6000_PIC_OFFSET_TABLE_REGNUM
14f00213 14495 && ((DEFAULT_ABI == ABI_V4 && flag_pic != 0)
f607bc57 14496 || (DEFAULT_ABI == ABI_DARWIN && flag_pic))))
a3170dc6
AH
14497 {
14498 rtx addr, reg, mem;
14499 reg = gen_rtx_REG (reg_mode, info->first_gp_reg_save + i);
14500
c19de7aa 14501 if (TARGET_SPE_ABI && info->spe_64bit_regs_used != 0)
a3170dc6
AH
14502 {
14503 int offset = info->spe_gp_save_offset + sp_offset + 8 * i;
14504 rtx b;
14505
14506 if (!SPE_CONST_OFFSET_OK (offset))
14507 {
14508 b = gen_rtx_REG (Pmode, FIXED_SCRATCH);
14509 emit_move_insn (b, GEN_INT (offset));
14510 }
14511 else
14512 b = GEN_INT (offset);
14513
14514 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx, b);
0be76840 14515 mem = gen_frame_mem (V2SImode, addr);
a3170dc6
AH
14516 insn = emit_move_insn (mem, reg);
14517
14518 if (GET_CODE (b) == CONST_INT)
14519 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
14520 NULL_RTX, NULL_RTX);
14521 else
14522 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
14523 b, GEN_INT (offset));
14524 }
14525 else
14526 {
f676971a
EC
14527 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14528 GEN_INT (info->gp_save_offset
14529 + sp_offset
a3170dc6 14530 + reg_size * i));
0be76840 14531 mem = gen_frame_mem (reg_mode, addr);
a3170dc6
AH
14532
14533 insn = emit_move_insn (mem, reg);
f676971a 14534 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
a3170dc6
AH
14535 NULL_RTX, NULL_RTX);
14536 }
14537 }
9ebbca7d
GK
14538 }
14539
83720594
RH
14540 /* ??? There's no need to emit actual instructions here, but it's the
14541 easiest way to get the frame unwind information emitted. */
f57fe068 14542 if (!WORLD_SAVE_P (info) && current_function_calls_eh_return)
83720594 14543 {
78e1b90d
DE
14544 unsigned int i, regno;
14545
fc4767bb
JJ
14546 /* In AIX ABI we need to pretend we save r2 here. */
14547 if (TARGET_AIX)
14548 {
14549 rtx addr, reg, mem;
14550
14551 reg = gen_rtx_REG (reg_mode, 2);
14552 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14553 GEN_INT (sp_offset + 5 * reg_size));
0be76840 14554 mem = gen_frame_mem (reg_mode, addr);
fc4767bb
JJ
14555
14556 insn = emit_move_insn (mem, reg);
f676971a 14557 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
fc4767bb
JJ
14558 NULL_RTX, NULL_RTX);
14559 PATTERN (insn) = gen_blockage ();
14560 }
14561
83720594
RH
14562 for (i = 0; ; ++i)
14563 {
83720594
RH
14564 regno = EH_RETURN_DATA_REGNO (i);
14565 if (regno == INVALID_REGNUM)
14566 break;
14567
89e7058f
AH
14568 emit_frame_save (frame_reg_rtx, frame_ptr_rtx, reg_mode, regno,
14569 info->ehrd_offset + sp_offset
14570 + reg_size * (int) i,
14571 info->total_size);
83720594
RH
14572 }
14573 }
14574
9ebbca7d 14575 /* Save lr if we used it. */
f57fe068 14576 if (!WORLD_SAVE_P (info) && info->lr_save_p)
9ebbca7d
GK
14577 {
14578 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14579 GEN_INT (info->lr_save_offset + sp_offset));
14580 rtx reg = gen_rtx_REG (Pmode, 0);
14581 rtx mem = gen_rtx_MEM (Pmode, addr);
0be76840 14582 /* This should not be of frame_alias_set, because of
9ebbca7d 14583 __builtin_return_address. */
f676971a 14584
9ebbca7d 14585 insn = emit_move_insn (mem, reg);
f676971a 14586 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
f8a57be8 14587 NULL_RTX, NULL_RTX);
9ebbca7d
GK
14588 }
14589
14590 /* Save CR if we use any that must be preserved. */
f57fe068 14591 if (!WORLD_SAVE_P (info) && info->cr_save_p)
9ebbca7d
GK
14592 {
14593 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14594 GEN_INT (info->cr_save_offset + sp_offset));
0be76840 14595 rtx mem = gen_frame_mem (SImode, addr);
f8a57be8
GK
14596 /* See the large comment above about why CR2_REGNO is used. */
14597 rtx magic_eh_cr_reg = gen_rtx_REG (SImode, CR2_REGNO);
ba4828e0 14598
9ebbca7d
GK
14599 /* If r12 was used to hold the original sp, copy cr into r0 now
14600 that it's free. */
14601 if (REGNO (frame_reg_rtx) == 12)
14602 {
f8a57be8
GK
14603 rtx set;
14604
9ebbca7d 14605 cr_save_rtx = gen_rtx_REG (SImode, 0);
f8a57be8
GK
14606 insn = emit_insn (gen_movesi_from_cr (cr_save_rtx));
14607 RTX_FRAME_RELATED_P (insn) = 1;
14608 set = gen_rtx_SET (VOIDmode, cr_save_rtx, magic_eh_cr_reg);
14609 REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
14610 set,
14611 REG_NOTES (insn));
f676971a 14612
9ebbca7d
GK
14613 }
14614 insn = emit_move_insn (mem, cr_save_rtx);
14615
f676971a 14616 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
f8a57be8 14617 NULL_RTX, NULL_RTX);
9ebbca7d
GK
14618 }
14619
f676971a 14620 /* Update stack and set back pointer unless this is V.4,
9ebbca7d 14621 for which it was done previously. */
f57fe068 14622 if (!WORLD_SAVE_P (info) && info->push_p
fc4767bb 14623 && !(DEFAULT_ABI == ABI_V4 || current_function_calls_eh_return))
9ebbca7d
GK
14624 rs6000_emit_allocate_stack (info->total_size, FALSE);
14625
14626 /* Set frame pointer, if needed. */
14627 if (frame_pointer_needed)
14628 {
7d5175e1 14629 insn = emit_move_insn (gen_rtx_REG (Pmode, HARD_FRAME_POINTER_REGNUM),
9ebbca7d
GK
14630 sp_reg_rtx);
14631 RTX_FRAME_RELATED_P (insn) = 1;
b6c9286a 14632 }
9878760c 14633
1db02437 14634 /* If we are using RS6000_PIC_OFFSET_TABLE_REGNUM, we need to set it up. */
9ebbca7d 14635 if ((TARGET_TOC && TARGET_MINIMAL_TOC && get_pool_size () != 0)
7f970b70
AM
14636 || (DEFAULT_ABI == ABI_V4
14637 && (flag_pic == 1 || (flag_pic && TARGET_SECURE_PLT))
1db02437 14638 && regs_ever_live[RS6000_PIC_OFFSET_TABLE_REGNUM]))
c4ad648e
AM
14639 {
14640 /* If emit_load_toc_table will use the link register, we need to save
14641 it. We use R12 for this purpose because emit_load_toc_table
14642 can use register 0. This allows us to use a plain 'blr' to return
14643 from the procedure more often. */
14644 int save_LR_around_toc_setup = (TARGET_ELF
14645 && DEFAULT_ABI != ABI_AIX
14646 && flag_pic
14647 && ! info->lr_save_p
14648 && EDGE_COUNT (EXIT_BLOCK_PTR->preds) > 0);
14649 if (save_LR_around_toc_setup)
14650 {
14651 rtx lr = gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM);
f8a57be8 14652
c4ad648e
AM
14653 insn = emit_move_insn (frame_ptr_rtx, lr);
14654 rs6000_maybe_dead (insn);
14655 RTX_FRAME_RELATED_P (insn) = 1;
f8a57be8 14656
c4ad648e 14657 rs6000_emit_load_toc_table (TRUE);
f8a57be8 14658
c4ad648e
AM
14659 insn = emit_move_insn (lr, frame_ptr_rtx);
14660 rs6000_maybe_dead (insn);
14661 RTX_FRAME_RELATED_P (insn) = 1;
14662 }
14663 else
14664 rs6000_emit_load_toc_table (TRUE);
14665 }
ee890fe2 14666
fcce224d 14667#if TARGET_MACHO
ee890fe2
SS
14668 if (DEFAULT_ABI == ABI_DARWIN
14669 && flag_pic && current_function_uses_pic_offset_table)
14670 {
f8a57be8 14671 rtx lr = gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM);
11abc112 14672 rtx src = machopic_function_base_sym ();
ee890fe2 14673
6d0a8091
DJ
14674 /* Save and restore LR locally around this call (in R0). */
14675 if (!info->lr_save_p)
14676 rs6000_maybe_dead (emit_move_insn (gen_rtx_REG (Pmode, 0), lr));
14677
f8a57be8 14678 rs6000_maybe_dead (emit_insn (gen_load_macho_picbase (lr, src)));
ee890fe2 14679
f676971a 14680 insn = emit_move_insn (gen_rtx_REG (Pmode,
f8a57be8
GK
14681 RS6000_PIC_OFFSET_TABLE_REGNUM),
14682 lr);
14683 rs6000_maybe_dead (insn);
6d0a8091
DJ
14684
14685 if (!info->lr_save_p)
14686 rs6000_maybe_dead (emit_move_insn (lr, gen_rtx_REG (Pmode, 0)));
ee890fe2 14687 }
fcce224d 14688#endif
9ebbca7d
GK
14689}
14690
9ebbca7d 14691/* Write function prologue. */
a4f6c312 14692
08c148a8 14693static void
f676971a 14694rs6000_output_function_prologue (FILE *file,
a2369ed3 14695 HOST_WIDE_INT size ATTRIBUTE_UNUSED)
9ebbca7d
GK
14696{
14697 rs6000_stack_t *info = rs6000_stack_info ();
14698
4697a36c
MM
14699 if (TARGET_DEBUG_STACK)
14700 debug_stack_info (info);
9878760c 14701
a4f6c312
SS
14702 /* Write .extern for any function we will call to save and restore
14703 fp values. */
14704 if (info->first_fp_reg_save < 64
14705 && !FP_SAVE_INLINE (info->first_fp_reg_save))
4d30c363 14706 fprintf (file, "\t.extern %s%d%s\n\t.extern %s%d%s\n",
4697a36c 14707 SAVE_FP_PREFIX, info->first_fp_reg_save - 32, SAVE_FP_SUFFIX,
a4f6c312
SS
14708 RESTORE_FP_PREFIX, info->first_fp_reg_save - 32,
14709 RESTORE_FP_SUFFIX);
9878760c 14710
c764f757
RK
14711 /* Write .extern for AIX common mode routines, if needed. */
14712 if (! TARGET_POWER && ! TARGET_POWERPC && ! common_mode_defined)
14713 {
f6709c70
JW
14714 fputs ("\t.extern __mulh\n", file);
14715 fputs ("\t.extern __mull\n", file);
14716 fputs ("\t.extern __divss\n", file);
14717 fputs ("\t.extern __divus\n", file);
14718 fputs ("\t.extern __quoss\n", file);
14719 fputs ("\t.extern __quous\n", file);
c764f757
RK
14720 common_mode_defined = 1;
14721 }
9878760c 14722
9ebbca7d 14723 if (! HAVE_prologue)
979721f8 14724 {
9ebbca7d 14725 start_sequence ();
9dda4cc8 14726
a4f6c312
SS
14727 /* A NOTE_INSN_DELETED is supposed to be at the start and end of
14728 the "toplevel" insn chain. */
2e040219 14729 emit_note (NOTE_INSN_DELETED);
9ebbca7d 14730 rs6000_emit_prologue ();
2e040219 14731 emit_note (NOTE_INSN_DELETED);
178c3eff 14732
a3c9585f 14733 /* Expand INSN_ADDRESSES so final() doesn't crash. */
178c3eff
DJ
14734 {
14735 rtx insn;
14736 unsigned addr = 0;
14737 for (insn = get_insns (); insn != 0; insn = NEXT_INSN (insn))
14738 {
14739 INSN_ADDRESSES_NEW (insn, addr);
14740 addr += 4;
14741 }
14742 }
9dda4cc8 14743
9ebbca7d 14744 if (TARGET_DEBUG_STACK)
a4f6c312 14745 debug_rtx_list (get_insns (), 100);
c9d691e9 14746 final (get_insns (), file, FALSE);
9ebbca7d 14747 end_sequence ();
979721f8
MM
14748 }
14749
9ebbca7d
GK
14750 rs6000_pic_labelno++;
14751}
f676971a 14752
9ebbca7d 14753/* Emit function epilogue as insns.
9878760c 14754
9ebbca7d
GK
14755 At present, dwarf2out_frame_debug_expr doesn't understand
14756 register restores, so we don't bother setting RTX_FRAME_RELATED_P
14757 anywhere in the epilogue. Most of the insns below would in any case
14758 need special notes to explain where r11 is in relation to the stack. */
9878760c 14759
9ebbca7d 14760void
a2369ed3 14761rs6000_emit_epilogue (int sibcall)
9ebbca7d
GK
14762{
14763 rs6000_stack_t *info;
14764 int restoring_FPRs_inline;
14765 int using_load_multiple;
14766 int using_mfcr_multiple;
14767 int use_backchain_to_restore_sp;
14768 int sp_offset = 0;
14769 rtx sp_reg_rtx = gen_rtx_REG (Pmode, 1);
14770 rtx frame_reg_rtx = sp_reg_rtx;
0e67400a 14771 enum machine_mode reg_mode = Pmode;
327e5343 14772 int reg_size = TARGET_32BIT ? 4 : 8;
9ebbca7d
GK
14773 int i;
14774
c19de7aa
AH
14775 info = rs6000_stack_info ();
14776
14777 if (TARGET_SPE_ABI && info->spe_64bit_regs_used != 0)
a3170dc6
AH
14778 {
14779 reg_mode = V2SImode;
14780 reg_size = 8;
14781 }
14782
9ebbca7d 14783 using_load_multiple = (TARGET_MULTIPLE && ! TARGET_POWERPC64
c19de7aa
AH
14784 && (!TARGET_SPE_ABI
14785 || info->spe_64bit_regs_used == 0)
6d0a8091
DJ
14786 && info->first_gp_reg_save < 31
14787 && no_global_regs_above (info->first_gp_reg_save));
9ebbca7d 14788 restoring_FPRs_inline = (sibcall
83720594 14789 || current_function_calls_eh_return
9ebbca7d
GK
14790 || info->first_fp_reg_save == 64
14791 || FP_SAVE_INLINE (info->first_fp_reg_save));
f676971a 14792 use_backchain_to_restore_sp = (frame_pointer_needed
9ebbca7d
GK
14793 || current_function_calls_alloca
14794 || info->total_size > 32767);
14795 using_mfcr_multiple = (rs6000_cpu == PROCESSOR_PPC601
14796 || rs6000_cpu == PROCESSOR_PPC603
14797 || rs6000_cpu == PROCESSOR_PPC750
14798 || optimize_size);
14799
f57fe068 14800 if (WORLD_SAVE_P (info))
d62294f5
FJ
14801 {
14802 int i, j;
14803 char rname[30];
14804 const char *alloc_rname;
14805 rtvec p;
14806
14807 /* eh_rest_world_r10 will return to the location saved in the LR
c4ad648e
AM
14808 stack slot (which is not likely to be our caller.)
14809 Input: R10 -- stack adjustment. Clobbers R0, R11, R12, R7, R8.
14810 rest_world is similar, except any R10 parameter is ignored.
14811 The exception-handling stuff that was here in 2.95 is no
14812 longer necessary. */
d62294f5
FJ
14813
14814 p = rtvec_alloc (9
14815 + 1
f676971a 14816 + 32 - info->first_gp_reg_save
c4ad648e
AM
14817 + LAST_ALTIVEC_REGNO + 1 - info->first_altivec_reg_save
14818 + 63 + 1 - info->first_fp_reg_save);
d62294f5 14819
c4ad648e
AM
14820 strcpy (rname, ((current_function_calls_eh_return) ?
14821 "*eh_rest_world_r10" : "*rest_world"));
d62294f5
FJ
14822 alloc_rname = ggc_strdup (rname);
14823
14824 j = 0;
14825 RTVEC_ELT (p, j++) = gen_rtx_RETURN (VOIDmode);
14826 RTVEC_ELT (p, j++) = gen_rtx_USE (VOIDmode,
c4ad648e
AM
14827 gen_rtx_REG (Pmode,
14828 LINK_REGISTER_REGNUM));
d62294f5 14829 RTVEC_ELT (p, j++)
c4ad648e 14830 = gen_rtx_USE (VOIDmode, gen_rtx_SYMBOL_REF (Pmode, alloc_rname));
d62294f5 14831 /* The instruction pattern requires a clobber here;
c4ad648e 14832 it is shared with the restVEC helper. */
d62294f5 14833 RTVEC_ELT (p, j++)
c4ad648e 14834 = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 11));
d62294f5
FJ
14835
14836 {
c4ad648e
AM
14837 /* CR register traditionally saved as CR2. */
14838 rtx reg = gen_rtx_REG (reg_mode, CR2_REGNO);
14839 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14840 GEN_INT (info->cr_save_offset));
0be76840 14841 rtx mem = gen_frame_mem (reg_mode, addr);
c4ad648e
AM
14842
14843 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, reg, mem);
d62294f5
FJ
14844 }
14845
14846 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
c4ad648e
AM
14847 {
14848 rtx reg = gen_rtx_REG (reg_mode, info->first_gp_reg_save + i);
14849 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14850 GEN_INT (info->gp_save_offset
14851 + reg_size * i));
0be76840 14852 rtx mem = gen_frame_mem (reg_mode, addr);
c4ad648e
AM
14853
14854 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, reg, mem);
14855 }
d62294f5 14856 for (i = 0; info->first_altivec_reg_save + i <= LAST_ALTIVEC_REGNO; i++)
c4ad648e
AM
14857 {
14858 rtx reg = gen_rtx_REG (V4SImode, info->first_altivec_reg_save + i);
14859 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14860 GEN_INT (info->altivec_save_offset
14861 + 16 * i));
0be76840 14862 rtx mem = gen_frame_mem (V4SImode, addr);
c4ad648e
AM
14863
14864 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, reg, mem);
14865 }
d62294f5 14866 for (i = 0; info->first_fp_reg_save + i <= 63; i++)
c4ad648e
AM
14867 {
14868 rtx reg = gen_rtx_REG (DFmode, info->first_fp_reg_save + i);
14869 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14870 GEN_INT (info->fp_save_offset
14871 + 8 * i));
0be76840 14872 rtx mem = gen_frame_mem (DFmode, addr);
c4ad648e
AM
14873
14874 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, reg, mem);
14875 }
d62294f5 14876 RTVEC_ELT (p, j++)
c4ad648e 14877 = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 0));
d62294f5 14878 RTVEC_ELT (p, j++)
c4ad648e 14879 = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (SImode, 12));
d62294f5 14880 RTVEC_ELT (p, j++)
c4ad648e 14881 = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (SImode, 7));
d62294f5 14882 RTVEC_ELT (p, j++)
c4ad648e 14883 = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (SImode, 8));
d62294f5 14884 RTVEC_ELT (p, j++)
c4ad648e 14885 = gen_rtx_USE (VOIDmode, gen_rtx_REG (SImode, 10));
d62294f5
FJ
14886 emit_jump_insn (gen_rtx_PARALLEL (VOIDmode, p));
14887
14888 return;
14889 }
14890
9ebbca7d
GK
14891 /* If we have a frame pointer, a call to alloca, or a large stack
14892 frame, restore the old stack pointer using the backchain. Otherwise,
14893 we know what size to update it with. */
14894 if (use_backchain_to_restore_sp)
bacbde18 14895 {
9ebbca7d
GK
14896 /* Under V.4, don't reset the stack pointer until after we're done
14897 loading the saved registers. */
f607bc57 14898 if (DEFAULT_ABI == ABI_V4)
9ebbca7d 14899 frame_reg_rtx = gen_rtx_REG (Pmode, 11);
4697a36c 14900
9ebbca7d
GK
14901 emit_move_insn (frame_reg_rtx,
14902 gen_rtx_MEM (Pmode, sp_reg_rtx));
bacbde18 14903 }
9ebbca7d 14904 else if (info->push_p)
85638c0d 14905 {
fc4767bb
JJ
14906 if (DEFAULT_ABI == ABI_V4
14907 || current_function_calls_eh_return)
9ebbca7d
GK
14908 sp_offset = info->total_size;
14909 else
14910 {
14911 emit_insn (TARGET_32BIT
14912 ? gen_addsi3 (sp_reg_rtx, sp_reg_rtx,
14913 GEN_INT (info->total_size))
14914 : gen_adddi3 (sp_reg_rtx, sp_reg_rtx,
14915 GEN_INT (info->total_size)));
14916 }
85638c0d 14917 }
f676971a 14918
9aa86737
AH
14919 /* Restore AltiVec registers if needed. */
14920 if (TARGET_ALTIVEC_ABI && info->altivec_size != 0)
14921 {
14922 int i;
14923
14924 for (i = info->first_altivec_reg_save; i <= LAST_ALTIVEC_REGNO; ++i)
14925 if (info->vrsave_mask & ALTIVEC_REG_BIT (i))
14926 {
14927 rtx addr, areg, mem;
14928
14929 areg = gen_rtx_REG (Pmode, 0);
14930 emit_move_insn
14931 (areg, GEN_INT (info->altivec_save_offset
14932 + sp_offset
14933 + 16 * (i - info->first_altivec_reg_save)));
14934
14935 /* AltiVec addressing mode is [reg+reg]. */
14936 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx, areg);
0be76840 14937 mem = gen_frame_mem (V4SImode, addr);
9aa86737
AH
14938
14939 emit_move_insn (gen_rtx_REG (V4SImode, i), mem);
14940 }
14941 }
14942
14943 /* Restore VRSAVE if needed. */
44688022 14944 if (TARGET_ALTIVEC && TARGET_ALTIVEC_VRSAVE
4d774ff8 14945 && info->vrsave_mask != 0)
9aa86737
AH
14946 {
14947 rtx addr, mem, reg;
14948
14949 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14950 GEN_INT (info->vrsave_save_offset + sp_offset));
0be76840 14951 mem = gen_frame_mem (SImode, addr);
9aa86737
AH
14952 reg = gen_rtx_REG (SImode, 12);
14953 emit_move_insn (reg, mem);
14954
14955 emit_insn (generate_set_vrsave (reg, info, 1));
14956 }
14957
9ebbca7d
GK
14958 /* Get the old lr if we saved it. */
14959 if (info->lr_save_p)
b6c9286a 14960 {
a3170dc6
AH
14961 rtx mem = gen_frame_mem_offset (Pmode, frame_reg_rtx,
14962 info->lr_save_offset + sp_offset);
ba4828e0 14963
9ebbca7d 14964 emit_move_insn (gen_rtx_REG (Pmode, 0), mem);
b6c9286a 14965 }
f676971a 14966
9ebbca7d
GK
14967 /* Get the old cr if we saved it. */
14968 if (info->cr_save_p)
14969 {
14970 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14971 GEN_INT (info->cr_save_offset + sp_offset));
0be76840 14972 rtx mem = gen_frame_mem (SImode, addr);
b6c9286a 14973
9ebbca7d
GK
14974 emit_move_insn (gen_rtx_REG (SImode, 12), mem);
14975 }
f676971a 14976
9ebbca7d 14977 /* Set LR here to try to overlap restores below. */
4697a36c 14978 if (info->lr_save_p)
9ebbca7d
GK
14979 emit_move_insn (gen_rtx_REG (Pmode, LINK_REGISTER_REGNUM),
14980 gen_rtx_REG (Pmode, 0));
f676971a 14981
83720594
RH
14982 /* Load exception handler data registers, if needed. */
14983 if (current_function_calls_eh_return)
14984 {
78e1b90d
DE
14985 unsigned int i, regno;
14986
fc4767bb
JJ
14987 if (TARGET_AIX)
14988 {
14989 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
14990 GEN_INT (sp_offset + 5 * reg_size));
0be76840 14991 rtx mem = gen_frame_mem (reg_mode, addr);
fc4767bb
JJ
14992
14993 emit_move_insn (gen_rtx_REG (reg_mode, 2), mem);
14994 }
14995
83720594
RH
14996 for (i = 0; ; ++i)
14997 {
a3170dc6 14998 rtx mem;
83720594
RH
14999
15000 regno = EH_RETURN_DATA_REGNO (i);
15001 if (regno == INVALID_REGNUM)
15002 break;
15003
a3170dc6
AH
15004 mem = gen_frame_mem_offset (reg_mode, frame_reg_rtx,
15005 info->ehrd_offset + sp_offset
15006 + reg_size * (int) i);
83720594
RH
15007
15008 emit_move_insn (gen_rtx_REG (reg_mode, regno), mem);
15009 }
15010 }
f676971a 15011
9ebbca7d
GK
15012 /* Restore GPRs. This is done as a PARALLEL if we are using
15013 the load-multiple instructions. */
15014 if (using_load_multiple)
979721f8 15015 {
9ebbca7d
GK
15016 rtvec p;
15017 p = rtvec_alloc (32 - info->first_gp_reg_save);
15018 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
979721f8 15019 {
f676971a
EC
15020 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
15021 GEN_INT (info->gp_save_offset
15022 + sp_offset
9ebbca7d 15023 + reg_size * i));
0be76840 15024 rtx mem = gen_frame_mem (reg_mode, addr);
9ebbca7d 15025
f676971a 15026 RTVEC_ELT (p, i) =
9ebbca7d
GK
15027 gen_rtx_SET (VOIDmode,
15028 gen_rtx_REG (reg_mode, info->first_gp_reg_save + i),
15029 mem);
979721f8 15030 }
9ebbca7d 15031 emit_insn (gen_rtx_PARALLEL (VOIDmode, p));
979721f8 15032 }
9ebbca7d
GK
15033 else
15034 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
6d0a8091
DJ
15035 if ((regs_ever_live[info->first_gp_reg_save + i]
15036 && (!call_used_regs[info->first_gp_reg_save + i]
15037 || (i + info->first_gp_reg_save == RS6000_PIC_OFFSET_TABLE_REGNUM
b4db40bf 15038 && TARGET_TOC && TARGET_MINIMAL_TOC)))
6d0a8091 15039 || (i + info->first_gp_reg_save == RS6000_PIC_OFFSET_TABLE_REGNUM
14f00213 15040 && ((DEFAULT_ABI == ABI_V4 && flag_pic != 0)
f607bc57 15041 || (DEFAULT_ABI == ABI_DARWIN && flag_pic))))
9ebbca7d 15042 {
f676971a
EC
15043 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
15044 GEN_INT (info->gp_save_offset
15045 + sp_offset
9ebbca7d 15046 + reg_size * i));
0be76840 15047 rtx mem = gen_frame_mem (reg_mode, addr);
ba4828e0 15048
a3170dc6 15049 /* Restore 64-bit quantities for SPE. */
c19de7aa 15050 if (TARGET_SPE_ABI && info->spe_64bit_regs_used != 0)
a3170dc6
AH
15051 {
15052 int offset = info->spe_gp_save_offset + sp_offset + 8 * i;
15053 rtx b;
15054
15055 if (!SPE_CONST_OFFSET_OK (offset))
15056 {
15057 b = gen_rtx_REG (Pmode, FIXED_SCRATCH);
15058 emit_move_insn (b, GEN_INT (offset));
15059 }
15060 else
15061 b = GEN_INT (offset);
15062
15063 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx, b);
0be76840 15064 mem = gen_frame_mem (V2SImode, addr);
a3170dc6
AH
15065 }
15066
f676971a 15067 emit_move_insn (gen_rtx_REG (reg_mode,
a3170dc6 15068 info->first_gp_reg_save + i), mem);
9ebbca7d 15069 }
9878760c 15070
9ebbca7d
GK
15071 /* Restore fpr's if we need to do it without calling a function. */
15072 if (restoring_FPRs_inline)
15073 for (i = 0; i < 64 - info->first_fp_reg_save; i++)
f676971a 15074 if ((regs_ever_live[info->first_fp_reg_save+i]
9ebbca7d
GK
15075 && ! call_used_regs[info->first_fp_reg_save+i]))
15076 {
15077 rtx addr, mem;
15078 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
f676971a
EC
15079 GEN_INT (info->fp_save_offset
15080 + sp_offset
a4f6c312 15081 + 8 * i));
0be76840 15082 mem = gen_frame_mem (DFmode, addr);
9ebbca7d 15083
f676971a 15084 emit_move_insn (gen_rtx_REG (DFmode,
9ebbca7d
GK
15085 info->first_fp_reg_save + i),
15086 mem);
15087 }
8d30c4ee 15088
9ebbca7d
GK
15089 /* If we saved cr, restore it here. Just those that were used. */
15090 if (info->cr_save_p)
979721f8 15091 {
9ebbca7d 15092 rtx r12_rtx = gen_rtx_REG (SImode, 12);
e35b9579 15093 int count = 0;
f676971a 15094
9ebbca7d 15095 if (using_mfcr_multiple)
979721f8 15096 {
9ebbca7d
GK
15097 for (i = 0; i < 8; i++)
15098 if (regs_ever_live[CR0_REGNO+i] && ! call_used_regs[CR0_REGNO+i])
e35b9579 15099 count++;
37409796 15100 gcc_assert (count);
e35b9579
GK
15101 }
15102
15103 if (using_mfcr_multiple && count > 1)
15104 {
15105 rtvec p;
15106 int ndx;
f676971a 15107
e35b9579 15108 p = rtvec_alloc (count);
9ebbca7d 15109
e35b9579 15110 ndx = 0;
9ebbca7d
GK
15111 for (i = 0; i < 8; i++)
15112 if (regs_ever_live[CR0_REGNO+i] && ! call_used_regs[CR0_REGNO+i])
15113 {
15114 rtvec r = rtvec_alloc (2);
15115 RTVEC_ELT (r, 0) = r12_rtx;
15116 RTVEC_ELT (r, 1) = GEN_INT (1 << (7-i));
e35b9579 15117 RTVEC_ELT (p, ndx) =
f676971a 15118 gen_rtx_SET (VOIDmode, gen_rtx_REG (CCmode, CR0_REGNO+i),
615158e2 15119 gen_rtx_UNSPEC (CCmode, r, UNSPEC_MOVESI_TO_CR));
e35b9579 15120 ndx++;
9ebbca7d
GK
15121 }
15122 emit_insn (gen_rtx_PARALLEL (VOIDmode, p));
37409796 15123 gcc_assert (ndx == count);
979721f8
MM
15124 }
15125 else
9ebbca7d
GK
15126 for (i = 0; i < 8; i++)
15127 if (regs_ever_live[CR0_REGNO+i] && ! call_used_regs[CR0_REGNO+i])
979721f8 15128 {
f676971a 15129 emit_insn (gen_movsi_to_cr_one (gen_rtx_REG (CCmode,
9ebbca7d
GK
15130 CR0_REGNO+i),
15131 r12_rtx));
979721f8 15132 }
979721f8
MM
15133 }
15134
9ebbca7d 15135 /* If this is V.4, unwind the stack pointer after all of the loads
022123e6
AM
15136 have been done. */
15137 if (frame_reg_rtx != sp_reg_rtx)
15138 {
15139 /* This blockage is needed so that sched doesn't decide to move
15140 the sp change before the register restores. */
15141 rs6000_emit_stack_tie ();
15142 emit_move_insn (sp_reg_rtx, frame_reg_rtx);
15143 }
15144 else if (sp_offset != 0)
15145 emit_insn (TARGET_32BIT
15146 ? gen_addsi3 (sp_reg_rtx, sp_reg_rtx,
15147 GEN_INT (sp_offset))
15148 : gen_adddi3 (sp_reg_rtx, sp_reg_rtx,
15149 GEN_INT (sp_offset)));
b6c9286a 15150
83720594
RH
15151 if (current_function_calls_eh_return)
15152 {
15153 rtx sa = EH_RETURN_STACKADJ_RTX;
5b71a4e7 15154 emit_insn (TARGET_32BIT
83720594
RH
15155 ? gen_addsi3 (sp_reg_rtx, sp_reg_rtx, sa)
15156 : gen_adddi3 (sp_reg_rtx, sp_reg_rtx, sa));
15157 }
15158
9ebbca7d
GK
15159 if (!sibcall)
15160 {
15161 rtvec p;
15162 if (! restoring_FPRs_inline)
15163 p = rtvec_alloc (3 + 64 - info->first_fp_reg_save);
15164 else
15165 p = rtvec_alloc (2);
b6c9286a 15166
e35b9579 15167 RTVEC_ELT (p, 0) = gen_rtx_RETURN (VOIDmode);
f676971a
EC
15168 RTVEC_ELT (p, 1) = gen_rtx_USE (VOIDmode,
15169 gen_rtx_REG (Pmode,
9ebbca7d 15170 LINK_REGISTER_REGNUM));
9ebbca7d
GK
15171
15172 /* If we have to restore more than two FP registers, branch to the
15173 restore function. It will return to our caller. */
15174 if (! restoring_FPRs_inline)
15175 {
15176 int i;
15177 char rname[30];
520a57c8 15178 const char *alloc_rname;
979721f8 15179
f676971a 15180 sprintf (rname, "%s%d%s", RESTORE_FP_PREFIX,
9ebbca7d 15181 info->first_fp_reg_save - 32, RESTORE_FP_SUFFIX);
a8a05998 15182 alloc_rname = ggc_strdup (rname);
9ebbca7d
GK
15183 RTVEC_ELT (p, 2) = gen_rtx_USE (VOIDmode,
15184 gen_rtx_SYMBOL_REF (Pmode,
15185 alloc_rname));
b6c9286a 15186
9ebbca7d
GK
15187 for (i = 0; i < 64 - info->first_fp_reg_save; i++)
15188 {
15189 rtx addr, mem;
15190 addr = gen_rtx_PLUS (Pmode, sp_reg_rtx,
15191 GEN_INT (info->fp_save_offset + 8*i));
0be76840 15192 mem = gen_frame_mem (DFmode, addr);
9ebbca7d 15193
f676971a 15194 RTVEC_ELT (p, i+3) =
9ebbca7d
GK
15195 gen_rtx_SET (VOIDmode,
15196 gen_rtx_REG (DFmode, info->first_fp_reg_save + i),
15197 mem);
b6c9286a
MM
15198 }
15199 }
f676971a 15200
9ebbca7d 15201 emit_jump_insn (gen_rtx_PARALLEL (VOIDmode, p));
3daf36a4 15202 }
9878760c
RK
15203}
15204
15205/* Write function epilogue. */
15206
08c148a8 15207static void
f676971a 15208rs6000_output_function_epilogue (FILE *file,
a2369ed3 15209 HOST_WIDE_INT size ATTRIBUTE_UNUSED)
9878760c 15210{
9ebbca7d 15211 if (! HAVE_epilogue)
9878760c 15212 {
9ebbca7d
GK
15213 rtx insn = get_last_insn ();
15214 /* If the last insn was a BARRIER, we don't have to write anything except
15215 the trace table. */
15216 if (GET_CODE (insn) == NOTE)
15217 insn = prev_nonnote_insn (insn);
15218 if (insn == 0 || GET_CODE (insn) != BARRIER)
4697a36c 15219 {
9ebbca7d
GK
15220 /* This is slightly ugly, but at least we don't have two
15221 copies of the epilogue-emitting code. */
15222 start_sequence ();
15223
15224 /* A NOTE_INSN_DELETED is supposed to be at the start
15225 and end of the "toplevel" insn chain. */
2e040219 15226 emit_note (NOTE_INSN_DELETED);
9ebbca7d 15227 rs6000_emit_epilogue (FALSE);
2e040219 15228 emit_note (NOTE_INSN_DELETED);
9ebbca7d 15229
a3c9585f 15230 /* Expand INSN_ADDRESSES so final() doesn't crash. */
178c3eff
DJ
15231 {
15232 rtx insn;
15233 unsigned addr = 0;
15234 for (insn = get_insns (); insn != 0; insn = NEXT_INSN (insn))
15235 {
15236 INSN_ADDRESSES_NEW (insn, addr);
15237 addr += 4;
15238 }
15239 }
15240
9ebbca7d 15241 if (TARGET_DEBUG_STACK)
a4f6c312 15242 debug_rtx_list (get_insns (), 100);
c9d691e9 15243 final (get_insns (), file, FALSE);
9ebbca7d 15244 end_sequence ();
4697a36c 15245 }
9878760c 15246 }
b4ac57ab 15247
efdba735
SH
15248#if TARGET_MACHO
15249 macho_branch_islands ();
0e5da0be
GK
15250 /* Mach-O doesn't support labels at the end of objects, so if
15251 it looks like we might want one, insert a NOP. */
15252 {
15253 rtx insn = get_last_insn ();
15254 while (insn
15255 && NOTE_P (insn)
15256 && NOTE_LINE_NUMBER (insn) != NOTE_INSN_DELETED_LABEL)
15257 insn = PREV_INSN (insn);
f676971a
EC
15258 if (insn
15259 && (LABEL_P (insn)
0e5da0be
GK
15260 || (NOTE_P (insn)
15261 && NOTE_LINE_NUMBER (insn) == NOTE_INSN_DELETED_LABEL)))
15262 fputs ("\tnop\n", file);
15263 }
15264#endif
15265
9b30bae2 15266 /* Output a traceback table here. See /usr/include/sys/debug.h for info
314fc5a9
ILT
15267 on its format.
15268
15269 We don't output a traceback table if -finhibit-size-directive was
15270 used. The documentation for -finhibit-size-directive reads
15271 ``don't output a @code{.size} assembler directive, or anything
15272 else that would cause trouble if the function is split in the
15273 middle, and the two halves are placed at locations far apart in
15274 memory.'' The traceback table has this property, since it
15275 includes the offset from the start of the function to the
4d30c363
MM
15276 traceback table itself.
15277
15278 System V.4 Powerpc's (and the embedded ABI derived from it) use a
b6c9286a 15279 different traceback table. */
57ac7be9 15280 if (DEFAULT_ABI == ABI_AIX && ! flag_inhibit_size_directive
8097c268 15281 && rs6000_traceback != traceback_none && !current_function_is_thunk)
9b30bae2 15282 {
69c75916 15283 const char *fname = NULL;
3ac88239 15284 const char *language_string = lang_hooks.name;
6041bf2f 15285 int fixed_parms = 0, float_parms = 0, parm_info = 0;
314fc5a9 15286 int i;
57ac7be9 15287 int optional_tbtab;
8097c268 15288 rs6000_stack_t *info = rs6000_stack_info ();
57ac7be9
AM
15289
15290 if (rs6000_traceback == traceback_full)
15291 optional_tbtab = 1;
15292 else if (rs6000_traceback == traceback_part)
15293 optional_tbtab = 0;
15294 else
15295 optional_tbtab = !optimize_size && !TARGET_ELF;
314fc5a9 15296
69c75916
AM
15297 if (optional_tbtab)
15298 {
15299 fname = XSTR (XEXP (DECL_RTL (current_function_decl), 0), 0);
15300 while (*fname == '.') /* V.4 encodes . in the name */
15301 fname++;
15302
15303 /* Need label immediately before tbtab, so we can compute
15304 its offset from the function start. */
15305 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (file, "LT");
15306 ASM_OUTPUT_LABEL (file, fname);
15307 }
314fc5a9
ILT
15308
15309 /* The .tbtab pseudo-op can only be used for the first eight
15310 expressions, since it can't handle the possibly variable
15311 length fields that follow. However, if you omit the optional
15312 fields, the assembler outputs zeros for all optional fields
15313 anyways, giving each variable length field is minimum length
15314 (as defined in sys/debug.h). Thus we can not use the .tbtab
15315 pseudo-op at all. */
15316
15317 /* An all-zero word flags the start of the tbtab, for debuggers
15318 that have to find it by searching forward from the entry
15319 point or from the current pc. */
19d2d16f 15320 fputs ("\t.long 0\n", file);
314fc5a9
ILT
15321
15322 /* Tbtab format type. Use format type 0. */
19d2d16f 15323 fputs ("\t.byte 0,", file);
314fc5a9 15324
5fc921c1
DE
15325 /* Language type. Unfortunately, there does not seem to be any
15326 official way to discover the language being compiled, so we
15327 use language_string.
15328 C is 0. Fortran is 1. Pascal is 2. Ada is 3. C++ is 9.
56438901
AM
15329 Java is 13. Objective-C is 14. Objective-C++ isn't assigned
15330 a number, so for now use 9. */
5fc921c1 15331 if (! strcmp (language_string, "GNU C"))
314fc5a9 15332 i = 0;
6de9cd9a
DN
15333 else if (! strcmp (language_string, "GNU F77")
15334 || ! strcmp (language_string, "GNU F95"))
314fc5a9 15335 i = 1;
8b83775b 15336 else if (! strcmp (language_string, "GNU Pascal"))
314fc5a9 15337 i = 2;
5fc921c1
DE
15338 else if (! strcmp (language_string, "GNU Ada"))
15339 i = 3;
56438901
AM
15340 else if (! strcmp (language_string, "GNU C++")
15341 || ! strcmp (language_string, "GNU Objective-C++"))
314fc5a9 15342 i = 9;
9517ead8
AG
15343 else if (! strcmp (language_string, "GNU Java"))
15344 i = 13;
5fc921c1
DE
15345 else if (! strcmp (language_string, "GNU Objective-C"))
15346 i = 14;
314fc5a9 15347 else
37409796 15348 gcc_unreachable ();
314fc5a9
ILT
15349 fprintf (file, "%d,", i);
15350
15351 /* 8 single bit fields: global linkage (not set for C extern linkage,
15352 apparently a PL/I convention?), out-of-line epilogue/prologue, offset
15353 from start of procedure stored in tbtab, internal function, function
15354 has controlled storage, function has no toc, function uses fp,
15355 function logs/aborts fp operations. */
15356 /* Assume that fp operations are used if any fp reg must be saved. */
6041bf2f
DE
15357 fprintf (file, "%d,",
15358 (optional_tbtab << 5) | ((info->first_fp_reg_save != 64) << 1));
314fc5a9
ILT
15359
15360 /* 6 bitfields: function is interrupt handler, name present in
15361 proc table, function calls alloca, on condition directives
15362 (controls stack walks, 3 bits), saves condition reg, saves
15363 link reg. */
15364 /* The `function calls alloca' bit seems to be set whenever reg 31 is
15365 set up as a frame pointer, even when there is no alloca call. */
15366 fprintf (file, "%d,",
6041bf2f
DE
15367 ((optional_tbtab << 6)
15368 | ((optional_tbtab & frame_pointer_needed) << 5)
15369 | (info->cr_save_p << 1)
15370 | (info->lr_save_p)));
314fc5a9 15371
6041bf2f 15372 /* 3 bitfields: saves backchain, fixup code, number of fpr saved
314fc5a9
ILT
15373 (6 bits). */
15374 fprintf (file, "%d,",
4697a36c 15375 (info->push_p << 7) | (64 - info->first_fp_reg_save));
314fc5a9
ILT
15376
15377 /* 2 bitfields: spare bits (2 bits), number of gpr saved (6 bits). */
15378 fprintf (file, "%d,", (32 - first_reg_to_save ()));
15379
6041bf2f
DE
15380 if (optional_tbtab)
15381 {
15382 /* Compute the parameter info from the function decl argument
15383 list. */
15384 tree decl;
15385 int next_parm_info_bit = 31;
314fc5a9 15386
6041bf2f
DE
15387 for (decl = DECL_ARGUMENTS (current_function_decl);
15388 decl; decl = TREE_CHAIN (decl))
15389 {
15390 rtx parameter = DECL_INCOMING_RTL (decl);
15391 enum machine_mode mode = GET_MODE (parameter);
314fc5a9 15392
6041bf2f
DE
15393 if (GET_CODE (parameter) == REG)
15394 {
ebb109ad 15395 if (SCALAR_FLOAT_MODE_P (mode))
6041bf2f
DE
15396 {
15397 int bits;
15398
15399 float_parms++;
15400
37409796
NS
15401 switch (mode)
15402 {
15403 case SFmode:
15404 bits = 0x2;
15405 break;
15406
15407 case DFmode:
15408 case TFmode:
15409 bits = 0x3;
15410 break;
15411
15412 default:
15413 gcc_unreachable ();
15414 }
6041bf2f
DE
15415
15416 /* If only one bit will fit, don't or in this entry. */
15417 if (next_parm_info_bit > 0)
15418 parm_info |= (bits << (next_parm_info_bit - 1));
15419 next_parm_info_bit -= 2;
15420 }
15421 else
15422 {
15423 fixed_parms += ((GET_MODE_SIZE (mode)
15424 + (UNITS_PER_WORD - 1))
15425 / UNITS_PER_WORD);
15426 next_parm_info_bit -= 1;
15427 }
15428 }
15429 }
15430 }
314fc5a9
ILT
15431
15432 /* Number of fixed point parameters. */
15433 /* This is actually the number of words of fixed point parameters; thus
15434 an 8 byte struct counts as 2; and thus the maximum value is 8. */
15435 fprintf (file, "%d,", fixed_parms);
15436
15437 /* 2 bitfields: number of floating point parameters (7 bits), parameters
15438 all on stack. */
15439 /* This is actually the number of fp registers that hold parameters;
15440 and thus the maximum value is 13. */
15441 /* Set parameters on stack bit if parameters are not in their original
15442 registers, regardless of whether they are on the stack? Xlc
15443 seems to set the bit when not optimizing. */
15444 fprintf (file, "%d\n", ((float_parms << 1) | (! optimize)));
15445
6041bf2f
DE
15446 if (! optional_tbtab)
15447 return;
15448
314fc5a9
ILT
15449 /* Optional fields follow. Some are variable length. */
15450
15451 /* Parameter types, left adjusted bit fields: 0 fixed, 10 single float,
15452 11 double float. */
15453 /* There is an entry for each parameter in a register, in the order that
15454 they occur in the parameter list. Any intervening arguments on the
15455 stack are ignored. If the list overflows a long (max possible length
15456 34 bits) then completely leave off all elements that don't fit. */
15457 /* Only emit this long if there was at least one parameter. */
15458 if (fixed_parms || float_parms)
15459 fprintf (file, "\t.long %d\n", parm_info);
15460
15461 /* Offset from start of code to tb table. */
19d2d16f 15462 fputs ("\t.long ", file);
314fc5a9 15463 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (file, "LT");
85b776df
AM
15464 if (TARGET_AIX)
15465 RS6000_OUTPUT_BASENAME (file, fname);
15466 else
15467 assemble_name (file, fname);
15468 putc ('-', file);
15469 rs6000_output_function_entry (file, fname);
19d2d16f 15470 putc ('\n', file);
314fc5a9
ILT
15471
15472 /* Interrupt handler mask. */
15473 /* Omit this long, since we never set the interrupt handler bit
15474 above. */
15475
15476 /* Number of CTL (controlled storage) anchors. */
15477 /* Omit this long, since the has_ctl bit is never set above. */
15478
15479 /* Displacement into stack of each CTL anchor. */
15480 /* Omit this list of longs, because there are no CTL anchors. */
15481
15482 /* Length of function name. */
69c75916
AM
15483 if (*fname == '*')
15484 ++fname;
296b8152 15485 fprintf (file, "\t.short %d\n", (int) strlen (fname));
314fc5a9
ILT
15486
15487 /* Function name. */
15488 assemble_string (fname, strlen (fname));
15489
15490 /* Register for alloca automatic storage; this is always reg 31.
15491 Only emit this if the alloca bit was set above. */
15492 if (frame_pointer_needed)
19d2d16f 15493 fputs ("\t.byte 31\n", file);
b1765bde
DE
15494
15495 fputs ("\t.align 2\n", file);
9b30bae2 15496 }
9878760c 15497}
17167fd8 15498\f
a4f6c312
SS
15499/* A C compound statement that outputs the assembler code for a thunk
15500 function, used to implement C++ virtual function calls with
15501 multiple inheritance. The thunk acts as a wrapper around a virtual
15502 function, adjusting the implicit object parameter before handing
15503 control off to the real function.
15504
15505 First, emit code to add the integer DELTA to the location that
15506 contains the incoming first argument. Assume that this argument
15507 contains a pointer, and is the one used to pass the `this' pointer
15508 in C++. This is the incoming argument *before* the function
15509 prologue, e.g. `%o0' on a sparc. The addition must preserve the
15510 values of all other incoming arguments.
17167fd8
MM
15511
15512 After the addition, emit code to jump to FUNCTION, which is a
a4f6c312
SS
15513 `FUNCTION_DECL'. This is a direct pure jump, not a call, and does
15514 not touch the return address. Hence returning from FUNCTION will
15515 return to whoever called the current `thunk'.
17167fd8 15516
a4f6c312
SS
15517 The effect must be as if FUNCTION had been called directly with the
15518 adjusted first argument. This macro is responsible for emitting
15519 all of the code for a thunk function; output_function_prologue()
15520 and output_function_epilogue() are not invoked.
17167fd8 15521
a4f6c312
SS
15522 The THUNK_FNDECL is redundant. (DELTA and FUNCTION have already
15523 been extracted from it.) It might possibly be useful on some
15524 targets, but probably not.
17167fd8 15525
a4f6c312
SS
15526 If you do not define this macro, the target-independent code in the
15527 C++ frontend will generate a less efficient heavyweight thunk that
15528 calls FUNCTION instead of jumping to it. The generic approach does
15529 not support varargs. */
17167fd8 15530
3961e8fe 15531static void
f676971a
EC
15532rs6000_output_mi_thunk (FILE *file, tree thunk_fndecl ATTRIBUTE_UNUSED,
15533 HOST_WIDE_INT delta, HOST_WIDE_INT vcall_offset,
a2369ed3 15534 tree function)
17167fd8 15535{
5b71a4e7 15536 rtx this, insn, funexp;
17167fd8 15537
5b71a4e7 15538 reload_completed = 1;
fe3ad572 15539 epilogue_completed = 1;
5b71a4e7 15540 no_new_pseudos = 1;
6429e3be 15541 reset_block_changes ();
56a7189a 15542
5b71a4e7 15543 /* Mark the end of the (empty) prologue. */
2e040219 15544 emit_note (NOTE_INSN_PROLOGUE_END);
17167fd8 15545
5b71a4e7
DE
15546 /* Find the "this" pointer. If the function returns a structure,
15547 the structure return pointer is in r3. */
61f71b34 15548 if (aggregate_value_p (TREE_TYPE (TREE_TYPE (function)), function))
5b71a4e7 15549 this = gen_rtx_REG (Pmode, 4);
56a7189a 15550 else
5b71a4e7 15551 this = gen_rtx_REG (Pmode, 3);
17167fd8 15552
5b71a4e7
DE
15553 /* Apply the constant offset, if required. */
15554 if (delta)
15555 {
15556 rtx delta_rtx = GEN_INT (delta);
15557 emit_insn (TARGET_32BIT
15558 ? gen_addsi3 (this, this, delta_rtx)
15559 : gen_adddi3 (this, this, delta_rtx));
17167fd8
MM
15560 }
15561
5b71a4e7
DE
15562 /* Apply the offset from the vtable, if required. */
15563 if (vcall_offset)
17167fd8 15564 {
5b71a4e7
DE
15565 rtx vcall_offset_rtx = GEN_INT (vcall_offset);
15566 rtx tmp = gen_rtx_REG (Pmode, 12);
17167fd8 15567
5b71a4e7 15568 emit_move_insn (tmp, gen_rtx_MEM (Pmode, this));
eeff9307
JJ
15569 if (((unsigned HOST_WIDE_INT) vcall_offset) + 0x8000 >= 0x10000)
15570 {
15571 emit_insn (TARGET_32BIT
15572 ? gen_addsi3 (tmp, tmp, vcall_offset_rtx)
15573 : gen_adddi3 (tmp, tmp, vcall_offset_rtx));
15574 emit_move_insn (tmp, gen_rtx_MEM (Pmode, tmp));
15575 }
15576 else
15577 {
15578 rtx loc = gen_rtx_PLUS (Pmode, tmp, vcall_offset_rtx);
15579
15580 emit_move_insn (tmp, gen_rtx_MEM (Pmode, loc));
15581 }
5b71a4e7
DE
15582 emit_insn (TARGET_32BIT
15583 ? gen_addsi3 (this, this, tmp)
15584 : gen_adddi3 (this, this, tmp));
17167fd8
MM
15585 }
15586
5b71a4e7
DE
15587 /* Generate a tail call to the target function. */
15588 if (!TREE_USED (function))
15589 {
15590 assemble_external (function);
15591 TREE_USED (function) = 1;
15592 }
15593 funexp = XEXP (DECL_RTL (function), 0);
5b71a4e7 15594 funexp = gen_rtx_MEM (FUNCTION_MODE, funexp);
ee890fe2
SS
15595
15596#if TARGET_MACHO
ab82a49f 15597 if (MACHOPIC_INDIRECT)
5b71a4e7 15598 funexp = machopic_indirect_call_target (funexp);
ee890fe2 15599#endif
5b71a4e7
DE
15600
15601 /* gen_sibcall expects reload to convert scratch pseudo to LR so we must
992d08b1 15602 generate sibcall RTL explicitly. */
5b71a4e7
DE
15603 insn = emit_call_insn (
15604 gen_rtx_PARALLEL (VOIDmode,
15605 gen_rtvec (4,
15606 gen_rtx_CALL (VOIDmode,
15607 funexp, const0_rtx),
15608 gen_rtx_USE (VOIDmode, const0_rtx),
15609 gen_rtx_USE (VOIDmode,
15610 gen_rtx_REG (SImode,
15611 LINK_REGISTER_REGNUM)),
15612 gen_rtx_RETURN (VOIDmode))));
15613 SIBLING_CALL_P (insn) = 1;
15614 emit_barrier ();
15615
15616 /* Run just enough of rest_of_compilation to get the insns emitted.
15617 There's not really enough bulk here to make other passes such as
15618 instruction scheduling worth while. Note that use_thunk calls
15619 assemble_start_function and assemble_end_function. */
15620 insn = get_insns ();
a2855205 15621 insn_locators_initialize ();
5b71a4e7
DE
15622 shorten_branches (insn);
15623 final_start_function (insn, file, 1);
c9d691e9 15624 final (insn, file, 1);
5b71a4e7
DE
15625 final_end_function ();
15626
15627 reload_completed = 0;
fe3ad572 15628 epilogue_completed = 0;
5b71a4e7 15629 no_new_pseudos = 0;
9ebbca7d 15630}
9ebbca7d
GK
15631\f
15632/* A quick summary of the various types of 'constant-pool tables'
15633 under PowerPC:
15634
f676971a 15635 Target Flags Name One table per
9ebbca7d
GK
15636 AIX (none) AIX TOC object file
15637 AIX -mfull-toc AIX TOC object file
15638 AIX -mminimal-toc AIX minimal TOC translation unit
15639 SVR4/EABI (none) SVR4 SDATA object file
15640 SVR4/EABI -fpic SVR4 pic object file
15641 SVR4/EABI -fPIC SVR4 PIC translation unit
15642 SVR4/EABI -mrelocatable EABI TOC function
15643 SVR4/EABI -maix AIX TOC object file
f676971a 15644 SVR4/EABI -maix -mminimal-toc
9ebbca7d
GK
15645 AIX minimal TOC translation unit
15646
15647 Name Reg. Set by entries contains:
15648 made by addrs? fp? sum?
15649
15650 AIX TOC 2 crt0 as Y option option
15651 AIX minimal TOC 30 prolog gcc Y Y option
15652 SVR4 SDATA 13 crt0 gcc N Y N
15653 SVR4 pic 30 prolog ld Y not yet N
15654 SVR4 PIC 30 prolog gcc Y option option
15655 EABI TOC 30 prolog gcc Y option option
15656
15657*/
15658
9ebbca7d
GK
15659/* Hash functions for the hash table. */
15660
15661static unsigned
a2369ed3 15662rs6000_hash_constant (rtx k)
9ebbca7d 15663{
46b33600
RH
15664 enum rtx_code code = GET_CODE (k);
15665 enum machine_mode mode = GET_MODE (k);
15666 unsigned result = (code << 3) ^ mode;
15667 const char *format;
15668 int flen, fidx;
f676971a 15669
46b33600
RH
15670 format = GET_RTX_FORMAT (code);
15671 flen = strlen (format);
15672 fidx = 0;
9ebbca7d 15673
46b33600
RH
15674 switch (code)
15675 {
15676 case LABEL_REF:
15677 return result * 1231 + (unsigned) INSN_UID (XEXP (k, 0));
15678
15679 case CONST_DOUBLE:
15680 if (mode != VOIDmode)
15681 return real_hash (CONST_DOUBLE_REAL_VALUE (k)) * result;
15682 flen = 2;
15683 break;
15684
15685 case CODE_LABEL:
15686 fidx = 3;
15687 break;
15688
15689 default:
15690 break;
15691 }
9ebbca7d
GK
15692
15693 for (; fidx < flen; fidx++)
15694 switch (format[fidx])
15695 {
15696 case 's':
15697 {
15698 unsigned i, len;
15699 const char *str = XSTR (k, fidx);
15700 len = strlen (str);
15701 result = result * 613 + len;
15702 for (i = 0; i < len; i++)
15703 result = result * 613 + (unsigned) str[i];
17167fd8
MM
15704 break;
15705 }
9ebbca7d
GK
15706 case 'u':
15707 case 'e':
15708 result = result * 1231 + rs6000_hash_constant (XEXP (k, fidx));
15709 break;
15710 case 'i':
15711 case 'n':
15712 result = result * 613 + (unsigned) XINT (k, fidx);
15713 break;
15714 case 'w':
15715 if (sizeof (unsigned) >= sizeof (HOST_WIDE_INT))
15716 result = result * 613 + (unsigned) XWINT (k, fidx);
15717 else
15718 {
15719 size_t i;
9390387d 15720 for (i = 0; i < sizeof (HOST_WIDE_INT) / sizeof (unsigned); i++)
9ebbca7d
GK
15721 result = result * 613 + (unsigned) (XWINT (k, fidx)
15722 >> CHAR_BIT * i);
15723 }
15724 break;
09501938
DE
15725 case '0':
15726 break;
9ebbca7d 15727 default:
37409796 15728 gcc_unreachable ();
9ebbca7d 15729 }
46b33600 15730
9ebbca7d
GK
15731 return result;
15732}
15733
15734static unsigned
a2369ed3 15735toc_hash_function (const void *hash_entry)
9ebbca7d 15736{
f676971a 15737 const struct toc_hash_struct *thc =
a9098fd0
GK
15738 (const struct toc_hash_struct *) hash_entry;
15739 return rs6000_hash_constant (thc->key) ^ thc->key_mode;
9ebbca7d
GK
15740}
15741
15742/* Compare H1 and H2 for equivalence. */
15743
15744static int
a2369ed3 15745toc_hash_eq (const void *h1, const void *h2)
9ebbca7d
GK
15746{
15747 rtx r1 = ((const struct toc_hash_struct *) h1)->key;
15748 rtx r2 = ((const struct toc_hash_struct *) h2)->key;
15749
a9098fd0
GK
15750 if (((const struct toc_hash_struct *) h1)->key_mode
15751 != ((const struct toc_hash_struct *) h2)->key_mode)
15752 return 0;
15753
5692c7bc 15754 return rtx_equal_p (r1, r2);
9ebbca7d
GK
15755}
15756
28e510bd
MM
15757/* These are the names given by the C++ front-end to vtables, and
15758 vtable-like objects. Ideally, this logic should not be here;
15759 instead, there should be some programmatic way of inquiring as
15760 to whether or not an object is a vtable. */
15761
15762#define VTABLE_NAME_P(NAME) \
9390387d 15763 (strncmp ("_vt.", name, strlen ("_vt.")) == 0 \
28e510bd
MM
15764 || strncmp ("_ZTV", name, strlen ("_ZTV")) == 0 \
15765 || strncmp ("_ZTT", name, strlen ("_ZTT")) == 0 \
26be75db 15766 || strncmp ("_ZTI", name, strlen ("_ZTI")) == 0 \
f676971a 15767 || strncmp ("_ZTC", name, strlen ("_ZTC")) == 0)
28e510bd
MM
15768
15769void
a2369ed3 15770rs6000_output_symbol_ref (FILE *file, rtx x)
28e510bd
MM
15771{
15772 /* Currently C++ toc references to vtables can be emitted before it
15773 is decided whether the vtable is public or private. If this is
15774 the case, then the linker will eventually complain that there is
f676971a 15775 a reference to an unknown section. Thus, for vtables only,
28e510bd
MM
15776 we emit the TOC reference to reference the symbol and not the
15777 section. */
15778 const char *name = XSTR (x, 0);
54ee9799 15779
f676971a 15780 if (VTABLE_NAME_P (name))
54ee9799
DE
15781 {
15782 RS6000_OUTPUT_BASENAME (file, name);
15783 }
15784 else
15785 assemble_name (file, name);
28e510bd
MM
15786}
15787
a4f6c312
SS
15788/* Output a TOC entry. We derive the entry name from what is being
15789 written. */
9878760c
RK
15790
15791void
a2369ed3 15792output_toc (FILE *file, rtx x, int labelno, enum machine_mode mode)
9878760c
RK
15793{
15794 char buf[256];
3cce094d 15795 const char *name = buf;
ec940faa 15796 const char *real_name;
9878760c 15797 rtx base = x;
16fdeb48 15798 HOST_WIDE_INT offset = 0;
9878760c 15799
37409796 15800 gcc_assert (!TARGET_NO_TOC);
4697a36c 15801
9ebbca7d
GK
15802 /* When the linker won't eliminate them, don't output duplicate
15803 TOC entries (this happens on AIX if there is any kind of TOC,
17211ab5
GK
15804 and on SVR4 under -fPIC or -mrelocatable). Don't do this for
15805 CODE_LABELs. */
15806 if (TARGET_TOC && GET_CODE (x) != LABEL_REF)
9ebbca7d
GK
15807 {
15808 struct toc_hash_struct *h;
15809 void * * found;
f676971a 15810
17211ab5 15811 /* Create toc_hash_table. This can't be done at OVERRIDE_OPTIONS
c4ad648e 15812 time because GGC is not initialized at that point. */
17211ab5 15813 if (toc_hash_table == NULL)
f676971a 15814 toc_hash_table = htab_create_ggc (1021, toc_hash_function,
17211ab5
GK
15815 toc_hash_eq, NULL);
15816
9ebbca7d
GK
15817 h = ggc_alloc (sizeof (*h));
15818 h->key = x;
a9098fd0 15819 h->key_mode = mode;
9ebbca7d 15820 h->labelno = labelno;
f676971a 15821
9ebbca7d
GK
15822 found = htab_find_slot (toc_hash_table, h, 1);
15823 if (*found == NULL)
15824 *found = h;
f676971a 15825 else /* This is indeed a duplicate.
9ebbca7d
GK
15826 Set this label equal to that label. */
15827 {
15828 fputs ("\t.set ", file);
15829 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (file, "LC");
15830 fprintf (file, "%d,", labelno);
15831 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (file, "LC");
f676971a 15832 fprintf (file, "%d\n", ((*(const struct toc_hash_struct **)
9ebbca7d
GK
15833 found)->labelno));
15834 return;
15835 }
15836 }
15837
15838 /* If we're going to put a double constant in the TOC, make sure it's
15839 aligned properly when strict alignment is on. */
ff1720ed
RK
15840 if (GET_CODE (x) == CONST_DOUBLE
15841 && STRICT_ALIGNMENT
a9098fd0 15842 && GET_MODE_BITSIZE (mode) >= 64
ff1720ed
RK
15843 && ! (TARGET_NO_FP_IN_TOC && ! TARGET_MINIMAL_TOC)) {
15844 ASM_OUTPUT_ALIGN (file, 3);
15845 }
15846
4977bab6 15847 (*targetm.asm_out.internal_label) (file, "LC", labelno);
9878760c 15848
37c37a57
RK
15849 /* Handle FP constants specially. Note that if we have a minimal
15850 TOC, things we put here aren't actually in the TOC, so we can allow
15851 FP constants. */
00b79d54
BE
15852 if (GET_CODE (x) == CONST_DOUBLE &&
15853 (GET_MODE (x) == TFmode || GET_MODE (x) == TDmode))
fcce224d
DE
15854 {
15855 REAL_VALUE_TYPE rv;
15856 long k[4];
15857
15858 REAL_VALUE_FROM_CONST_DOUBLE (rv, x);
00b79d54
BE
15859 if (DECIMAL_FLOAT_MODE_P (GET_MODE (x)))
15860 REAL_VALUE_TO_TARGET_DECIMAL128 (rv, k);
15861 else
15862 REAL_VALUE_TO_TARGET_LONG_DOUBLE (rv, k);
fcce224d
DE
15863
15864 if (TARGET_64BIT)
15865 {
15866 if (TARGET_MINIMAL_TOC)
15867 fputs (DOUBLE_INT_ASM_OP, file);
15868 else
15869 fprintf (file, "\t.tc FT_%lx_%lx_%lx_%lx[TC],",
15870 k[0] & 0xffffffff, k[1] & 0xffffffff,
15871 k[2] & 0xffffffff, k[3] & 0xffffffff);
15872 fprintf (file, "0x%lx%08lx,0x%lx%08lx\n",
15873 k[0] & 0xffffffff, k[1] & 0xffffffff,
15874 k[2] & 0xffffffff, k[3] & 0xffffffff);
15875 return;
15876 }
15877 else
15878 {
15879 if (TARGET_MINIMAL_TOC)
15880 fputs ("\t.long ", file);
15881 else
15882 fprintf (file, "\t.tc FT_%lx_%lx_%lx_%lx[TC],",
15883 k[0] & 0xffffffff, k[1] & 0xffffffff,
15884 k[2] & 0xffffffff, k[3] & 0xffffffff);
15885 fprintf (file, "0x%lx,0x%lx,0x%lx,0x%lx\n",
15886 k[0] & 0xffffffff, k[1] & 0xffffffff,
15887 k[2] & 0xffffffff, k[3] & 0xffffffff);
15888 return;
15889 }
15890 }
00b79d54
BE
15891 else if (GET_CODE (x) == CONST_DOUBLE &&
15892 (GET_MODE (x) == DFmode || GET_MODE (x) == DDmode))
9878760c 15893 {
042259f2
DE
15894 REAL_VALUE_TYPE rv;
15895 long k[2];
0adc764e 15896
042259f2 15897 REAL_VALUE_FROM_CONST_DOUBLE (rv, x);
00b79d54
BE
15898
15899 if (DECIMAL_FLOAT_MODE_P (GET_MODE (x)))
15900 REAL_VALUE_TO_TARGET_DECIMAL64 (rv, k);
15901 else
15902 REAL_VALUE_TO_TARGET_DOUBLE (rv, k);
31bfaa0b 15903
13ded975
DE
15904 if (TARGET_64BIT)
15905 {
15906 if (TARGET_MINIMAL_TOC)
2bfcf297 15907 fputs (DOUBLE_INT_ASM_OP, file);
13ded975 15908 else
2f0552b6
AM
15909 fprintf (file, "\t.tc FD_%lx_%lx[TC],",
15910 k[0] & 0xffffffff, k[1] & 0xffffffff);
15911 fprintf (file, "0x%lx%08lx\n",
15912 k[0] & 0xffffffff, k[1] & 0xffffffff);
13ded975
DE
15913 return;
15914 }
1875cc88 15915 else
13ded975
DE
15916 {
15917 if (TARGET_MINIMAL_TOC)
2bfcf297 15918 fputs ("\t.long ", file);
13ded975 15919 else
2f0552b6
AM
15920 fprintf (file, "\t.tc FD_%lx_%lx[TC],",
15921 k[0] & 0xffffffff, k[1] & 0xffffffff);
15922 fprintf (file, "0x%lx,0x%lx\n",
15923 k[0] & 0xffffffff, k[1] & 0xffffffff);
13ded975
DE
15924 return;
15925 }
9878760c 15926 }
00b79d54
BE
15927 else if (GET_CODE (x) == CONST_DOUBLE &&
15928 (GET_MODE (x) == SFmode || GET_MODE (x) == SDmode))
9878760c 15929 {
042259f2
DE
15930 REAL_VALUE_TYPE rv;
15931 long l;
9878760c 15932
042259f2 15933 REAL_VALUE_FROM_CONST_DOUBLE (rv, x);
00b79d54
BE
15934 if (DECIMAL_FLOAT_MODE_P (GET_MODE (x)))
15935 REAL_VALUE_TO_TARGET_DECIMAL32 (rv, l);
15936 else
15937 REAL_VALUE_TO_TARGET_SINGLE (rv, l);
042259f2 15938
31bfaa0b
DE
15939 if (TARGET_64BIT)
15940 {
15941 if (TARGET_MINIMAL_TOC)
2bfcf297 15942 fputs (DOUBLE_INT_ASM_OP, file);
31bfaa0b 15943 else
2f0552b6
AM
15944 fprintf (file, "\t.tc FS_%lx[TC],", l & 0xffffffff);
15945 fprintf (file, "0x%lx00000000\n", l & 0xffffffff);
31bfaa0b
DE
15946 return;
15947 }
042259f2 15948 else
31bfaa0b
DE
15949 {
15950 if (TARGET_MINIMAL_TOC)
2bfcf297 15951 fputs ("\t.long ", file);
31bfaa0b 15952 else
2f0552b6
AM
15953 fprintf (file, "\t.tc FS_%lx[TC],", l & 0xffffffff);
15954 fprintf (file, "0x%lx\n", l & 0xffffffff);
31bfaa0b
DE
15955 return;
15956 }
042259f2 15957 }
f176e826 15958 else if (GET_MODE (x) == VOIDmode
a9098fd0 15959 && (GET_CODE (x) == CONST_INT || GET_CODE (x) == CONST_DOUBLE))
042259f2 15960 {
e2c953b6 15961 unsigned HOST_WIDE_INT low;
042259f2
DE
15962 HOST_WIDE_INT high;
15963
15964 if (GET_CODE (x) == CONST_DOUBLE)
15965 {
15966 low = CONST_DOUBLE_LOW (x);
15967 high = CONST_DOUBLE_HIGH (x);
15968 }
15969 else
15970#if HOST_BITS_PER_WIDE_INT == 32
15971 {
15972 low = INTVAL (x);
0858c623 15973 high = (low & 0x80000000) ? ~0 : 0;
042259f2
DE
15974 }
15975#else
15976 {
c4ad648e
AM
15977 low = INTVAL (x) & 0xffffffff;
15978 high = (HOST_WIDE_INT) INTVAL (x) >> 32;
042259f2
DE
15979 }
15980#endif
9878760c 15981
a9098fd0
GK
15982 /* TOC entries are always Pmode-sized, but since this
15983 is a bigendian machine then if we're putting smaller
15984 integer constants in the TOC we have to pad them.
15985 (This is still a win over putting the constants in
15986 a separate constant pool, because then we'd have
02a4ec28
FS
15987 to have both a TOC entry _and_ the actual constant.)
15988
15989 For a 32-bit target, CONST_INT values are loaded and shifted
15990 entirely within `low' and can be stored in one TOC entry. */
15991
37409796
NS
15992 /* It would be easy to make this work, but it doesn't now. */
15993 gcc_assert (!TARGET_64BIT || POINTER_SIZE >= GET_MODE_BITSIZE (mode));
02a4ec28
FS
15994
15995 if (POINTER_SIZE > GET_MODE_BITSIZE (mode))
fb52d8de
AM
15996 {
15997#if HOST_BITS_PER_WIDE_INT == 32
15998 lshift_double (low, high, POINTER_SIZE - GET_MODE_BITSIZE (mode),
15999 POINTER_SIZE, &low, &high, 0);
16000#else
16001 low |= high << 32;
16002 low <<= POINTER_SIZE - GET_MODE_BITSIZE (mode);
16003 high = (HOST_WIDE_INT) low >> 32;
16004 low &= 0xffffffff;
16005#endif
16006 }
a9098fd0 16007
13ded975
DE
16008 if (TARGET_64BIT)
16009 {
16010 if (TARGET_MINIMAL_TOC)
2bfcf297 16011 fputs (DOUBLE_INT_ASM_OP, file);
13ded975 16012 else
2f0552b6
AM
16013 fprintf (file, "\t.tc ID_%lx_%lx[TC],",
16014 (long) high & 0xffffffff, (long) low & 0xffffffff);
16015 fprintf (file, "0x%lx%08lx\n",
16016 (long) high & 0xffffffff, (long) low & 0xffffffff);
13ded975
DE
16017 return;
16018 }
1875cc88 16019 else
13ded975 16020 {
02a4ec28
FS
16021 if (POINTER_SIZE < GET_MODE_BITSIZE (mode))
16022 {
16023 if (TARGET_MINIMAL_TOC)
2bfcf297 16024 fputs ("\t.long ", file);
02a4ec28 16025 else
2bfcf297 16026 fprintf (file, "\t.tc ID_%lx_%lx[TC],",
2f0552b6
AM
16027 (long) high & 0xffffffff, (long) low & 0xffffffff);
16028 fprintf (file, "0x%lx,0x%lx\n",
16029 (long) high & 0xffffffff, (long) low & 0xffffffff);
02a4ec28 16030 }
13ded975 16031 else
02a4ec28
FS
16032 {
16033 if (TARGET_MINIMAL_TOC)
2bfcf297 16034 fputs ("\t.long ", file);
02a4ec28 16035 else
2f0552b6
AM
16036 fprintf (file, "\t.tc IS_%lx[TC],", (long) low & 0xffffffff);
16037 fprintf (file, "0x%lx\n", (long) low & 0xffffffff);
02a4ec28 16038 }
13ded975
DE
16039 return;
16040 }
9878760c
RK
16041 }
16042
16043 if (GET_CODE (x) == CONST)
16044 {
37409796 16045 gcc_assert (GET_CODE (XEXP (x, 0)) == PLUS);
2bfcf297 16046
9878760c
RK
16047 base = XEXP (XEXP (x, 0), 0);
16048 offset = INTVAL (XEXP (XEXP (x, 0), 1));
16049 }
f676971a 16050
37409796
NS
16051 switch (GET_CODE (base))
16052 {
16053 case SYMBOL_REF:
16054 name = XSTR (base, 0);
16055 break;
16056
16057 case LABEL_REF:
16058 ASM_GENERATE_INTERNAL_LABEL (buf, "L",
16059 CODE_LABEL_NUMBER (XEXP (base, 0)));
16060 break;
16061
16062 case CODE_LABEL:
16063 ASM_GENERATE_INTERNAL_LABEL (buf, "L", CODE_LABEL_NUMBER (base));
16064 break;
16065
16066 default:
16067 gcc_unreachable ();
16068 }
9878760c 16069
772c5265 16070 real_name = (*targetm.strip_name_encoding) (name);
1875cc88 16071 if (TARGET_MINIMAL_TOC)
2bfcf297 16072 fputs (TARGET_32BIT ? "\t.long " : DOUBLE_INT_ASM_OP, file);
1875cc88
JW
16073 else
16074 {
b6c9286a 16075 fprintf (file, "\t.tc %s", real_name);
9878760c 16076
1875cc88 16077 if (offset < 0)
16fdeb48 16078 fprintf (file, ".N" HOST_WIDE_INT_PRINT_UNSIGNED, - offset);
1875cc88 16079 else if (offset)
16fdeb48 16080 fprintf (file, ".P" HOST_WIDE_INT_PRINT_UNSIGNED, offset);
9878760c 16081
19d2d16f 16082 fputs ("[TC],", file);
1875cc88 16083 }
581bc4de
MM
16084
16085 /* Currently C++ toc references to vtables can be emitted before it
16086 is decided whether the vtable is public or private. If this is
16087 the case, then the linker will eventually complain that there is
16088 a TOC reference to an unknown section. Thus, for vtables only,
16089 we emit the TOC reference to reference the symbol and not the
16090 section. */
28e510bd 16091 if (VTABLE_NAME_P (name))
581bc4de 16092 {
54ee9799 16093 RS6000_OUTPUT_BASENAME (file, name);
581bc4de 16094 if (offset < 0)
16fdeb48 16095 fprintf (file, HOST_WIDE_INT_PRINT_DEC, offset);
581bc4de 16096 else if (offset > 0)
16fdeb48 16097 fprintf (file, "+" HOST_WIDE_INT_PRINT_DEC, offset);
581bc4de
MM
16098 }
16099 else
16100 output_addr_const (file, x);
19d2d16f 16101 putc ('\n', file);
9878760c
RK
16102}
16103\f
16104/* Output an assembler pseudo-op to write an ASCII string of N characters
16105 starting at P to FILE.
16106
16107 On the RS/6000, we have to do this using the .byte operation and
16108 write out special characters outside the quoted string.
16109 Also, the assembler is broken; very long strings are truncated,
a4f6c312 16110 so we must artificially break them up early. */
9878760c
RK
16111
16112void
a2369ed3 16113output_ascii (FILE *file, const char *p, int n)
9878760c
RK
16114{
16115 char c;
16116 int i, count_string;
d330fd93
KG
16117 const char *for_string = "\t.byte \"";
16118 const char *for_decimal = "\t.byte ";
16119 const char *to_close = NULL;
9878760c
RK
16120
16121 count_string = 0;
16122 for (i = 0; i < n; i++)
16123 {
16124 c = *p++;
16125 if (c >= ' ' && c < 0177)
16126 {
16127 if (for_string)
16128 fputs (for_string, file);
16129 putc (c, file);
16130
16131 /* Write two quotes to get one. */
16132 if (c == '"')
16133 {
16134 putc (c, file);
16135 ++count_string;
16136 }
16137
16138 for_string = NULL;
16139 for_decimal = "\"\n\t.byte ";
16140 to_close = "\"\n";
16141 ++count_string;
16142
16143 if (count_string >= 512)
16144 {
16145 fputs (to_close, file);
16146
16147 for_string = "\t.byte \"";
16148 for_decimal = "\t.byte ";
16149 to_close = NULL;
16150 count_string = 0;
16151 }
16152 }
16153 else
16154 {
16155 if (for_decimal)
16156 fputs (for_decimal, file);
16157 fprintf (file, "%d", c);
16158
16159 for_string = "\n\t.byte \"";
16160 for_decimal = ", ";
16161 to_close = "\n";
16162 count_string = 0;
16163 }
16164 }
16165
16166 /* Now close the string if we have written one. Then end the line. */
16167 if (to_close)
9ebbca7d 16168 fputs (to_close, file);
9878760c
RK
16169}
16170\f
16171/* Generate a unique section name for FILENAME for a section type
16172 represented by SECTION_DESC. Output goes into BUF.
16173
16174 SECTION_DESC can be any string, as long as it is different for each
16175 possible section type.
16176
16177 We name the section in the same manner as xlc. The name begins with an
16178 underscore followed by the filename (after stripping any leading directory
11e5fe42
RK
16179 names) with the last period replaced by the string SECTION_DESC. If
16180 FILENAME does not contain a period, SECTION_DESC is appended to the end of
16181 the name. */
9878760c
RK
16182
16183void
f676971a 16184rs6000_gen_section_name (char **buf, const char *filename,
c4ad648e 16185 const char *section_desc)
9878760c 16186{
9ebbca7d 16187 const char *q, *after_last_slash, *last_period = 0;
9878760c
RK
16188 char *p;
16189 int len;
9878760c
RK
16190
16191 after_last_slash = filename;
16192 for (q = filename; *q; q++)
11e5fe42
RK
16193 {
16194 if (*q == '/')
16195 after_last_slash = q + 1;
16196 else if (*q == '.')
16197 last_period = q;
16198 }
9878760c 16199
11e5fe42 16200 len = strlen (after_last_slash) + strlen (section_desc) + 2;
6d9f628e 16201 *buf = (char *) xmalloc (len);
9878760c
RK
16202
16203 p = *buf;
16204 *p++ = '_';
16205
16206 for (q = after_last_slash; *q; q++)
16207 {
11e5fe42 16208 if (q == last_period)
c4ad648e 16209 {
9878760c
RK
16210 strcpy (p, section_desc);
16211 p += strlen (section_desc);
e3981aab 16212 break;
c4ad648e 16213 }
9878760c 16214
e9a780ec 16215 else if (ISALNUM (*q))
c4ad648e 16216 *p++ = *q;
9878760c
RK
16217 }
16218
11e5fe42 16219 if (last_period == 0)
9878760c
RK
16220 strcpy (p, section_desc);
16221 else
16222 *p = '\0';
16223}
e165f3f0 16224\f
a4f6c312 16225/* Emit profile function. */
411707f4 16226
411707f4 16227void
a2369ed3 16228output_profile_hook (int labelno ATTRIBUTE_UNUSED)
411707f4 16229{
858081ad
AH
16230 /* Non-standard profiling for kernels, which just saves LR then calls
16231 _mcount without worrying about arg saves. The idea is to change
16232 the function prologue as little as possible as it isn't easy to
16233 account for arg save/restore code added just for _mcount. */
ffcfcb5f
AM
16234 if (TARGET_PROFILE_KERNEL)
16235 return;
16236
8480e480
CC
16237 if (DEFAULT_ABI == ABI_AIX)
16238 {
9739c90c
JJ
16239#ifndef NO_PROFILE_COUNTERS
16240# define NO_PROFILE_COUNTERS 0
16241#endif
f676971a 16242 if (NO_PROFILE_COUNTERS)
9739c90c
JJ
16243 emit_library_call (init_one_libfunc (RS6000_MCOUNT), 0, VOIDmode, 0);
16244 else
16245 {
16246 char buf[30];
16247 const char *label_name;
16248 rtx fun;
411707f4 16249
9739c90c
JJ
16250 ASM_GENERATE_INTERNAL_LABEL (buf, "LP", labelno);
16251 label_name = (*targetm.strip_name_encoding) (ggc_strdup (buf));
16252 fun = gen_rtx_SYMBOL_REF (Pmode, label_name);
411707f4 16253
9739c90c
JJ
16254 emit_library_call (init_one_libfunc (RS6000_MCOUNT), 0, VOIDmode, 1,
16255 fun, Pmode);
16256 }
8480e480 16257 }
ee890fe2
SS
16258 else if (DEFAULT_ABI == ABI_DARWIN)
16259 {
d5fa86ba 16260 const char *mcount_name = RS6000_MCOUNT;
ee890fe2
SS
16261 int caller_addr_regno = LINK_REGISTER_REGNUM;
16262
16263 /* Be conservative and always set this, at least for now. */
16264 current_function_uses_pic_offset_table = 1;
16265
16266#if TARGET_MACHO
16267 /* For PIC code, set up a stub and collect the caller's address
16268 from r0, which is where the prologue puts it. */
11abc112
MM
16269 if (MACHOPIC_INDIRECT
16270 && current_function_uses_pic_offset_table)
16271 caller_addr_regno = 0;
ee890fe2
SS
16272#endif
16273 emit_library_call (gen_rtx_SYMBOL_REF (Pmode, mcount_name),
16274 0, VOIDmode, 1,
16275 gen_rtx_REG (Pmode, caller_addr_regno), Pmode);
16276 }
411707f4
CC
16277}
16278
a4f6c312 16279/* Write function profiler code. */
e165f3f0
RK
16280
16281void
a2369ed3 16282output_function_profiler (FILE *file, int labelno)
e165f3f0 16283{
3daf36a4 16284 char buf[100];
e165f3f0 16285
38c1f2d7 16286 switch (DEFAULT_ABI)
3daf36a4 16287 {
38c1f2d7 16288 default:
37409796 16289 gcc_unreachable ();
38c1f2d7
MM
16290
16291 case ABI_V4:
09eeeacb
AM
16292 if (!TARGET_32BIT)
16293 {
d4ee4d25 16294 warning (0, "no profiling of 64-bit code for this ABI");
09eeeacb
AM
16295 return;
16296 }
ffcfcb5f 16297 ASM_GENERATE_INTERNAL_LABEL (buf, "LP", labelno);
38c1f2d7 16298 fprintf (file, "\tmflr %s\n", reg_names[0]);
71625f3d
AM
16299 if (NO_PROFILE_COUNTERS)
16300 {
16301 asm_fprintf (file, "\t{st|stw} %s,4(%s)\n",
16302 reg_names[0], reg_names[1]);
16303 }
16304 else if (TARGET_SECURE_PLT && flag_pic)
16305 {
16306 asm_fprintf (file, "\tbcl 20,31,1f\n1:\n\t{st|stw} %s,4(%s)\n",
16307 reg_names[0], reg_names[1]);
16308 asm_fprintf (file, "\tmflr %s\n", reg_names[12]);
16309 asm_fprintf (file, "\t{cau|addis} %s,%s,",
16310 reg_names[12], reg_names[12]);
16311 assemble_name (file, buf);
16312 asm_fprintf (file, "-1b@ha\n\t{cal|la} %s,", reg_names[0]);
16313 assemble_name (file, buf);
16314 asm_fprintf (file, "-1b@l(%s)\n", reg_names[12]);
16315 }
16316 else if (flag_pic == 1)
38c1f2d7 16317 {
dfdfa60f 16318 fputs ("\tbl _GLOBAL_OFFSET_TABLE_@local-4\n", file);
71625f3d
AM
16319 asm_fprintf (file, "\t{st|stw} %s,4(%s)\n",
16320 reg_names[0], reg_names[1]);
17167fd8 16321 asm_fprintf (file, "\tmflr %s\n", reg_names[12]);
dfdfa60f 16322 asm_fprintf (file, "\t{l|lwz} %s,", reg_names[0]);
38c1f2d7 16323 assemble_name (file, buf);
17167fd8 16324 asm_fprintf (file, "@got(%s)\n", reg_names[12]);
38c1f2d7 16325 }
9ebbca7d 16326 else if (flag_pic > 1)
38c1f2d7 16327 {
71625f3d
AM
16328 asm_fprintf (file, "\t{st|stw} %s,4(%s)\n",
16329 reg_names[0], reg_names[1]);
9ebbca7d 16330 /* Now, we need to get the address of the label. */
71625f3d 16331 fputs ("\tbcl 20,31,1f\n\t.long ", file);
034e84c4 16332 assemble_name (file, buf);
9ebbca7d
GK
16333 fputs ("-.\n1:", file);
16334 asm_fprintf (file, "\tmflr %s\n", reg_names[11]);
f676971a 16335 asm_fprintf (file, "\t{l|lwz} %s,0(%s)\n",
9ebbca7d
GK
16336 reg_names[0], reg_names[11]);
16337 asm_fprintf (file, "\t{cax|add} %s,%s,%s\n",
16338 reg_names[0], reg_names[0], reg_names[11]);
38c1f2d7 16339 }
38c1f2d7
MM
16340 else
16341 {
17167fd8 16342 asm_fprintf (file, "\t{liu|lis} %s,", reg_names[12]);
38c1f2d7 16343 assemble_name (file, buf);
dfdfa60f 16344 fputs ("@ha\n", file);
71625f3d
AM
16345 asm_fprintf (file, "\t{st|stw} %s,4(%s)\n",
16346 reg_names[0], reg_names[1]);
a260abc9 16347 asm_fprintf (file, "\t{cal|la} %s,", reg_names[0]);
38c1f2d7 16348 assemble_name (file, buf);
17167fd8 16349 asm_fprintf (file, "@l(%s)\n", reg_names[12]);
38c1f2d7
MM
16350 }
16351
50d440bc 16352 /* ABI_V4 saves the static chain reg with ASM_OUTPUT_REG_PUSH. */
3b6ce0af
DE
16353 fprintf (file, "\tbl %s%s\n",
16354 RS6000_MCOUNT, flag_pic ? "@plt" : "");
38c1f2d7
MM
16355 break;
16356
16357 case ABI_AIX:
ee890fe2 16358 case ABI_DARWIN:
ffcfcb5f
AM
16359 if (!TARGET_PROFILE_KERNEL)
16360 {
a3c9585f 16361 /* Don't do anything, done in output_profile_hook (). */
ffcfcb5f
AM
16362 }
16363 else
16364 {
37409796 16365 gcc_assert (!TARGET_32BIT);
ffcfcb5f
AM
16366
16367 asm_fprintf (file, "\tmflr %s\n", reg_names[0]);
16368 asm_fprintf (file, "\tstd %s,16(%s)\n", reg_names[0], reg_names[1]);
16369
6de9cd9a 16370 if (cfun->static_chain_decl != NULL)
ffcfcb5f
AM
16371 {
16372 asm_fprintf (file, "\tstd %s,24(%s)\n",
16373 reg_names[STATIC_CHAIN_REGNUM], reg_names[1]);
16374 fprintf (file, "\tbl %s\n", RS6000_MCOUNT);
16375 asm_fprintf (file, "\tld %s,24(%s)\n",
16376 reg_names[STATIC_CHAIN_REGNUM], reg_names[1]);
16377 }
16378 else
16379 fprintf (file, "\tbl %s\n", RS6000_MCOUNT);
16380 }
38c1f2d7
MM
16381 break;
16382 }
e165f3f0 16383}
a251ffd0 16384
b54cf83a 16385\f
b54cf83a
DE
16386/* Power4 load update and store update instructions are cracked into a
16387 load or store and an integer insn which are executed in the same cycle.
16388 Branches have their own dispatch slot which does not count against the
16389 GCC issue rate, but it changes the program flow so there are no other
16390 instructions to issue in this cycle. */
16391
16392static int
f676971a
EC
16393rs6000_variable_issue (FILE *stream ATTRIBUTE_UNUSED,
16394 int verbose ATTRIBUTE_UNUSED,
a2369ed3 16395 rtx insn, int more)
b54cf83a
DE
16396{
16397 if (GET_CODE (PATTERN (insn)) == USE
16398 || GET_CODE (PATTERN (insn)) == CLOBBER)
16399 return more;
16400
ec507f2d 16401 if (rs6000_sched_groups)
b54cf83a 16402 {
cbe26ab8 16403 if (is_microcoded_insn (insn))
c4ad648e 16404 return 0;
cbe26ab8 16405 else if (is_cracked_insn (insn))
c4ad648e 16406 return more > 2 ? more - 2 : 0;
b54cf83a 16407 }
165b263e
DE
16408
16409 return more - 1;
b54cf83a
DE
16410}
16411
a251ffd0
TG
16412/* Adjust the cost of a scheduling dependency. Return the new cost of
16413 a dependency LINK or INSN on DEP_INSN. COST is the current cost. */
16414
c237e94a 16415static int
0a4f0294 16416rs6000_adjust_cost (rtx insn, rtx link, rtx dep_insn, int cost)
a251ffd0
TG
16417{
16418 if (! recog_memoized (insn))
16419 return 0;
16420
16421 if (REG_NOTE_KIND (link) != 0)
16422 return 0;
16423
16424 if (REG_NOTE_KIND (link) == 0)
16425 {
ed947a96
DJ
16426 /* Data dependency; DEP_INSN writes a register that INSN reads
16427 some cycles later. */
c9dbf840
DE
16428
16429 /* Separate a load from a narrower, dependent store. */
16430 if (rs6000_sched_groups
16431 && GET_CODE (PATTERN (insn)) == SET
16432 && GET_CODE (PATTERN (dep_insn)) == SET
16433 && GET_CODE (XEXP (PATTERN (insn), 1)) == MEM
16434 && GET_CODE (XEXP (PATTERN (dep_insn), 0)) == MEM
16435 && (GET_MODE_SIZE (GET_MODE (XEXP (PATTERN (insn), 1)))
16436 > GET_MODE_SIZE (GET_MODE (XEXP (PATTERN (dep_insn), 0)))))
16437 return cost + 14;
16438
ed947a96
DJ
16439 switch (get_attr_type (insn))
16440 {
16441 case TYPE_JMPREG:
309323c2 16442 /* Tell the first scheduling pass about the latency between
ed947a96
DJ
16443 a mtctr and bctr (and mtlr and br/blr). The first
16444 scheduling pass will not know about this latency since
16445 the mtctr instruction, which has the latency associated
16446 to it, will be generated by reload. */
309323c2 16447 return TARGET_POWER ? 5 : 4;
ed947a96
DJ
16448 case TYPE_BRANCH:
16449 /* Leave some extra cycles between a compare and its
16450 dependent branch, to inhibit expensive mispredicts. */
309323c2
DE
16451 if ((rs6000_cpu_attr == CPU_PPC603
16452 || rs6000_cpu_attr == CPU_PPC604
16453 || rs6000_cpu_attr == CPU_PPC604E
16454 || rs6000_cpu_attr == CPU_PPC620
16455 || rs6000_cpu_attr == CPU_PPC630
16456 || rs6000_cpu_attr == CPU_PPC750
16457 || rs6000_cpu_attr == CPU_PPC7400
16458 || rs6000_cpu_attr == CPU_PPC7450
ec507f2d
DE
16459 || rs6000_cpu_attr == CPU_POWER4
16460 || rs6000_cpu_attr == CPU_POWER5)
ed947a96
DJ
16461 && recog_memoized (dep_insn)
16462 && (INSN_CODE (dep_insn) >= 0)
b54cf83a
DE
16463 && (get_attr_type (dep_insn) == TYPE_CMP
16464 || get_attr_type (dep_insn) == TYPE_COMPARE
ed947a96 16465 || get_attr_type (dep_insn) == TYPE_DELAYED_COMPARE
9259f3b0
DE
16466 || get_attr_type (dep_insn) == TYPE_IMUL_COMPARE
16467 || get_attr_type (dep_insn) == TYPE_LMUL_COMPARE
ed947a96 16468 || get_attr_type (dep_insn) == TYPE_FPCOMPARE
b54cf83a
DE
16469 || get_attr_type (dep_insn) == TYPE_CR_LOGICAL
16470 || get_attr_type (dep_insn) == TYPE_DELAYED_CR))
ed947a96
DJ
16471 return cost + 2;
16472 default:
16473 break;
16474 }
a251ffd0
TG
16475 /* Fall out to return default cost. */
16476 }
16477
16478 return cost;
16479}
b6c9286a 16480
cbe26ab8 16481/* The function returns a true if INSN is microcoded.
839a4992 16482 Return false otherwise. */
cbe26ab8
DN
16483
16484static bool
16485is_microcoded_insn (rtx insn)
16486{
16487 if (!insn || !INSN_P (insn)
16488 || GET_CODE (PATTERN (insn)) == USE
16489 || GET_CODE (PATTERN (insn)) == CLOBBER)
16490 return false;
16491
ec507f2d 16492 if (rs6000_sched_groups)
cbe26ab8
DN
16493 {
16494 enum attr_type type = get_attr_type (insn);
16495 if (type == TYPE_LOAD_EXT_U
16496 || type == TYPE_LOAD_EXT_UX
16497 || type == TYPE_LOAD_UX
16498 || type == TYPE_STORE_UX
16499 || type == TYPE_MFCR)
c4ad648e 16500 return true;
cbe26ab8
DN
16501 }
16502
16503 return false;
16504}
16505
5c425df5 16506/* The function returns a nonzero value if INSN can be scheduled only
cbe26ab8
DN
16507 as the first insn in a dispatch group ("dispatch-slot restricted").
16508 In this case, the returned value indicates how many dispatch slots
16509 the insn occupies (at the beginning of the group).
79ae11c4
DN
16510 Return 0 otherwise. */
16511
cbe26ab8 16512static int
79ae11c4
DN
16513is_dispatch_slot_restricted (rtx insn)
16514{
16515 enum attr_type type;
16516
ec507f2d 16517 if (!rs6000_sched_groups)
79ae11c4
DN
16518 return 0;
16519
16520 if (!insn
16521 || insn == NULL_RTX
16522 || GET_CODE (insn) == NOTE
16523 || GET_CODE (PATTERN (insn)) == USE
16524 || GET_CODE (PATTERN (insn)) == CLOBBER)
16525 return 0;
16526
16527 type = get_attr_type (insn);
16528
ec507f2d
DE
16529 switch (type)
16530 {
16531 case TYPE_MFCR:
16532 case TYPE_MFCRF:
16533 case TYPE_MTCR:
16534 case TYPE_DELAYED_CR:
16535 case TYPE_CR_LOGICAL:
16536 case TYPE_MTJMPR:
16537 case TYPE_MFJMPR:
16538 return 1;
16539 case TYPE_IDIV:
16540 case TYPE_LDIV:
16541 return 2;
b52110d4
DE
16542 case TYPE_LOAD_L:
16543 case TYPE_STORE_C:
16544 case TYPE_ISYNC:
16545 case TYPE_SYNC:
16546 return 4;
ec507f2d
DE
16547 default:
16548 if (rs6000_cpu == PROCESSOR_POWER5
16549 && is_cracked_insn (insn))
16550 return 2;
16551 return 0;
16552 }
79ae11c4
DN
16553}
16554
cbe26ab8
DN
16555/* The function returns true if INSN is cracked into 2 instructions
16556 by the processor (and therefore occupies 2 issue slots). */
16557
16558static bool
16559is_cracked_insn (rtx insn)
16560{
16561 if (!insn || !INSN_P (insn)
16562 || GET_CODE (PATTERN (insn)) == USE
16563 || GET_CODE (PATTERN (insn)) == CLOBBER)
16564 return false;
16565
ec507f2d 16566 if (rs6000_sched_groups)
cbe26ab8
DN
16567 {
16568 enum attr_type type = get_attr_type (insn);
16569 if (type == TYPE_LOAD_U || type == TYPE_STORE_U
c4ad648e
AM
16570 || type == TYPE_FPLOAD_U || type == TYPE_FPSTORE_U
16571 || type == TYPE_FPLOAD_UX || type == TYPE_FPSTORE_UX
16572 || type == TYPE_LOAD_EXT || type == TYPE_DELAYED_CR
16573 || type == TYPE_COMPARE || type == TYPE_DELAYED_COMPARE
16574 || type == TYPE_IMUL_COMPARE || type == TYPE_LMUL_COMPARE
16575 || type == TYPE_IDIV || type == TYPE_LDIV
16576 || type == TYPE_INSERT_WORD)
16577 return true;
cbe26ab8
DN
16578 }
16579
16580 return false;
16581}
16582
16583/* The function returns true if INSN can be issued only from
a3c9585f 16584 the branch slot. */
cbe26ab8
DN
16585
16586static bool
16587is_branch_slot_insn (rtx insn)
16588{
16589 if (!insn || !INSN_P (insn)
16590 || GET_CODE (PATTERN (insn)) == USE
16591 || GET_CODE (PATTERN (insn)) == CLOBBER)
16592 return false;
16593
ec507f2d 16594 if (rs6000_sched_groups)
cbe26ab8
DN
16595 {
16596 enum attr_type type = get_attr_type (insn);
16597 if (type == TYPE_BRANCH || type == TYPE_JMPREG)
f676971a 16598 return true;
cbe26ab8
DN
16599 return false;
16600 }
16601
16602 return false;
16603}
79ae11c4 16604
a4f6c312 16605/* A C statement (sans semicolon) to update the integer scheduling
79ae11c4
DN
16606 priority INSN_PRIORITY (INSN). Increase the priority to execute the
16607 INSN earlier, reduce the priority to execute INSN later. Do not
a4f6c312
SS
16608 define this macro if you do not need to adjust the scheduling
16609 priorities of insns. */
bef84347 16610
c237e94a 16611static int
a2369ed3 16612rs6000_adjust_priority (rtx insn ATTRIBUTE_UNUSED, int priority)
bef84347 16613{
a4f6c312
SS
16614 /* On machines (like the 750) which have asymmetric integer units,
16615 where one integer unit can do multiply and divides and the other
16616 can't, reduce the priority of multiply/divide so it is scheduled
16617 before other integer operations. */
bef84347
VM
16618
16619#if 0
2c3c49de 16620 if (! INSN_P (insn))
bef84347
VM
16621 return priority;
16622
16623 if (GET_CODE (PATTERN (insn)) == USE)
16624 return priority;
16625
16626 switch (rs6000_cpu_attr) {
16627 case CPU_PPC750:
16628 switch (get_attr_type (insn))
16629 {
16630 default:
16631 break;
16632
16633 case TYPE_IMUL:
16634 case TYPE_IDIV:
3cb999d8
DE
16635 fprintf (stderr, "priority was %#x (%d) before adjustment\n",
16636 priority, priority);
bef84347
VM
16637 if (priority >= 0 && priority < 0x01000000)
16638 priority >>= 3;
16639 break;
16640 }
16641 }
16642#endif
16643
79ae11c4
DN
16644 if (is_dispatch_slot_restricted (insn)
16645 && reload_completed
f676971a 16646 && current_sched_info->sched_max_insns_priority
79ae11c4
DN
16647 && rs6000_sched_restricted_insns_priority)
16648 {
16649
c4ad648e
AM
16650 /* Prioritize insns that can be dispatched only in the first
16651 dispatch slot. */
79ae11c4 16652 if (rs6000_sched_restricted_insns_priority == 1)
f676971a
EC
16653 /* Attach highest priority to insn. This means that in
16654 haifa-sched.c:ready_sort(), dispatch-slot restriction considerations
79ae11c4 16655 precede 'priority' (critical path) considerations. */
f676971a 16656 return current_sched_info->sched_max_insns_priority;
79ae11c4 16657 else if (rs6000_sched_restricted_insns_priority == 2)
f676971a 16658 /* Increase priority of insn by a minimal amount. This means that in
c4ad648e
AM
16659 haifa-sched.c:ready_sort(), only 'priority' (critical path)
16660 considerations precede dispatch-slot restriction considerations. */
f676971a
EC
16661 return (priority + 1);
16662 }
79ae11c4 16663
bef84347
VM
16664 return priority;
16665}
16666
a4f6c312
SS
16667/* Return how many instructions the machine can issue per cycle. */
16668
c237e94a 16669static int
863d938c 16670rs6000_issue_rate (void)
b6c9286a 16671{
3317bab1
DE
16672 /* Use issue rate of 1 for first scheduling pass to decrease degradation. */
16673 if (!reload_completed)
16674 return 1;
16675
b6c9286a 16676 switch (rs6000_cpu_attr) {
3cb999d8
DE
16677 case CPU_RIOS1: /* ? */
16678 case CPU_RS64A:
16679 case CPU_PPC601: /* ? */
ed947a96 16680 case CPU_PPC7450:
3cb999d8 16681 return 3;
b54cf83a 16682 case CPU_PPC440:
b6c9286a 16683 case CPU_PPC603:
bef84347 16684 case CPU_PPC750:
ed947a96 16685 case CPU_PPC7400:
be12c2b0 16686 case CPU_PPC8540:
f676971a 16687 return 2;
3cb999d8 16688 case CPU_RIOS2:
b6c9286a 16689 case CPU_PPC604:
19684119 16690 case CPU_PPC604E:
b6c9286a 16691 case CPU_PPC620:
3cb999d8 16692 case CPU_PPC630:
b6c9286a 16693 return 4;
cbe26ab8 16694 case CPU_POWER4:
ec507f2d 16695 case CPU_POWER5:
cbe26ab8 16696 return 5;
b6c9286a
MM
16697 default:
16698 return 1;
16699 }
16700}
16701
be12c2b0
VM
16702/* Return how many instructions to look ahead for better insn
16703 scheduling. */
16704
16705static int
863d938c 16706rs6000_use_sched_lookahead (void)
be12c2b0
VM
16707{
16708 if (rs6000_cpu_attr == CPU_PPC8540)
16709 return 4;
16710 return 0;
16711}
16712
569fa502
DN
16713/* Determine is PAT refers to memory. */
16714
16715static bool
16716is_mem_ref (rtx pat)
16717{
16718 const char * fmt;
16719 int i, j;
16720 bool ret = false;
16721
16722 if (GET_CODE (pat) == MEM)
16723 return true;
16724
16725 /* Recursively process the pattern. */
16726 fmt = GET_RTX_FORMAT (GET_CODE (pat));
16727
16728 for (i = GET_RTX_LENGTH (GET_CODE (pat)) - 1; i >= 0 && !ret; i--)
16729 {
16730 if (fmt[i] == 'e')
16731 ret |= is_mem_ref (XEXP (pat, i));
16732 else if (fmt[i] == 'E')
16733 for (j = XVECLEN (pat, i) - 1; j >= 0; j--)
16734 ret |= is_mem_ref (XVECEXP (pat, i, j));
16735 }
16736
16737 return ret;
16738}
16739
16740/* Determine if PAT is a PATTERN of a load insn. */
f676971a 16741
569fa502
DN
16742static bool
16743is_load_insn1 (rtx pat)
16744{
16745 if (!pat || pat == NULL_RTX)
16746 return false;
16747
16748 if (GET_CODE (pat) == SET)
16749 return is_mem_ref (SET_SRC (pat));
16750
16751 if (GET_CODE (pat) == PARALLEL)
16752 {
16753 int i;
16754
16755 for (i = 0; i < XVECLEN (pat, 0); i++)
16756 if (is_load_insn1 (XVECEXP (pat, 0, i)))
16757 return true;
16758 }
16759
16760 return false;
16761}
16762
16763/* Determine if INSN loads from memory. */
16764
16765static bool
16766is_load_insn (rtx insn)
16767{
16768 if (!insn || !INSN_P (insn))
16769 return false;
16770
16771 if (GET_CODE (insn) == CALL_INSN)
16772 return false;
16773
16774 return is_load_insn1 (PATTERN (insn));
16775}
16776
16777/* Determine if PAT is a PATTERN of a store insn. */
16778
16779static bool
16780is_store_insn1 (rtx pat)
16781{
16782 if (!pat || pat == NULL_RTX)
16783 return false;
16784
16785 if (GET_CODE (pat) == SET)
16786 return is_mem_ref (SET_DEST (pat));
16787
16788 if (GET_CODE (pat) == PARALLEL)
16789 {
16790 int i;
16791
16792 for (i = 0; i < XVECLEN (pat, 0); i++)
16793 if (is_store_insn1 (XVECEXP (pat, 0, i)))
16794 return true;
16795 }
16796
16797 return false;
16798}
16799
16800/* Determine if INSN stores to memory. */
16801
16802static bool
16803is_store_insn (rtx insn)
16804{
16805 if (!insn || !INSN_P (insn))
16806 return false;
16807
16808 return is_store_insn1 (PATTERN (insn));
16809}
16810
16811/* Returns whether the dependence between INSN and NEXT is considered
16812 costly by the given target. */
16813
16814static bool
c4ad648e
AM
16815rs6000_is_costly_dependence (rtx insn, rtx next, rtx link, int cost,
16816 int distance)
f676971a 16817{
aabcd309 16818 /* If the flag is not enabled - no dependence is considered costly;
f676971a 16819 allow all dependent insns in the same group.
569fa502
DN
16820 This is the most aggressive option. */
16821 if (rs6000_sched_costly_dep == no_dep_costly)
16822 return false;
16823
f676971a 16824 /* If the flag is set to 1 - a dependence is always considered costly;
569fa502
DN
16825 do not allow dependent instructions in the same group.
16826 This is the most conservative option. */
16827 if (rs6000_sched_costly_dep == all_deps_costly)
f676971a 16828 return true;
569fa502 16829
f676971a
EC
16830 if (rs6000_sched_costly_dep == store_to_load_dep_costly
16831 && is_load_insn (next)
569fa502
DN
16832 && is_store_insn (insn))
16833 /* Prevent load after store in the same group. */
16834 return true;
16835
16836 if (rs6000_sched_costly_dep == true_store_to_load_dep_costly
f676971a 16837 && is_load_insn (next)
569fa502
DN
16838 && is_store_insn (insn)
16839 && (!link || (int) REG_NOTE_KIND (link) == 0))
c4ad648e
AM
16840 /* Prevent load after store in the same group if it is a true
16841 dependence. */
569fa502 16842 return true;
f676971a
EC
16843
16844 /* The flag is set to X; dependences with latency >= X are considered costly,
569fa502
DN
16845 and will not be scheduled in the same group. */
16846 if (rs6000_sched_costly_dep <= max_dep_latency
16847 && ((cost - distance) >= (int)rs6000_sched_costly_dep))
16848 return true;
16849
16850 return false;
16851}
16852
f676971a 16853/* Return the next insn after INSN that is found before TAIL is reached,
cbe26ab8
DN
16854 skipping any "non-active" insns - insns that will not actually occupy
16855 an issue slot. Return NULL_RTX if such an insn is not found. */
16856
16857static rtx
16858get_next_active_insn (rtx insn, rtx tail)
16859{
f489aff8 16860 if (insn == NULL_RTX || insn == tail)
cbe26ab8
DN
16861 return NULL_RTX;
16862
f489aff8 16863 while (1)
cbe26ab8 16864 {
f489aff8
AM
16865 insn = NEXT_INSN (insn);
16866 if (insn == NULL_RTX || insn == tail)
16867 return NULL_RTX;
cbe26ab8 16868
f489aff8
AM
16869 if (CALL_P (insn)
16870 || JUMP_P (insn)
16871 || (NONJUMP_INSN_P (insn)
16872 && GET_CODE (PATTERN (insn)) != USE
16873 && GET_CODE (PATTERN (insn)) != CLOBBER
309ebcd0 16874 && INSN_CODE (insn) != CODE_FOR_stack_tie))
f489aff8
AM
16875 break;
16876 }
16877 return insn;
cbe26ab8
DN
16878}
16879
839a4992 16880/* Return whether the presence of INSN causes a dispatch group termination
cbe26ab8
DN
16881 of group WHICH_GROUP.
16882
16883 If WHICH_GROUP == current_group, this function will return true if INSN
16884 causes the termination of the current group (i.e, the dispatch group to
16885 which INSN belongs). This means that INSN will be the last insn in the
16886 group it belongs to.
16887
16888 If WHICH_GROUP == previous_group, this function will return true if INSN
16889 causes the termination of the previous group (i.e, the dispatch group that
16890 precedes the group to which INSN belongs). This means that INSN will be
16891 the first insn in the group it belongs to). */
16892
16893static bool
16894insn_terminates_group_p (rtx insn, enum group_termination which_group)
16895{
16896 enum attr_type type;
16897
16898 if (! insn)
16899 return false;
569fa502 16900
cbe26ab8
DN
16901 type = get_attr_type (insn);
16902
16903 if (is_microcoded_insn (insn))
16904 return true;
16905
16906 if (which_group == current_group)
16907 {
16908 if (is_branch_slot_insn (insn))
c4ad648e 16909 return true;
cbe26ab8
DN
16910 return false;
16911 }
16912 else if (which_group == previous_group)
16913 {
16914 if (is_dispatch_slot_restricted (insn))
c4ad648e 16915 return true;
cbe26ab8
DN
16916 return false;
16917 }
16918
16919 return false;
16920}
16921
839a4992 16922/* Return true if it is recommended to keep NEXT_INSN "far" (in a separate
cbe26ab8
DN
16923 dispatch group) from the insns in GROUP_INSNS. Return false otherwise. */
16924
16925static bool
16926is_costly_group (rtx *group_insns, rtx next_insn)
16927{
16928 int i;
16929 rtx link;
16930 int cost;
16931 int issue_rate = rs6000_issue_rate ();
16932
16933 for (i = 0; i < issue_rate; i++)
16934 {
16935 rtx insn = group_insns[i];
16936 if (!insn)
c4ad648e 16937 continue;
cbe26ab8 16938 for (link = INSN_DEPEND (insn); link != 0; link = XEXP (link, 1))
c4ad648e
AM
16939 {
16940 rtx next = XEXP (link, 0);
16941 if (next == next_insn)
16942 {
16943 cost = insn_cost (insn, link, next_insn);
16944 if (rs6000_is_costly_dependence (insn, next_insn, link, cost, 0))
16945 return true;
16946 }
16947 }
cbe26ab8
DN
16948 }
16949
16950 return false;
16951}
16952
f676971a 16953/* Utility of the function redefine_groups.
cbe26ab8
DN
16954 Check if it is too costly to schedule NEXT_INSN together with GROUP_INSNS
16955 in the same dispatch group. If so, insert nops before NEXT_INSN, in order
16956 to keep it "far" (in a separate group) from GROUP_INSNS, following
16957 one of the following schemes, depending on the value of the flag
16958 -minsert_sched_nops = X:
16959 (1) X == sched_finish_regroup_exact: insert exactly as many nops as needed
839a4992 16960 in order to force NEXT_INSN into a separate group.
f676971a
EC
16961 (2) X < sched_finish_regroup_exact: insert exactly X nops.
16962 GROUP_END, CAN_ISSUE_MORE and GROUP_COUNT record the state after nop
cbe26ab8
DN
16963 insertion (has a group just ended, how many vacant issue slots remain in the
16964 last group, and how many dispatch groups were encountered so far). */
16965
f676971a 16966static int
c4ad648e
AM
16967force_new_group (int sched_verbose, FILE *dump, rtx *group_insns,
16968 rtx next_insn, bool *group_end, int can_issue_more,
16969 int *group_count)
cbe26ab8
DN
16970{
16971 rtx nop;
16972 bool force;
16973 int issue_rate = rs6000_issue_rate ();
16974 bool end = *group_end;
16975 int i;
16976
16977 if (next_insn == NULL_RTX)
16978 return can_issue_more;
16979
16980 if (rs6000_sched_insert_nops > sched_finish_regroup_exact)
16981 return can_issue_more;
16982
16983 force = is_costly_group (group_insns, next_insn);
16984 if (!force)
16985 return can_issue_more;
16986
16987 if (sched_verbose > 6)
16988 fprintf (dump,"force: group count = %d, can_issue_more = %d\n",
c4ad648e 16989 *group_count ,can_issue_more);
cbe26ab8
DN
16990
16991 if (rs6000_sched_insert_nops == sched_finish_regroup_exact)
16992 {
16993 if (*group_end)
c4ad648e 16994 can_issue_more = 0;
cbe26ab8
DN
16995
16996 /* Since only a branch can be issued in the last issue_slot, it is
16997 sufficient to insert 'can_issue_more - 1' nops if next_insn is not
16998 a branch. If next_insn is a branch, we insert 'can_issue_more' nops;
c4ad648e
AM
16999 in this case the last nop will start a new group and the branch
17000 will be forced to the new group. */
cbe26ab8 17001 if (can_issue_more && !is_branch_slot_insn (next_insn))
c4ad648e 17002 can_issue_more--;
cbe26ab8
DN
17003
17004 while (can_issue_more > 0)
c4ad648e 17005 {
9390387d 17006 nop = gen_nop ();
c4ad648e
AM
17007 emit_insn_before (nop, next_insn);
17008 can_issue_more--;
17009 }
cbe26ab8
DN
17010
17011 *group_end = true;
17012 return 0;
f676971a 17013 }
cbe26ab8
DN
17014
17015 if (rs6000_sched_insert_nops < sched_finish_regroup_exact)
17016 {
17017 int n_nops = rs6000_sched_insert_nops;
17018
f676971a 17019 /* Nops can't be issued from the branch slot, so the effective
c4ad648e 17020 issue_rate for nops is 'issue_rate - 1'. */
cbe26ab8 17021 if (can_issue_more == 0)
c4ad648e 17022 can_issue_more = issue_rate;
cbe26ab8
DN
17023 can_issue_more--;
17024 if (can_issue_more == 0)
c4ad648e
AM
17025 {
17026 can_issue_more = issue_rate - 1;
17027 (*group_count)++;
17028 end = true;
17029 for (i = 0; i < issue_rate; i++)
17030 {
17031 group_insns[i] = 0;
17032 }
17033 }
cbe26ab8
DN
17034
17035 while (n_nops > 0)
c4ad648e
AM
17036 {
17037 nop = gen_nop ();
17038 emit_insn_before (nop, next_insn);
17039 if (can_issue_more == issue_rate - 1) /* new group begins */
17040 end = false;
17041 can_issue_more--;
17042 if (can_issue_more == 0)
17043 {
17044 can_issue_more = issue_rate - 1;
17045 (*group_count)++;
17046 end = true;
17047 for (i = 0; i < issue_rate; i++)
17048 {
17049 group_insns[i] = 0;
17050 }
17051 }
17052 n_nops--;
17053 }
cbe26ab8
DN
17054
17055 /* Scale back relative to 'issue_rate' (instead of 'issue_rate - 1'). */
f676971a 17056 can_issue_more++;
cbe26ab8 17057
c4ad648e
AM
17058 /* Is next_insn going to start a new group? */
17059 *group_end
17060 = (end
cbe26ab8
DN
17061 || (can_issue_more == 1 && !is_branch_slot_insn (next_insn))
17062 || (can_issue_more <= 2 && is_cracked_insn (next_insn))
17063 || (can_issue_more < issue_rate &&
c4ad648e 17064 insn_terminates_group_p (next_insn, previous_group)));
cbe26ab8 17065 if (*group_end && end)
c4ad648e 17066 (*group_count)--;
cbe26ab8
DN
17067
17068 if (sched_verbose > 6)
c4ad648e
AM
17069 fprintf (dump, "done force: group count = %d, can_issue_more = %d\n",
17070 *group_count, can_issue_more);
f676971a
EC
17071 return can_issue_more;
17072 }
cbe26ab8
DN
17073
17074 return can_issue_more;
17075}
17076
17077/* This function tries to synch the dispatch groups that the compiler "sees"
f676971a 17078 with the dispatch groups that the processor dispatcher is expected to
cbe26ab8
DN
17079 form in practice. It tries to achieve this synchronization by forcing the
17080 estimated processor grouping on the compiler (as opposed to the function
17081 'pad_goups' which tries to force the scheduler's grouping on the processor).
17082
17083 The function scans the insn sequence between PREV_HEAD_INSN and TAIL and
17084 examines the (estimated) dispatch groups that will be formed by the processor
17085 dispatcher. It marks these group boundaries to reflect the estimated
17086 processor grouping, overriding the grouping that the scheduler had marked.
17087 Depending on the value of the flag '-minsert-sched-nops' this function can
17088 force certain insns into separate groups or force a certain distance between
17089 them by inserting nops, for example, if there exists a "costly dependence"
17090 between the insns.
17091
17092 The function estimates the group boundaries that the processor will form as
0fa2e4df 17093 follows: It keeps track of how many vacant issue slots are available after
cbe26ab8
DN
17094 each insn. A subsequent insn will start a new group if one of the following
17095 4 cases applies:
17096 - no more vacant issue slots remain in the current dispatch group.
17097 - only the last issue slot, which is the branch slot, is vacant, but the next
17098 insn is not a branch.
17099 - only the last 2 or less issue slots, including the branch slot, are vacant,
17100 which means that a cracked insn (which occupies two issue slots) can't be
17101 issued in this group.
f676971a 17102 - less than 'issue_rate' slots are vacant, and the next insn always needs to
cbe26ab8
DN
17103 start a new group. */
17104
17105static int
17106redefine_groups (FILE *dump, int sched_verbose, rtx prev_head_insn, rtx tail)
17107{
17108 rtx insn, next_insn;
17109 int issue_rate;
17110 int can_issue_more;
17111 int slot, i;
17112 bool group_end;
17113 int group_count = 0;
17114 rtx *group_insns;
17115
17116 /* Initialize. */
17117 issue_rate = rs6000_issue_rate ();
17118 group_insns = alloca (issue_rate * sizeof (rtx));
f676971a 17119 for (i = 0; i < issue_rate; i++)
cbe26ab8
DN
17120 {
17121 group_insns[i] = 0;
17122 }
17123 can_issue_more = issue_rate;
17124 slot = 0;
17125 insn = get_next_active_insn (prev_head_insn, tail);
17126 group_end = false;
17127
17128 while (insn != NULL_RTX)
17129 {
17130 slot = (issue_rate - can_issue_more);
17131 group_insns[slot] = insn;
17132 can_issue_more =
c4ad648e 17133 rs6000_variable_issue (dump, sched_verbose, insn, can_issue_more);
cbe26ab8 17134 if (insn_terminates_group_p (insn, current_group))
c4ad648e 17135 can_issue_more = 0;
cbe26ab8
DN
17136
17137 next_insn = get_next_active_insn (insn, tail);
17138 if (next_insn == NULL_RTX)
c4ad648e 17139 return group_count + 1;
cbe26ab8 17140
c4ad648e
AM
17141 /* Is next_insn going to start a new group? */
17142 group_end
17143 = (can_issue_more == 0
17144 || (can_issue_more == 1 && !is_branch_slot_insn (next_insn))
17145 || (can_issue_more <= 2 && is_cracked_insn (next_insn))
17146 || (can_issue_more < issue_rate &&
17147 insn_terminates_group_p (next_insn, previous_group)));
cbe26ab8 17148
f676971a 17149 can_issue_more = force_new_group (sched_verbose, dump, group_insns,
c4ad648e
AM
17150 next_insn, &group_end, can_issue_more,
17151 &group_count);
cbe26ab8
DN
17152
17153 if (group_end)
c4ad648e
AM
17154 {
17155 group_count++;
17156 can_issue_more = 0;
17157 for (i = 0; i < issue_rate; i++)
17158 {
17159 group_insns[i] = 0;
17160 }
17161 }
cbe26ab8
DN
17162
17163 if (GET_MODE (next_insn) == TImode && can_issue_more)
9390387d 17164 PUT_MODE (next_insn, VOIDmode);
cbe26ab8 17165 else if (!can_issue_more && GET_MODE (next_insn) != TImode)
c4ad648e 17166 PUT_MODE (next_insn, TImode);
cbe26ab8
DN
17167
17168 insn = next_insn;
17169 if (can_issue_more == 0)
c4ad648e
AM
17170 can_issue_more = issue_rate;
17171 } /* while */
cbe26ab8
DN
17172
17173 return group_count;
17174}
17175
17176/* Scan the insn sequence between PREV_HEAD_INSN and TAIL and examine the
17177 dispatch group boundaries that the scheduler had marked. Pad with nops
17178 any dispatch groups which have vacant issue slots, in order to force the
17179 scheduler's grouping on the processor dispatcher. The function
17180 returns the number of dispatch groups found. */
17181
17182static int
17183pad_groups (FILE *dump, int sched_verbose, rtx prev_head_insn, rtx tail)
17184{
17185 rtx insn, next_insn;
17186 rtx nop;
17187 int issue_rate;
17188 int can_issue_more;
17189 int group_end;
17190 int group_count = 0;
17191
17192 /* Initialize issue_rate. */
17193 issue_rate = rs6000_issue_rate ();
17194 can_issue_more = issue_rate;
17195
17196 insn = get_next_active_insn (prev_head_insn, tail);
17197 next_insn = get_next_active_insn (insn, tail);
17198
17199 while (insn != NULL_RTX)
17200 {
17201 can_issue_more =
17202 rs6000_variable_issue (dump, sched_verbose, insn, can_issue_more);
17203
17204 group_end = (next_insn == NULL_RTX || GET_MODE (next_insn) == TImode);
17205
17206 if (next_insn == NULL_RTX)
c4ad648e 17207 break;
cbe26ab8
DN
17208
17209 if (group_end)
c4ad648e
AM
17210 {
17211 /* If the scheduler had marked group termination at this location
17212 (between insn and next_indn), and neither insn nor next_insn will
17213 force group termination, pad the group with nops to force group
17214 termination. */
17215 if (can_issue_more
17216 && (rs6000_sched_insert_nops == sched_finish_pad_groups)
17217 && !insn_terminates_group_p (insn, current_group)
17218 && !insn_terminates_group_p (next_insn, previous_group))
17219 {
9390387d 17220 if (!is_branch_slot_insn (next_insn))
c4ad648e
AM
17221 can_issue_more--;
17222
17223 while (can_issue_more)
17224 {
17225 nop = gen_nop ();
17226 emit_insn_before (nop, next_insn);
17227 can_issue_more--;
17228 }
17229 }
17230
17231 can_issue_more = issue_rate;
17232 group_count++;
17233 }
cbe26ab8
DN
17234
17235 insn = next_insn;
17236 next_insn = get_next_active_insn (insn, tail);
17237 }
17238
17239 return group_count;
17240}
17241
17242/* The following function is called at the end of scheduling BB.
17243 After reload, it inserts nops at insn group bundling. */
17244
17245static void
38f391a5 17246rs6000_sched_finish (FILE *dump, int sched_verbose)
cbe26ab8
DN
17247{
17248 int n_groups;
17249
17250 if (sched_verbose)
17251 fprintf (dump, "=== Finishing schedule.\n");
17252
ec507f2d 17253 if (reload_completed && rs6000_sched_groups)
cbe26ab8
DN
17254 {
17255 if (rs6000_sched_insert_nops == sched_finish_none)
c4ad648e 17256 return;
cbe26ab8
DN
17257
17258 if (rs6000_sched_insert_nops == sched_finish_pad_groups)
c4ad648e
AM
17259 n_groups = pad_groups (dump, sched_verbose,
17260 current_sched_info->prev_head,
17261 current_sched_info->next_tail);
cbe26ab8 17262 else
c4ad648e
AM
17263 n_groups = redefine_groups (dump, sched_verbose,
17264 current_sched_info->prev_head,
17265 current_sched_info->next_tail);
cbe26ab8
DN
17266
17267 if (sched_verbose >= 6)
17268 {
17269 fprintf (dump, "ngroups = %d\n", n_groups);
17270 print_rtl (dump, current_sched_info->prev_head);
17271 fprintf (dump, "Done finish_sched\n");
17272 }
17273 }
17274}
b6c9286a 17275\f
b6c9286a
MM
17276/* Length in units of the trampoline for entering a nested function. */
17277
17278int
863d938c 17279rs6000_trampoline_size (void)
b6c9286a
MM
17280{
17281 int ret = 0;
17282
17283 switch (DEFAULT_ABI)
17284 {
17285 default:
37409796 17286 gcc_unreachable ();
b6c9286a
MM
17287
17288 case ABI_AIX:
8f802bfb 17289 ret = (TARGET_32BIT) ? 12 : 24;
b6c9286a
MM
17290 break;
17291
4dabc42d 17292 case ABI_DARWIN:
b6c9286a 17293 case ABI_V4:
03a7e1a5 17294 ret = (TARGET_32BIT) ? 40 : 48;
b6c9286a 17295 break;
b6c9286a
MM
17296 }
17297
17298 return ret;
17299}
17300
17301/* Emit RTL insns to initialize the variable parts of a trampoline.
17302 FNADDR is an RTX for the address of the function's pure code.
17303 CXT is an RTX for the static chain value for the function. */
17304
17305void
a2369ed3 17306rs6000_initialize_trampoline (rtx addr, rtx fnaddr, rtx cxt)
b6c9286a 17307{
8bd04c56 17308 int regsize = (TARGET_32BIT) ? 4 : 8;
9613eaff 17309 rtx ctx_reg = force_reg (Pmode, cxt);
b6c9286a
MM
17310
17311 switch (DEFAULT_ABI)
17312 {
17313 default:
37409796 17314 gcc_unreachable ();
b6c9286a 17315
8bd04c56 17316/* Macros to shorten the code expansions below. */
9613eaff 17317#define MEM_DEREF(addr) gen_rtx_MEM (Pmode, memory_address (Pmode, addr))
c5c76735 17318#define MEM_PLUS(addr,offset) \
9613eaff 17319 gen_rtx_MEM (Pmode, memory_address (Pmode, plus_constant (addr, offset)))
7c59dc5d 17320
b6c9286a
MM
17321 /* Under AIX, just build the 3 word function descriptor */
17322 case ABI_AIX:
8bd04c56 17323 {
9613eaff
SH
17324 rtx fn_reg = gen_reg_rtx (Pmode);
17325 rtx toc_reg = gen_reg_rtx (Pmode);
8bd04c56 17326 emit_move_insn (fn_reg, MEM_DEREF (fnaddr));
1cb18e3c 17327 emit_move_insn (toc_reg, MEM_PLUS (fnaddr, regsize));
8bd04c56
MM
17328 emit_move_insn (MEM_DEREF (addr), fn_reg);
17329 emit_move_insn (MEM_PLUS (addr, regsize), toc_reg);
17330 emit_move_insn (MEM_PLUS (addr, 2*regsize), ctx_reg);
17331 }
b6c9286a
MM
17332 break;
17333
4dabc42d
TC
17334 /* Under V.4/eabi/darwin, __trampoline_setup does the real work. */
17335 case ABI_DARWIN:
b6c9286a 17336 case ABI_V4:
9613eaff 17337 emit_library_call (gen_rtx_SYMBOL_REF (Pmode, "__trampoline_setup"),
eaf1bcf1 17338 FALSE, VOIDmode, 4,
9613eaff 17339 addr, Pmode,
eaf1bcf1 17340 GEN_INT (rs6000_trampoline_size ()), SImode,
9613eaff
SH
17341 fnaddr, Pmode,
17342 ctx_reg, Pmode);
b6c9286a 17343 break;
b6c9286a
MM
17344 }
17345
17346 return;
17347}
7509c759
MM
17348
17349\f
91d231cb 17350/* Table of valid machine attributes. */
a4f6c312 17351
91d231cb 17352const struct attribute_spec rs6000_attribute_table[] =
7509c759 17353{
91d231cb 17354 /* { name, min_len, max_len, decl_req, type_req, fn_type_req, handler } */
8bb418a3 17355 { "altivec", 1, 1, false, true, false, rs6000_handle_altivec_attribute },
a5c76ee6
ZW
17356 { "longcall", 0, 0, false, true, true, rs6000_handle_longcall_attribute },
17357 { "shortcall", 0, 0, false, true, true, rs6000_handle_longcall_attribute },
77ccdfed
EC
17358 { "ms_struct", 0, 0, false, false, false, rs6000_handle_struct_attribute },
17359 { "gcc_struct", 0, 0, false, false, false, rs6000_handle_struct_attribute },
005c1a13
GK
17360#ifdef SUBTARGET_ATTRIBUTE_TABLE
17361 SUBTARGET_ATTRIBUTE_TABLE,
17362#endif
a5c76ee6 17363 { NULL, 0, 0, false, false, false, NULL }
91d231cb 17364};
7509c759 17365
8bb418a3
ZL
17366/* Handle the "altivec" attribute. The attribute may have
17367 arguments as follows:
f676971a 17368
8bb418a3
ZL
17369 __attribute__((altivec(vector__)))
17370 __attribute__((altivec(pixel__))) (always followed by 'unsigned short')
17371 __attribute__((altivec(bool__))) (always followed by 'unsigned')
17372
17373 and may appear more than once (e.g., 'vector bool char') in a
17374 given declaration. */
17375
17376static tree
f90ac3f0
UP
17377rs6000_handle_altivec_attribute (tree *node,
17378 tree name ATTRIBUTE_UNUSED,
17379 tree args,
8bb418a3
ZL
17380 int flags ATTRIBUTE_UNUSED,
17381 bool *no_add_attrs)
17382{
17383 tree type = *node, result = NULL_TREE;
17384 enum machine_mode mode;
17385 int unsigned_p;
17386 char altivec_type
17387 = ((args && TREE_CODE (args) == TREE_LIST && TREE_VALUE (args)
17388 && TREE_CODE (TREE_VALUE (args)) == IDENTIFIER_NODE)
17389 ? *IDENTIFIER_POINTER (TREE_VALUE (args))
f676971a 17390 : '?');
8bb418a3
ZL
17391
17392 while (POINTER_TYPE_P (type)
17393 || TREE_CODE (type) == FUNCTION_TYPE
17394 || TREE_CODE (type) == METHOD_TYPE
17395 || TREE_CODE (type) == ARRAY_TYPE)
17396 type = TREE_TYPE (type);
17397
17398 mode = TYPE_MODE (type);
17399
f90ac3f0
UP
17400 /* Check for invalid AltiVec type qualifiers. */
17401 if (type == long_unsigned_type_node || type == long_integer_type_node)
17402 {
17403 if (TARGET_64BIT)
17404 error ("use of %<long%> in AltiVec types is invalid for 64-bit code");
17405 else if (rs6000_warn_altivec_long)
d4ee4d25 17406 warning (0, "use of %<long%> in AltiVec types is deprecated; use %<int%>");
f90ac3f0
UP
17407 }
17408 else if (type == long_long_unsigned_type_node
17409 || type == long_long_integer_type_node)
17410 error ("use of %<long long%> in AltiVec types is invalid");
17411 else if (type == double_type_node)
17412 error ("use of %<double%> in AltiVec types is invalid");
17413 else if (type == long_double_type_node)
17414 error ("use of %<long double%> in AltiVec types is invalid");
17415 else if (type == boolean_type_node)
17416 error ("use of boolean types in AltiVec types is invalid");
17417 else if (TREE_CODE (type) == COMPLEX_TYPE)
17418 error ("use of %<complex%> in AltiVec types is invalid");
00b79d54
BE
17419 else if (DECIMAL_FLOAT_MODE_P (mode))
17420 error ("use of decimal floating point types in AltiVec types is invalid");
8bb418a3
ZL
17421
17422 switch (altivec_type)
17423 {
17424 case 'v':
8df83eae 17425 unsigned_p = TYPE_UNSIGNED (type);
8bb418a3
ZL
17426 switch (mode)
17427 {
c4ad648e
AM
17428 case SImode:
17429 result = (unsigned_p ? unsigned_V4SI_type_node : V4SI_type_node);
17430 break;
17431 case HImode:
17432 result = (unsigned_p ? unsigned_V8HI_type_node : V8HI_type_node);
17433 break;
17434 case QImode:
17435 result = (unsigned_p ? unsigned_V16QI_type_node : V16QI_type_node);
17436 break;
17437 case SFmode: result = V4SF_type_node; break;
17438 /* If the user says 'vector int bool', we may be handed the 'bool'
17439 attribute _before_ the 'vector' attribute, and so select the
17440 proper type in the 'b' case below. */
17441 case V4SImode: case V8HImode: case V16QImode: case V4SFmode:
17442 result = type;
17443 default: break;
8bb418a3
ZL
17444 }
17445 break;
17446 case 'b':
17447 switch (mode)
17448 {
c4ad648e
AM
17449 case SImode: case V4SImode: result = bool_V4SI_type_node; break;
17450 case HImode: case V8HImode: result = bool_V8HI_type_node; break;
17451 case QImode: case V16QImode: result = bool_V16QI_type_node;
17452 default: break;
8bb418a3
ZL
17453 }
17454 break;
17455 case 'p':
17456 switch (mode)
17457 {
c4ad648e
AM
17458 case V8HImode: result = pixel_V8HI_type_node;
17459 default: break;
8bb418a3
ZL
17460 }
17461 default: break;
17462 }
17463
7958a2a6
FJ
17464 if (result && result != type && TYPE_READONLY (type))
17465 result = build_qualified_type (result, TYPE_QUAL_CONST);
17466
8bb418a3
ZL
17467 *no_add_attrs = true; /* No need to hang on to the attribute. */
17468
f90ac3f0 17469 if (result)
8bb418a3
ZL
17470 *node = reconstruct_complex_type (*node, result);
17471
17472 return NULL_TREE;
17473}
17474
f18eca82
ZL
17475/* AltiVec defines four built-in scalar types that serve as vector
17476 elements; we must teach the compiler how to mangle them. */
17477
17478static const char *
17479rs6000_mangle_fundamental_type (tree type)
17480{
17481 if (type == bool_char_type_node) return "U6__boolc";
17482 if (type == bool_short_type_node) return "U6__bools";
17483 if (type == pixel_type_node) return "u7__pixel";
17484 if (type == bool_int_type_node) return "U6__booli";
17485
337bde91
DE
17486 /* Mangle IBM extended float long double as `g' (__float128) on
17487 powerpc*-linux where long-double-64 previously was the default. */
17488 if (TYPE_MAIN_VARIANT (type) == long_double_type_node
17489 && TARGET_ELF
17490 && TARGET_LONG_DOUBLE_128
17491 && !TARGET_IEEEQUAD)
17492 return "g";
17493
f18eca82
ZL
17494 /* For all other types, use normal C++ mangling. */
17495 return NULL;
17496}
17497
a5c76ee6
ZW
17498/* Handle a "longcall" or "shortcall" attribute; arguments as in
17499 struct attribute_spec.handler. */
a4f6c312 17500
91d231cb 17501static tree
f676971a
EC
17502rs6000_handle_longcall_attribute (tree *node, tree name,
17503 tree args ATTRIBUTE_UNUSED,
17504 int flags ATTRIBUTE_UNUSED,
a2369ed3 17505 bool *no_add_attrs)
91d231cb
JM
17506{
17507 if (TREE_CODE (*node) != FUNCTION_TYPE
17508 && TREE_CODE (*node) != FIELD_DECL
17509 && TREE_CODE (*node) != TYPE_DECL)
17510 {
5c498b10 17511 warning (OPT_Wattributes, "%qs attribute only applies to functions",
91d231cb
JM
17512 IDENTIFIER_POINTER (name));
17513 *no_add_attrs = true;
17514 }
6a4cee5f 17515
91d231cb 17516 return NULL_TREE;
7509c759
MM
17517}
17518
a5c76ee6
ZW
17519/* Set longcall attributes on all functions declared when
17520 rs6000_default_long_calls is true. */
17521static void
a2369ed3 17522rs6000_set_default_type_attributes (tree type)
a5c76ee6
ZW
17523{
17524 if (rs6000_default_long_calls
17525 && (TREE_CODE (type) == FUNCTION_TYPE
17526 || TREE_CODE (type) == METHOD_TYPE))
17527 TYPE_ATTRIBUTES (type) = tree_cons (get_identifier ("longcall"),
17528 NULL_TREE,
17529 TYPE_ATTRIBUTES (type));
17530}
17531
3cb999d8
DE
17532/* Return a reference suitable for calling a function with the
17533 longcall attribute. */
a4f6c312 17534
9390387d 17535rtx
a2369ed3 17536rs6000_longcall_ref (rtx call_ref)
6a4cee5f 17537{
d330fd93 17538 const char *call_name;
6a4cee5f
MM
17539 tree node;
17540
17541 if (GET_CODE (call_ref) != SYMBOL_REF)
17542 return call_ref;
17543
17544 /* System V adds '.' to the internal name, so skip them. */
17545 call_name = XSTR (call_ref, 0);
17546 if (*call_name == '.')
17547 {
17548 while (*call_name == '.')
17549 call_name++;
17550
17551 node = get_identifier (call_name);
39403d82 17552 call_ref = gen_rtx_SYMBOL_REF (VOIDmode, IDENTIFIER_POINTER (node));
6a4cee5f
MM
17553 }
17554
17555 return force_reg (Pmode, call_ref);
17556}
7509c759 17557\f
77ccdfed
EC
17558#ifndef TARGET_USE_MS_BITFIELD_LAYOUT
17559#define TARGET_USE_MS_BITFIELD_LAYOUT 0
17560#endif
17561
17562/* Handle a "ms_struct" or "gcc_struct" attribute; arguments as in
17563 struct attribute_spec.handler. */
17564static tree
17565rs6000_handle_struct_attribute (tree *node, tree name,
17566 tree args ATTRIBUTE_UNUSED,
17567 int flags ATTRIBUTE_UNUSED, bool *no_add_attrs)
17568{
17569 tree *type = NULL;
17570 if (DECL_P (*node))
17571 {
17572 if (TREE_CODE (*node) == TYPE_DECL)
17573 type = &TREE_TYPE (*node);
17574 }
17575 else
17576 type = node;
17577
17578 if (!(type && (TREE_CODE (*type) == RECORD_TYPE
17579 || TREE_CODE (*type) == UNION_TYPE)))
17580 {
17581 warning (OPT_Wattributes, "%qs attribute ignored", IDENTIFIER_POINTER (name));
17582 *no_add_attrs = true;
17583 }
17584
17585 else if ((is_attribute_p ("ms_struct", name)
17586 && lookup_attribute ("gcc_struct", TYPE_ATTRIBUTES (*type)))
17587 || ((is_attribute_p ("gcc_struct", name)
17588 && lookup_attribute ("ms_struct", TYPE_ATTRIBUTES (*type)))))
17589 {
17590 warning (OPT_Wattributes, "%qs incompatible attribute ignored",
17591 IDENTIFIER_POINTER (name));
17592 *no_add_attrs = true;
17593 }
17594
17595 return NULL_TREE;
17596}
17597
17598static bool
17599rs6000_ms_bitfield_layout_p (tree record_type)
17600{
17601 return (TARGET_USE_MS_BITFIELD_LAYOUT &&
17602 !lookup_attribute ("gcc_struct", TYPE_ATTRIBUTES (record_type)))
17603 || lookup_attribute ("ms_struct", TYPE_ATTRIBUTES (record_type));
17604}
17605\f
b64a1b53
RH
17606#ifdef USING_ELFOS_H
17607
d6b5193b 17608/* A get_unnamed_section callback, used for switching to toc_section. */
7509c759 17609
d6b5193b
RS
17610static void
17611rs6000_elf_output_toc_section_asm_op (const void *data ATTRIBUTE_UNUSED)
17612{
17613 if (DEFAULT_ABI == ABI_AIX
17614 && TARGET_MINIMAL_TOC
17615 && !TARGET_RELOCATABLE)
17616 {
17617 if (!toc_initialized)
17618 {
17619 toc_initialized = 1;
17620 fprintf (asm_out_file, "%s\n", TOC_SECTION_ASM_OP);
17621 (*targetm.asm_out.internal_label) (asm_out_file, "LCTOC", 0);
17622 fprintf (asm_out_file, "\t.tc ");
17623 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (asm_out_file, "LCTOC1[TC],");
17624 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (asm_out_file, "LCTOC1");
17625 fprintf (asm_out_file, "\n");
17626
17627 fprintf (asm_out_file, "%s\n", MINIMAL_TOC_SECTION_ASM_OP);
17628 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (asm_out_file, "LCTOC1");
17629 fprintf (asm_out_file, " = .+32768\n");
17630 }
17631 else
17632 fprintf (asm_out_file, "%s\n", MINIMAL_TOC_SECTION_ASM_OP);
17633 }
17634 else if (DEFAULT_ABI == ABI_AIX && !TARGET_RELOCATABLE)
17635 fprintf (asm_out_file, "%s\n", TOC_SECTION_ASM_OP);
17636 else
17637 {
17638 fprintf (asm_out_file, "%s\n", MINIMAL_TOC_SECTION_ASM_OP);
17639 if (!toc_initialized)
17640 {
17641 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (asm_out_file, "LCTOC1");
17642 fprintf (asm_out_file, " = .+32768\n");
17643 toc_initialized = 1;
17644 }
17645 }
17646}
17647
17648/* Implement TARGET_ASM_INIT_SECTIONS. */
7509c759 17649
b64a1b53 17650static void
d6b5193b
RS
17651rs6000_elf_asm_init_sections (void)
17652{
17653 toc_section
17654 = get_unnamed_section (0, rs6000_elf_output_toc_section_asm_op, NULL);
17655
17656 sdata2_section
17657 = get_unnamed_section (SECTION_WRITE, output_section_asm_op,
17658 SDATA2_SECTION_ASM_OP);
17659}
17660
17661/* Implement TARGET_SELECT_RTX_SECTION. */
17662
17663static section *
f676971a 17664rs6000_elf_select_rtx_section (enum machine_mode mode, rtx x,
a2369ed3 17665 unsigned HOST_WIDE_INT align)
7509c759 17666{
a9098fd0 17667 if (ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (x, mode))
d6b5193b 17668 return toc_section;
7509c759 17669 else
d6b5193b 17670 return default_elf_select_rtx_section (mode, x, align);
7509c759
MM
17671}
17672
d6b5193b 17673/* Implement TARGET_ASM_SELECT_SECTION for ELF targets. */
7509c759 17674
d6b5193b 17675static section *
f676971a 17676rs6000_elf_select_section (tree decl, int reloc,
a2369ed3 17677 unsigned HOST_WIDE_INT align)
7509c759 17678{
f1384257
AM
17679 /* Pretend that we're always building for a shared library when
17680 ABI_AIX, because otherwise we end up with dynamic relocations
17681 in read-only sections. This happens for function pointers,
17682 references to vtables in typeinfo, and probably other cases. */
d6b5193b
RS
17683 return default_elf_select_section_1 (decl, reloc, align,
17684 flag_pic || DEFAULT_ABI == ABI_AIX);
63019373
GK
17685}
17686
17687/* A C statement to build up a unique section name, expressed as a
17688 STRING_CST node, and assign it to DECL_SECTION_NAME (decl).
17689 RELOC indicates whether the initial value of EXP requires
17690 link-time relocations. If you do not define this macro, GCC will use
17691 the symbol name prefixed by `.' as the section name. Note - this
f5143c46 17692 macro can now be called for uninitialized data items as well as
4912a07c 17693 initialized data and functions. */
63019373 17694
ae46c4e0 17695static void
a2369ed3 17696rs6000_elf_unique_section (tree decl, int reloc)
63019373 17697{
f1384257
AM
17698 /* As above, pretend that we're always building for a shared library
17699 when ABI_AIX, to avoid dynamic relocations in read-only sections. */
0e5dbd9b
DE
17700 default_unique_section_1 (decl, reloc,
17701 flag_pic || DEFAULT_ABI == ABI_AIX);
7509c759 17702}
d9407988 17703\f
d1908feb
JJ
17704/* For a SYMBOL_REF, set generic flags and then perform some
17705 target-specific processing.
17706
d1908feb
JJ
17707 When the AIX ABI is requested on a non-AIX system, replace the
17708 function name with the real name (with a leading .) rather than the
17709 function descriptor name. This saves a lot of overriding code to
17710 read the prefixes. */
d9407988 17711
fb49053f 17712static void
a2369ed3 17713rs6000_elf_encode_section_info (tree decl, rtx rtl, int first)
d9407988 17714{
d1908feb 17715 default_encode_section_info (decl, rtl, first);
b2003250 17716
d1908feb
JJ
17717 if (first
17718 && TREE_CODE (decl) == FUNCTION_DECL
17719 && !TARGET_AIX
17720 && DEFAULT_ABI == ABI_AIX)
d9407988 17721 {
c6a2438a 17722 rtx sym_ref = XEXP (rtl, 0);
d1908feb
JJ
17723 size_t len = strlen (XSTR (sym_ref, 0));
17724 char *str = alloca (len + 2);
17725 str[0] = '.';
17726 memcpy (str + 1, XSTR (sym_ref, 0), len + 1);
17727 XSTR (sym_ref, 0) = ggc_alloc_string (str, len + 1);
d9407988 17728 }
d9407988
MM
17729}
17730
c1b7d95a 17731bool
a2369ed3 17732rs6000_elf_in_small_data_p (tree decl)
0e5dbd9b
DE
17733{
17734 if (rs6000_sdata == SDATA_NONE)
17735 return false;
17736
7482ad25
AF
17737 /* We want to merge strings, so we never consider them small data. */
17738 if (TREE_CODE (decl) == STRING_CST)
17739 return false;
17740
17741 /* Functions are never in the small data area. */
17742 if (TREE_CODE (decl) == FUNCTION_DECL)
17743 return false;
17744
0e5dbd9b
DE
17745 if (TREE_CODE (decl) == VAR_DECL && DECL_SECTION_NAME (decl))
17746 {
17747 const char *section = TREE_STRING_POINTER (DECL_SECTION_NAME (decl));
17748 if (strcmp (section, ".sdata") == 0
17749 || strcmp (section, ".sdata2") == 0
20bfcd69
GK
17750 || strcmp (section, ".sbss") == 0
17751 || strcmp (section, ".sbss2") == 0
17752 || strcmp (section, ".PPC.EMB.sdata0") == 0
17753 || strcmp (section, ".PPC.EMB.sbss0") == 0)
0e5dbd9b
DE
17754 return true;
17755 }
17756 else
17757 {
17758 HOST_WIDE_INT size = int_size_in_bytes (TREE_TYPE (decl));
17759
17760 if (size > 0
307b599c 17761 && (unsigned HOST_WIDE_INT) size <= g_switch_value
20bfcd69
GK
17762 /* If it's not public, and we're not going to reference it there,
17763 there's no need to put it in the small data section. */
0e5dbd9b
DE
17764 && (rs6000_sdata != SDATA_DATA || TREE_PUBLIC (decl)))
17765 return true;
17766 }
17767
17768 return false;
17769}
17770
b91da81f 17771#endif /* USING_ELFOS_H */
aacd3885
RS
17772\f
17773/* Implement TARGET_USE_BLOCKS_FOR_CONSTANT_P. */
000034eb 17774
aacd3885
RS
17775static bool
17776rs6000_use_blocks_for_constant_p (enum machine_mode mode, rtx x)
17777{
17778 return !ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (x, mode);
17779}
a6c2a102 17780\f
000034eb 17781/* Return a REG that occurs in ADDR with coefficient 1.
02441cd6
JL
17782 ADDR can be effectively incremented by incrementing REG.
17783
17784 r0 is special and we must not select it as an address
17785 register by this routine since our caller will try to
17786 increment the returned register via an "la" instruction. */
000034eb 17787
9390387d 17788rtx
a2369ed3 17789find_addr_reg (rtx addr)
000034eb
DE
17790{
17791 while (GET_CODE (addr) == PLUS)
17792 {
02441cd6
JL
17793 if (GET_CODE (XEXP (addr, 0)) == REG
17794 && REGNO (XEXP (addr, 0)) != 0)
000034eb 17795 addr = XEXP (addr, 0);
02441cd6
JL
17796 else if (GET_CODE (XEXP (addr, 1)) == REG
17797 && REGNO (XEXP (addr, 1)) != 0)
000034eb
DE
17798 addr = XEXP (addr, 1);
17799 else if (CONSTANT_P (XEXP (addr, 0)))
17800 addr = XEXP (addr, 1);
17801 else if (CONSTANT_P (XEXP (addr, 1)))
17802 addr = XEXP (addr, 0);
17803 else
37409796 17804 gcc_unreachable ();
000034eb 17805 }
37409796
NS
17806 gcc_assert (GET_CODE (addr) == REG && REGNO (addr) != 0);
17807 return addr;
000034eb
DE
17808}
17809
a6c2a102 17810void
a2369ed3 17811rs6000_fatal_bad_address (rtx op)
a6c2a102
DE
17812{
17813 fatal_insn ("bad address", op);
17814}
c8023011 17815
ee890fe2
SS
17816#if TARGET_MACHO
17817
efdba735 17818static tree branch_island_list = 0;
ee890fe2 17819
efdba735
SH
17820/* Remember to generate a branch island for far calls to the given
17821 function. */
ee890fe2 17822
f676971a 17823static void
c4ad648e
AM
17824add_compiler_branch_island (tree label_name, tree function_name,
17825 int line_number)
ee890fe2 17826{
efdba735 17827 tree branch_island = build_tree_list (function_name, label_name);
7d60be94 17828 TREE_TYPE (branch_island) = build_int_cst (NULL_TREE, line_number);
efdba735
SH
17829 TREE_CHAIN (branch_island) = branch_island_list;
17830 branch_island_list = branch_island;
ee890fe2
SS
17831}
17832
efdba735
SH
17833#define BRANCH_ISLAND_LABEL_NAME(BRANCH_ISLAND) TREE_VALUE (BRANCH_ISLAND)
17834#define BRANCH_ISLAND_FUNCTION_NAME(BRANCH_ISLAND) TREE_PURPOSE (BRANCH_ISLAND)
17835#define BRANCH_ISLAND_LINE_NUMBER(BRANCH_ISLAND) \
17836 TREE_INT_CST_LOW (TREE_TYPE (BRANCH_ISLAND))
ee890fe2 17837
efdba735
SH
17838/* Generate far-jump branch islands for everything on the
17839 branch_island_list. Invoked immediately after the last instruction
17840 of the epilogue has been emitted; the branch-islands must be
17841 appended to, and contiguous with, the function body. Mach-O stubs
17842 are generated in machopic_output_stub(). */
ee890fe2 17843
efdba735
SH
17844static void
17845macho_branch_islands (void)
17846{
17847 char tmp_buf[512];
17848 tree branch_island;
17849
17850 for (branch_island = branch_island_list;
17851 branch_island;
17852 branch_island = TREE_CHAIN (branch_island))
17853 {
17854 const char *label =
17855 IDENTIFIER_POINTER (BRANCH_ISLAND_LABEL_NAME (branch_island));
17856 const char *name =
11abc112 17857 IDENTIFIER_POINTER (BRANCH_ISLAND_FUNCTION_NAME (branch_island));
efdba735
SH
17858 char name_buf[512];
17859 /* Cheap copy of the details from the Darwin ASM_OUTPUT_LABELREF(). */
17860 if (name[0] == '*' || name[0] == '&')
17861 strcpy (name_buf, name+1);
17862 else
17863 {
17864 name_buf[0] = '_';
17865 strcpy (name_buf+1, name);
17866 }
17867 strcpy (tmp_buf, "\n");
17868 strcat (tmp_buf, label);
ee890fe2 17869#if defined (DBX_DEBUGGING_INFO) || defined (XCOFF_DEBUGGING_INFO)
efdba735 17870 if (write_symbols == DBX_DEBUG || write_symbols == XCOFF_DEBUG)
93a27b7b 17871 dbxout_stabd (N_SLINE, BRANCH_ISLAND_LINE_NUMBER (branch_island));
ee890fe2 17872#endif /* DBX_DEBUGGING_INFO || XCOFF_DEBUGGING_INFO */
efdba735
SH
17873 if (flag_pic)
17874 {
17875 strcat (tmp_buf, ":\n\tmflr r0\n\tbcl 20,31,");
17876 strcat (tmp_buf, label);
17877 strcat (tmp_buf, "_pic\n");
17878 strcat (tmp_buf, label);
17879 strcat (tmp_buf, "_pic:\n\tmflr r11\n");
f676971a 17880
efdba735
SH
17881 strcat (tmp_buf, "\taddis r11,r11,ha16(");
17882 strcat (tmp_buf, name_buf);
17883 strcat (tmp_buf, " - ");
17884 strcat (tmp_buf, label);
17885 strcat (tmp_buf, "_pic)\n");
f676971a 17886
efdba735 17887 strcat (tmp_buf, "\tmtlr r0\n");
f676971a 17888
efdba735
SH
17889 strcat (tmp_buf, "\taddi r12,r11,lo16(");
17890 strcat (tmp_buf, name_buf);
17891 strcat (tmp_buf, " - ");
17892 strcat (tmp_buf, label);
17893 strcat (tmp_buf, "_pic)\n");
f676971a 17894
efdba735
SH
17895 strcat (tmp_buf, "\tmtctr r12\n\tbctr\n");
17896 }
17897 else
17898 {
17899 strcat (tmp_buf, ":\nlis r12,hi16(");
17900 strcat (tmp_buf, name_buf);
17901 strcat (tmp_buf, ")\n\tori r12,r12,lo16(");
17902 strcat (tmp_buf, name_buf);
17903 strcat (tmp_buf, ")\n\tmtctr r12\n\tbctr");
17904 }
17905 output_asm_insn (tmp_buf, 0);
ee890fe2 17906#if defined (DBX_DEBUGGING_INFO) || defined (XCOFF_DEBUGGING_INFO)
efdba735 17907 if (write_symbols == DBX_DEBUG || write_symbols == XCOFF_DEBUG)
93a27b7b 17908 dbxout_stabd (N_SLINE, BRANCH_ISLAND_LINE_NUMBER (branch_island));
ee890fe2 17909#endif /* DBX_DEBUGGING_INFO || XCOFF_DEBUGGING_INFO */
efdba735 17910 }
ee890fe2 17911
efdba735 17912 branch_island_list = 0;
ee890fe2
SS
17913}
17914
17915/* NO_PREVIOUS_DEF checks in the link list whether the function name is
17916 already there or not. */
17917
efdba735 17918static int
a2369ed3 17919no_previous_def (tree function_name)
ee890fe2 17920{
efdba735
SH
17921 tree branch_island;
17922 for (branch_island = branch_island_list;
17923 branch_island;
17924 branch_island = TREE_CHAIN (branch_island))
17925 if (function_name == BRANCH_ISLAND_FUNCTION_NAME (branch_island))
ee890fe2
SS
17926 return 0;
17927 return 1;
17928}
17929
17930/* GET_PREV_LABEL gets the label name from the previous definition of
17931 the function. */
17932
efdba735 17933static tree
a2369ed3 17934get_prev_label (tree function_name)
ee890fe2 17935{
efdba735
SH
17936 tree branch_island;
17937 for (branch_island = branch_island_list;
17938 branch_island;
17939 branch_island = TREE_CHAIN (branch_island))
17940 if (function_name == BRANCH_ISLAND_FUNCTION_NAME (branch_island))
17941 return BRANCH_ISLAND_LABEL_NAME (branch_island);
ee890fe2
SS
17942 return 0;
17943}
17944
17945/* INSN is either a function call or a millicode call. It may have an
f676971a 17946 unconditional jump in its delay slot.
ee890fe2
SS
17947
17948 CALL_DEST is the routine we are calling. */
17949
17950char *
c4ad648e
AM
17951output_call (rtx insn, rtx *operands, int dest_operand_number,
17952 int cookie_operand_number)
ee890fe2
SS
17953{
17954 static char buf[256];
efdba735
SH
17955 if (GET_CODE (operands[dest_operand_number]) == SYMBOL_REF
17956 && (INTVAL (operands[cookie_operand_number]) & CALL_LONG))
ee890fe2
SS
17957 {
17958 tree labelname;
efdba735 17959 tree funname = get_identifier (XSTR (operands[dest_operand_number], 0));
f676971a 17960
ee890fe2
SS
17961 if (no_previous_def (funname))
17962 {
308c142a 17963 int line_number = 0;
ee890fe2
SS
17964 rtx label_rtx = gen_label_rtx ();
17965 char *label_buf, temp_buf[256];
17966 ASM_GENERATE_INTERNAL_LABEL (temp_buf, "L",
17967 CODE_LABEL_NUMBER (label_rtx));
17968 label_buf = temp_buf[0] == '*' ? temp_buf + 1 : temp_buf;
17969 labelname = get_identifier (label_buf);
17970 for (; insn && GET_CODE (insn) != NOTE; insn = PREV_INSN (insn));
17971 if (insn)
17972 line_number = NOTE_LINE_NUMBER (insn);
efdba735 17973 add_compiler_branch_island (labelname, funname, line_number);
ee890fe2
SS
17974 }
17975 else
17976 labelname = get_prev_label (funname);
17977
efdba735
SH
17978 /* "jbsr foo, L42" is Mach-O for "Link as 'bl foo' if a 'bl'
17979 instruction will reach 'foo', otherwise link as 'bl L42'".
17980 "L42" should be a 'branch island', that will do a far jump to
17981 'foo'. Branch islands are generated in
17982 macho_branch_islands(). */
ee890fe2 17983 sprintf (buf, "jbsr %%z%d,%.246s",
efdba735 17984 dest_operand_number, IDENTIFIER_POINTER (labelname));
ee890fe2
SS
17985 }
17986 else
efdba735
SH
17987 sprintf (buf, "bl %%z%d", dest_operand_number);
17988 return buf;
ee890fe2
SS
17989}
17990
ee890fe2
SS
17991/* Generate PIC and indirect symbol stubs. */
17992
17993void
a2369ed3 17994machopic_output_stub (FILE *file, const char *symb, const char *stub)
ee890fe2
SS
17995{
17996 unsigned int length;
a4f6c312
SS
17997 char *symbol_name, *lazy_ptr_name;
17998 char *local_label_0;
ee890fe2
SS
17999 static int label = 0;
18000
df56a27f 18001 /* Lose our funky encoding stuff so it doesn't contaminate the stub. */
772c5265 18002 symb = (*targetm.strip_name_encoding) (symb);
df56a27f 18003
ee890fe2 18004
ee890fe2
SS
18005 length = strlen (symb);
18006 symbol_name = alloca (length + 32);
18007 GEN_SYMBOL_NAME_FOR_SYMBOL (symbol_name, symb, length);
18008
18009 lazy_ptr_name = alloca (length + 32);
18010 GEN_LAZY_PTR_NAME_FOR_SYMBOL (lazy_ptr_name, symb, length);
18011
ee890fe2 18012 if (flag_pic == 2)
56c779bc 18013 switch_to_section (darwin_sections[machopic_picsymbol_stub1_section]);
ee890fe2 18014 else
56c779bc 18015 switch_to_section (darwin_sections[machopic_symbol_stub1_section]);
ee890fe2
SS
18016
18017 if (flag_pic == 2)
18018 {
d974312d
DJ
18019 fprintf (file, "\t.align 5\n");
18020
18021 fprintf (file, "%s:\n", stub);
18022 fprintf (file, "\t.indirect_symbol %s\n", symbol_name);
18023
876455fa 18024 label++;
89da1f32 18025 local_label_0 = alloca (sizeof ("\"L00000000000$spb\""));
876455fa 18026 sprintf (local_label_0, "\"L%011d$spb\"", label);
f676971a 18027
ee890fe2
SS
18028 fprintf (file, "\tmflr r0\n");
18029 fprintf (file, "\tbcl 20,31,%s\n", local_label_0);
18030 fprintf (file, "%s:\n\tmflr r11\n", local_label_0);
18031 fprintf (file, "\taddis r11,r11,ha16(%s-%s)\n",
18032 lazy_ptr_name, local_label_0);
18033 fprintf (file, "\tmtlr r0\n");
3d0e2d58
SS
18034 fprintf (file, "\t%s r12,lo16(%s-%s)(r11)\n",
18035 (TARGET_64BIT ? "ldu" : "lwzu"),
ee890fe2
SS
18036 lazy_ptr_name, local_label_0);
18037 fprintf (file, "\tmtctr r12\n");
ee890fe2
SS
18038 fprintf (file, "\tbctr\n");
18039 }
18040 else
d974312d
DJ
18041 {
18042 fprintf (file, "\t.align 4\n");
18043
18044 fprintf (file, "%s:\n", stub);
18045 fprintf (file, "\t.indirect_symbol %s\n", symbol_name);
18046
18047 fprintf (file, "\tlis r11,ha16(%s)\n", lazy_ptr_name);
d9e4e4f5
SS
18048 fprintf (file, "\t%s r12,lo16(%s)(r11)\n",
18049 (TARGET_64BIT ? "ldu" : "lwzu"),
18050 lazy_ptr_name);
d974312d
DJ
18051 fprintf (file, "\tmtctr r12\n");
18052 fprintf (file, "\tbctr\n");
18053 }
f676971a 18054
56c779bc 18055 switch_to_section (darwin_sections[machopic_lazy_symbol_ptr_section]);
ee890fe2
SS
18056 fprintf (file, "%s:\n", lazy_ptr_name);
18057 fprintf (file, "\t.indirect_symbol %s\n", symbol_name);
49bd1d27
SS
18058 fprintf (file, "%sdyld_stub_binding_helper\n",
18059 (TARGET_64BIT ? DOUBLE_INT_ASM_OP : "\t.long\t"));
ee890fe2
SS
18060}
18061
18062/* Legitimize PIC addresses. If the address is already
18063 position-independent, we return ORIG. Newly generated
18064 position-independent addresses go into a reg. This is REG if non
18065 zero, otherwise we allocate register(s) as necessary. */
18066
9390387d 18067#define SMALL_INT(X) ((unsigned) (INTVAL (X) + 0x8000) < 0x10000)
ee890fe2
SS
18068
18069rtx
f676971a 18070rs6000_machopic_legitimize_pic_address (rtx orig, enum machine_mode mode,
a2369ed3 18071 rtx reg)
ee890fe2
SS
18072{
18073 rtx base, offset;
18074
18075 if (reg == NULL && ! reload_in_progress && ! reload_completed)
18076 reg = gen_reg_rtx (Pmode);
18077
18078 if (GET_CODE (orig) == CONST)
18079 {
37409796
NS
18080 rtx reg_temp;
18081
ee890fe2
SS
18082 if (GET_CODE (XEXP (orig, 0)) == PLUS
18083 && XEXP (XEXP (orig, 0), 0) == pic_offset_table_rtx)
18084 return orig;
18085
37409796 18086 gcc_assert (GET_CODE (XEXP (orig, 0)) == PLUS);
bb8df8a6 18087
37409796
NS
18088 /* Use a different reg for the intermediate value, as
18089 it will be marked UNCHANGING. */
18090 reg_temp = no_new_pseudos ? reg : gen_reg_rtx (Pmode);
18091 base = rs6000_machopic_legitimize_pic_address (XEXP (XEXP (orig, 0), 0),
18092 Pmode, reg_temp);
18093 offset =
18094 rs6000_machopic_legitimize_pic_address (XEXP (XEXP (orig, 0), 1),
18095 Pmode, reg);
bb8df8a6 18096
ee890fe2
SS
18097 if (GET_CODE (offset) == CONST_INT)
18098 {
18099 if (SMALL_INT (offset))
ed8908e7 18100 return plus_constant (base, INTVAL (offset));
ee890fe2
SS
18101 else if (! reload_in_progress && ! reload_completed)
18102 offset = force_reg (Pmode, offset);
18103 else
c859cda6
DJ
18104 {
18105 rtx mem = force_const_mem (Pmode, orig);
18106 return machopic_legitimize_pic_address (mem, Pmode, reg);
18107 }
ee890fe2 18108 }
f1c25d3b 18109 return gen_rtx_PLUS (Pmode, base, offset);
ee890fe2
SS
18110 }
18111
18112 /* Fall back on generic machopic code. */
18113 return machopic_legitimize_pic_address (orig, mode, reg);
18114}
18115
c4e18b1c
GK
18116/* Output a .machine directive for the Darwin assembler, and call
18117 the generic start_file routine. */
18118
18119static void
18120rs6000_darwin_file_start (void)
18121{
94ff898d 18122 static const struct
c4e18b1c
GK
18123 {
18124 const char *arg;
18125 const char *name;
18126 int if_set;
18127 } mapping[] = {
55dbfb48 18128 { "ppc64", "ppc64", MASK_64BIT },
c4e18b1c
GK
18129 { "970", "ppc970", MASK_PPC_GPOPT | MASK_MFCRF | MASK_POWERPC64 },
18130 { "power4", "ppc970", 0 },
18131 { "G5", "ppc970", 0 },
18132 { "7450", "ppc7450", 0 },
18133 { "7400", "ppc7400", MASK_ALTIVEC },
18134 { "G4", "ppc7400", 0 },
18135 { "750", "ppc750", 0 },
18136 { "740", "ppc750", 0 },
18137 { "G3", "ppc750", 0 },
18138 { "604e", "ppc604e", 0 },
18139 { "604", "ppc604", 0 },
18140 { "603e", "ppc603", 0 },
18141 { "603", "ppc603", 0 },
18142 { "601", "ppc601", 0 },
18143 { NULL, "ppc", 0 } };
18144 const char *cpu_id = "";
18145 size_t i;
94ff898d 18146
9390387d 18147 rs6000_file_start ();
192d0f89 18148 darwin_file_start ();
c4e18b1c
GK
18149
18150 /* Determine the argument to -mcpu=. Default to G3 if not specified. */
18151 for (i = 0; i < ARRAY_SIZE (rs6000_select); i++)
18152 if (rs6000_select[i].set_arch_p && rs6000_select[i].string
18153 && rs6000_select[i].string[0] != '\0')
18154 cpu_id = rs6000_select[i].string;
18155
18156 /* Look through the mapping array. Pick the first name that either
18157 matches the argument, has a bit set in IF_SET that is also set
18158 in the target flags, or has a NULL name. */
18159
18160 i = 0;
18161 while (mapping[i].arg != NULL
18162 && strcmp (mapping[i].arg, cpu_id) != 0
18163 && (mapping[i].if_set & target_flags) == 0)
18164 i++;
18165
18166 fprintf (asm_out_file, "\t.machine %s\n", mapping[i].name);
18167}
18168
ee890fe2 18169#endif /* TARGET_MACHO */
7c262518
RH
18170
18171#if TARGET_ELF
18172static unsigned int
a2369ed3 18173rs6000_elf_section_type_flags (tree decl, const char *name, int reloc)
7c262518 18174{
1ff8f81a
AM
18175 return default_section_type_flags_1 (decl, name, reloc,
18176 flag_pic || DEFAULT_ABI == ABI_AIX);
7c262518 18177}
d9f6800d
RH
18178
18179/* Record an element in the table of global constructors. SYMBOL is
18180 a SYMBOL_REF of the function to be called; PRIORITY is a number
18181 between 0 and MAX_INIT_PRIORITY.
18182
18183 This differs from default_named_section_asm_out_constructor in
18184 that we have special handling for -mrelocatable. */
18185
18186static void
a2369ed3 18187rs6000_elf_asm_out_constructor (rtx symbol, int priority)
d9f6800d
RH
18188{
18189 const char *section = ".ctors";
18190 char buf[16];
18191
18192 if (priority != DEFAULT_INIT_PRIORITY)
18193 {
18194 sprintf (buf, ".ctors.%.5u",
c4ad648e
AM
18195 /* Invert the numbering so the linker puts us in the proper
18196 order; constructors are run from right to left, and the
18197 linker sorts in increasing order. */
18198 MAX_INIT_PRIORITY - priority);
d9f6800d
RH
18199 section = buf;
18200 }
18201
d6b5193b 18202 switch_to_section (get_section (section, SECTION_WRITE, NULL));
715bdd29 18203 assemble_align (POINTER_SIZE);
d9f6800d
RH
18204
18205 if (TARGET_RELOCATABLE)
18206 {
18207 fputs ("\t.long (", asm_out_file);
18208 output_addr_const (asm_out_file, symbol);
18209 fputs (")@fixup\n", asm_out_file);
18210 }
18211 else
c8af3574 18212 assemble_integer (symbol, POINTER_SIZE / BITS_PER_UNIT, POINTER_SIZE, 1);
d9f6800d
RH
18213}
18214
18215static void
a2369ed3 18216rs6000_elf_asm_out_destructor (rtx symbol, int priority)
d9f6800d
RH
18217{
18218 const char *section = ".dtors";
18219 char buf[16];
18220
18221 if (priority != DEFAULT_INIT_PRIORITY)
18222 {
18223 sprintf (buf, ".dtors.%.5u",
c4ad648e
AM
18224 /* Invert the numbering so the linker puts us in the proper
18225 order; constructors are run from right to left, and the
18226 linker sorts in increasing order. */
18227 MAX_INIT_PRIORITY - priority);
d9f6800d
RH
18228 section = buf;
18229 }
18230
d6b5193b 18231 switch_to_section (get_section (section, SECTION_WRITE, NULL));
715bdd29 18232 assemble_align (POINTER_SIZE);
d9f6800d
RH
18233
18234 if (TARGET_RELOCATABLE)
18235 {
18236 fputs ("\t.long (", asm_out_file);
18237 output_addr_const (asm_out_file, symbol);
18238 fputs (")@fixup\n", asm_out_file);
18239 }
18240 else
c8af3574 18241 assemble_integer (symbol, POINTER_SIZE / BITS_PER_UNIT, POINTER_SIZE, 1);
d9f6800d 18242}
9739c90c
JJ
18243
18244void
a2369ed3 18245rs6000_elf_declare_function_name (FILE *file, const char *name, tree decl)
9739c90c
JJ
18246{
18247 if (TARGET_64BIT)
18248 {
18249 fputs ("\t.section\t\".opd\",\"aw\"\n\t.align 3\n", file);
18250 ASM_OUTPUT_LABEL (file, name);
18251 fputs (DOUBLE_INT_ASM_OP, file);
85b776df
AM
18252 rs6000_output_function_entry (file, name);
18253 fputs (",.TOC.@tocbase,0\n\t.previous\n", file);
18254 if (DOT_SYMBOLS)
9739c90c 18255 {
85b776df 18256 fputs ("\t.size\t", file);
9739c90c 18257 assemble_name (file, name);
85b776df
AM
18258 fputs (",24\n\t.type\t.", file);
18259 assemble_name (file, name);
18260 fputs (",@function\n", file);
18261 if (TREE_PUBLIC (decl) && ! DECL_WEAK (decl))
18262 {
18263 fputs ("\t.globl\t.", file);
18264 assemble_name (file, name);
18265 putc ('\n', file);
18266 }
9739c90c 18267 }
85b776df
AM
18268 else
18269 ASM_OUTPUT_TYPE_DIRECTIVE (file, name, "function");
9739c90c 18270 ASM_DECLARE_RESULT (file, DECL_RESULT (decl));
85b776df
AM
18271 rs6000_output_function_entry (file, name);
18272 fputs (":\n", file);
9739c90c
JJ
18273 return;
18274 }
18275
18276 if (TARGET_RELOCATABLE
7f970b70 18277 && !TARGET_SECURE_PLT
9739c90c 18278 && (get_pool_size () != 0 || current_function_profile)
3c9eb5f4 18279 && uses_TOC ())
9739c90c
JJ
18280 {
18281 char buf[256];
18282
18283 (*targetm.asm_out.internal_label) (file, "LCL", rs6000_pic_labelno);
18284
18285 ASM_GENERATE_INTERNAL_LABEL (buf, "LCTOC", 1);
18286 fprintf (file, "\t.long ");
18287 assemble_name (file, buf);
18288 putc ('-', file);
18289 ASM_GENERATE_INTERNAL_LABEL (buf, "LCF", rs6000_pic_labelno);
18290 assemble_name (file, buf);
18291 putc ('\n', file);
18292 }
18293
18294 ASM_OUTPUT_TYPE_DIRECTIVE (file, name, "function");
18295 ASM_DECLARE_RESULT (file, DECL_RESULT (decl));
18296
18297 if (DEFAULT_ABI == ABI_AIX)
18298 {
18299 const char *desc_name, *orig_name;
18300
18301 orig_name = (*targetm.strip_name_encoding) (name);
18302 desc_name = orig_name;
18303 while (*desc_name == '.')
18304 desc_name++;
18305
18306 if (TREE_PUBLIC (decl))
18307 fprintf (file, "\t.globl %s\n", desc_name);
18308
18309 fprintf (file, "%s\n", MINIMAL_TOC_SECTION_ASM_OP);
18310 fprintf (file, "%s:\n", desc_name);
18311 fprintf (file, "\t.long %s\n", orig_name);
18312 fputs ("\t.long _GLOBAL_OFFSET_TABLE_\n", file);
18313 if (DEFAULT_ABI == ABI_AIX)
18314 fputs ("\t.long 0\n", file);
18315 fprintf (file, "\t.previous\n");
18316 }
18317 ASM_OUTPUT_LABEL (file, name);
18318}
1334b570
AM
18319
18320static void
18321rs6000_elf_end_indicate_exec_stack (void)
18322{
18323 if (TARGET_32BIT)
18324 file_end_indicate_exec_stack ();
18325}
7c262518
RH
18326#endif
18327
cbaaba19 18328#if TARGET_XCOFF
0d5817b2
DE
18329static void
18330rs6000_xcoff_asm_output_anchor (rtx symbol)
18331{
18332 char buffer[100];
18333
18334 sprintf (buffer, "$ + " HOST_WIDE_INT_PRINT_DEC,
18335 SYMBOL_REF_BLOCK_OFFSET (symbol));
18336 ASM_OUTPUT_DEF (asm_out_file, XSTR (symbol, 0), buffer);
18337}
18338
7c262518 18339static void
a2369ed3 18340rs6000_xcoff_asm_globalize_label (FILE *stream, const char *name)
b275d088
DE
18341{
18342 fputs (GLOBAL_ASM_OP, stream);
18343 RS6000_OUTPUT_BASENAME (stream, name);
18344 putc ('\n', stream);
18345}
18346
d6b5193b
RS
18347/* A get_unnamed_decl callback, used for read-only sections. PTR
18348 points to the section string variable. */
18349
18350static void
18351rs6000_xcoff_output_readonly_section_asm_op (const void *directive)
18352{
18353 fprintf (asm_out_file, "\t.csect %s[RO],3\n",
18354 *(const char *const *) directive);
18355}
18356
18357/* Likewise for read-write sections. */
18358
18359static void
18360rs6000_xcoff_output_readwrite_section_asm_op (const void *directive)
18361{
18362 fprintf (asm_out_file, "\t.csect %s[RW],3\n",
18363 *(const char *const *) directive);
18364}
18365
18366/* A get_unnamed_section callback, used for switching to toc_section. */
18367
18368static void
18369rs6000_xcoff_output_toc_section_asm_op (const void *data ATTRIBUTE_UNUSED)
18370{
18371 if (TARGET_MINIMAL_TOC)
18372 {
18373 /* toc_section is always selected at least once from
18374 rs6000_xcoff_file_start, so this is guaranteed to
18375 always be defined once and only once in each file. */
18376 if (!toc_initialized)
18377 {
18378 fputs ("\t.toc\nLCTOC..1:\n", asm_out_file);
18379 fputs ("\t.tc toc_table[TC],toc_table[RW]\n", asm_out_file);
18380 toc_initialized = 1;
18381 }
18382 fprintf (asm_out_file, "\t.csect toc_table[RW]%s\n",
18383 (TARGET_32BIT ? "" : ",3"));
18384 }
18385 else
18386 fputs ("\t.toc\n", asm_out_file);
18387}
18388
18389/* Implement TARGET_ASM_INIT_SECTIONS. */
18390
18391static void
18392rs6000_xcoff_asm_init_sections (void)
18393{
18394 read_only_data_section
18395 = get_unnamed_section (0, rs6000_xcoff_output_readonly_section_asm_op,
18396 &xcoff_read_only_section_name);
18397
18398 private_data_section
18399 = get_unnamed_section (SECTION_WRITE,
18400 rs6000_xcoff_output_readwrite_section_asm_op,
18401 &xcoff_private_data_section_name);
18402
18403 read_only_private_data_section
18404 = get_unnamed_section (0, rs6000_xcoff_output_readonly_section_asm_op,
18405 &xcoff_private_data_section_name);
18406
18407 toc_section
18408 = get_unnamed_section (0, rs6000_xcoff_output_toc_section_asm_op, NULL);
18409
18410 readonly_data_section = read_only_data_section;
18411 exception_section = data_section;
18412}
18413
b275d088 18414static void
c18a5b6c
MM
18415rs6000_xcoff_asm_named_section (const char *name, unsigned int flags,
18416 tree decl ATTRIBUTE_UNUSED)
7c262518 18417{
0e5dbd9b
DE
18418 int smclass;
18419 static const char * const suffix[3] = { "PR", "RO", "RW" };
18420
18421 if (flags & SECTION_CODE)
18422 smclass = 0;
18423 else if (flags & SECTION_WRITE)
18424 smclass = 2;
18425 else
18426 smclass = 1;
18427
5b5198f7 18428 fprintf (asm_out_file, "\t.csect %s%s[%s],%u\n",
0e5dbd9b 18429 (flags & SECTION_CODE) ? "." : "",
5b5198f7 18430 name, suffix[smclass], flags & SECTION_ENTSIZE);
7c262518 18431}
ae46c4e0 18432
d6b5193b 18433static section *
f676971a 18434rs6000_xcoff_select_section (tree decl, int reloc,
c4ad648e 18435 unsigned HOST_WIDE_INT align ATTRIBUTE_UNUSED)
ae46c4e0 18436{
5add3202 18437 if (decl_readonly_section_1 (decl, reloc, 1))
ae46c4e0 18438 {
0e5dbd9b 18439 if (TREE_PUBLIC (decl))
d6b5193b 18440 return read_only_data_section;
ae46c4e0 18441 else
d6b5193b 18442 return read_only_private_data_section;
ae46c4e0
RH
18443 }
18444 else
18445 {
0e5dbd9b 18446 if (TREE_PUBLIC (decl))
d6b5193b 18447 return data_section;
ae46c4e0 18448 else
d6b5193b 18449 return private_data_section;
ae46c4e0
RH
18450 }
18451}
18452
18453static void
a2369ed3 18454rs6000_xcoff_unique_section (tree decl, int reloc ATTRIBUTE_UNUSED)
ae46c4e0
RH
18455{
18456 const char *name;
ae46c4e0 18457
5b5198f7
DE
18458 /* Use select_section for private and uninitialized data. */
18459 if (!TREE_PUBLIC (decl)
18460 || DECL_COMMON (decl)
0e5dbd9b
DE
18461 || DECL_INITIAL (decl) == NULL_TREE
18462 || DECL_INITIAL (decl) == error_mark_node
18463 || (flag_zero_initialized_in_bss
18464 && initializer_zerop (DECL_INITIAL (decl))))
18465 return;
18466
18467 name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl));
18468 name = (*targetm.strip_name_encoding) (name);
18469 DECL_SECTION_NAME (decl) = build_string (strlen (name), name);
ae46c4e0 18470}
b64a1b53 18471
fb49053f
RH
18472/* Select section for constant in constant pool.
18473
18474 On RS/6000, all constants are in the private read-only data area.
18475 However, if this is being placed in the TOC it must be output as a
18476 toc entry. */
18477
d6b5193b 18478static section *
f676971a 18479rs6000_xcoff_select_rtx_section (enum machine_mode mode, rtx x,
c4ad648e 18480 unsigned HOST_WIDE_INT align ATTRIBUTE_UNUSED)
b64a1b53
RH
18481{
18482 if (ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (x, mode))
d6b5193b 18483 return toc_section;
b64a1b53 18484 else
d6b5193b 18485 return read_only_private_data_section;
b64a1b53 18486}
772c5265
RH
18487
18488/* Remove any trailing [DS] or the like from the symbol name. */
18489
18490static const char *
a2369ed3 18491rs6000_xcoff_strip_name_encoding (const char *name)
772c5265
RH
18492{
18493 size_t len;
18494 if (*name == '*')
18495 name++;
18496 len = strlen (name);
18497 if (name[len - 1] == ']')
18498 return ggc_alloc_string (name, len - 4);
18499 else
18500 return name;
18501}
18502
5add3202
DE
18503/* Section attributes. AIX is always PIC. */
18504
18505static unsigned int
a2369ed3 18506rs6000_xcoff_section_type_flags (tree decl, const char *name, int reloc)
5add3202 18507{
5b5198f7
DE
18508 unsigned int align;
18509 unsigned int flags = default_section_type_flags_1 (decl, name, reloc, 1);
18510
18511 /* Align to at least UNIT size. */
18512 if (flags & SECTION_CODE)
18513 align = MIN_UNITS_PER_WORD;
18514 else
18515 /* Increase alignment of large objects if not already stricter. */
18516 align = MAX ((DECL_ALIGN (decl) / BITS_PER_UNIT),
18517 int_size_in_bytes (TREE_TYPE (decl)) > MIN_UNITS_PER_WORD
18518 ? UNITS_PER_FP_WORD : MIN_UNITS_PER_WORD);
18519
18520 return flags | (exact_log2 (align) & SECTION_ENTSIZE);
5add3202 18521}
a5fe455b 18522
1bc7c5b6
ZW
18523/* Output at beginning of assembler file.
18524
18525 Initialize the section names for the RS/6000 at this point.
18526
18527 Specify filename, including full path, to assembler.
18528
18529 We want to go into the TOC section so at least one .toc will be emitted.
18530 Also, in order to output proper .bs/.es pairs, we need at least one static
18531 [RW] section emitted.
18532
18533 Finally, declare mcount when profiling to make the assembler happy. */
18534
18535static void
863d938c 18536rs6000_xcoff_file_start (void)
1bc7c5b6
ZW
18537{
18538 rs6000_gen_section_name (&xcoff_bss_section_name,
18539 main_input_filename, ".bss_");
18540 rs6000_gen_section_name (&xcoff_private_data_section_name,
18541 main_input_filename, ".rw_");
18542 rs6000_gen_section_name (&xcoff_read_only_section_name,
18543 main_input_filename, ".ro_");
18544
18545 fputs ("\t.file\t", asm_out_file);
18546 output_quoted_string (asm_out_file, main_input_filename);
18547 fputc ('\n', asm_out_file);
1bc7c5b6 18548 if (write_symbols != NO_DEBUG)
d6b5193b
RS
18549 switch_to_section (private_data_section);
18550 switch_to_section (text_section);
1bc7c5b6
ZW
18551 if (profile_flag)
18552 fprintf (asm_out_file, "\t.extern %s\n", RS6000_MCOUNT);
18553 rs6000_file_start ();
18554}
18555
a5fe455b
ZW
18556/* Output at end of assembler file.
18557 On the RS/6000, referencing data should automatically pull in text. */
18558
18559static void
863d938c 18560rs6000_xcoff_file_end (void)
a5fe455b 18561{
d6b5193b 18562 switch_to_section (text_section);
a5fe455b 18563 fputs ("_section_.text:\n", asm_out_file);
d6b5193b 18564 switch_to_section (data_section);
a5fe455b
ZW
18565 fputs (TARGET_32BIT
18566 ? "\t.long _section_.text\n" : "\t.llong _section_.text\n",
18567 asm_out_file);
18568}
f1384257 18569#endif /* TARGET_XCOFF */
0e5dbd9b 18570
3c50106f
RH
18571/* Compute a (partial) cost for rtx X. Return true if the complete
18572 cost has been computed, and false if subexpressions should be
18573 scanned. In either case, *TOTAL contains the cost result. */
18574
18575static bool
1494c534 18576rs6000_rtx_costs (rtx x, int code, int outer_code, int *total)
3c50106f 18577{
f0517163
RS
18578 enum machine_mode mode = GET_MODE (x);
18579
3c50106f
RH
18580 switch (code)
18581 {
30a555d9 18582 /* On the RS/6000, if it is valid in the insn, it is free. */
3c50106f 18583 case CONST_INT:
066cd967
DE
18584 if (((outer_code == SET
18585 || outer_code == PLUS
18586 || outer_code == MINUS)
279bb624
DE
18587 && (satisfies_constraint_I (x)
18588 || satisfies_constraint_L (x)))
066cd967 18589 || (outer_code == AND
279bb624
DE
18590 && (satisfies_constraint_K (x)
18591 || (mode == SImode
18592 ? satisfies_constraint_L (x)
18593 : satisfies_constraint_J (x))
1990cd79
AM
18594 || mask_operand (x, mode)
18595 || (mode == DImode
18596 && mask64_operand (x, DImode))))
22e54023 18597 || ((outer_code == IOR || outer_code == XOR)
279bb624
DE
18598 && (satisfies_constraint_K (x)
18599 || (mode == SImode
18600 ? satisfies_constraint_L (x)
18601 : satisfies_constraint_J (x))))
066cd967
DE
18602 || outer_code == ASHIFT
18603 || outer_code == ASHIFTRT
18604 || outer_code == LSHIFTRT
18605 || outer_code == ROTATE
18606 || outer_code == ROTATERT
d5861a7a 18607 || outer_code == ZERO_EXTRACT
066cd967 18608 || (outer_code == MULT
279bb624 18609 && satisfies_constraint_I (x))
22e54023
DE
18610 || ((outer_code == DIV || outer_code == UDIV
18611 || outer_code == MOD || outer_code == UMOD)
18612 && exact_log2 (INTVAL (x)) >= 0)
066cd967 18613 || (outer_code == COMPARE
279bb624
DE
18614 && (satisfies_constraint_I (x)
18615 || satisfies_constraint_K (x)))
22e54023 18616 || (outer_code == EQ
279bb624
DE
18617 && (satisfies_constraint_I (x)
18618 || satisfies_constraint_K (x)
18619 || (mode == SImode
18620 ? satisfies_constraint_L (x)
18621 : satisfies_constraint_J (x))))
22e54023 18622 || (outer_code == GTU
279bb624 18623 && satisfies_constraint_I (x))
22e54023 18624 || (outer_code == LTU
279bb624 18625 && satisfies_constraint_P (x)))
066cd967
DE
18626 {
18627 *total = 0;
18628 return true;
18629 }
18630 else if ((outer_code == PLUS
4ae234b0 18631 && reg_or_add_cint_operand (x, VOIDmode))
066cd967 18632 || (outer_code == MINUS
4ae234b0 18633 && reg_or_sub_cint_operand (x, VOIDmode))
066cd967
DE
18634 || ((outer_code == SET
18635 || outer_code == IOR
18636 || outer_code == XOR)
18637 && (INTVAL (x)
18638 & ~ (unsigned HOST_WIDE_INT) 0xffffffff) == 0))
18639 {
18640 *total = COSTS_N_INSNS (1);
18641 return true;
18642 }
18643 /* FALLTHRU */
18644
18645 case CONST_DOUBLE:
f6fe3a22 18646 if (mode == DImode && code == CONST_DOUBLE)
066cd967 18647 {
f6fe3a22
DE
18648 if ((outer_code == IOR || outer_code == XOR)
18649 && CONST_DOUBLE_HIGH (x) == 0
18650 && (CONST_DOUBLE_LOW (x)
18651 & ~ (unsigned HOST_WIDE_INT) 0xffff) == 0)
18652 {
18653 *total = 0;
18654 return true;
18655 }
18656 else if ((outer_code == AND && and64_2_operand (x, DImode))
18657 || ((outer_code == SET
18658 || outer_code == IOR
18659 || outer_code == XOR)
18660 && CONST_DOUBLE_HIGH (x) == 0))
18661 {
18662 *total = COSTS_N_INSNS (1);
18663 return true;
18664 }
066cd967
DE
18665 }
18666 /* FALLTHRU */
18667
3c50106f 18668 case CONST:
066cd967 18669 case HIGH:
3c50106f 18670 case SYMBOL_REF:
066cd967
DE
18671 case MEM:
18672 /* When optimizing for size, MEM should be slightly more expensive
18673 than generating address, e.g., (plus (reg) (const)).
c112cf2b 18674 L1 cache latency is about two instructions. */
066cd967 18675 *total = optimize_size ? COSTS_N_INSNS (1) + 1 : COSTS_N_INSNS (2);
3c50106f
RH
18676 return true;
18677
30a555d9
DE
18678 case LABEL_REF:
18679 *total = 0;
18680 return true;
18681
3c50106f 18682 case PLUS:
f0517163 18683 if (mode == DFmode)
066cd967
DE
18684 {
18685 if (GET_CODE (XEXP (x, 0)) == MULT)
18686 {
18687 /* FNMA accounted in outer NEG. */
18688 if (outer_code == NEG)
18689 *total = rs6000_cost->dmul - rs6000_cost->fp;
18690 else
18691 *total = rs6000_cost->dmul;
18692 }
18693 else
18694 *total = rs6000_cost->fp;
18695 }
f0517163 18696 else if (mode == SFmode)
066cd967
DE
18697 {
18698 /* FNMA accounted in outer NEG. */
18699 if (outer_code == NEG && GET_CODE (XEXP (x, 0)) == MULT)
18700 *total = 0;
18701 else
18702 *total = rs6000_cost->fp;
18703 }
f0517163 18704 else
066cd967
DE
18705 *total = COSTS_N_INSNS (1);
18706 return false;
3c50106f 18707
52190329 18708 case MINUS:
f0517163 18709 if (mode == DFmode)
066cd967
DE
18710 {
18711 if (GET_CODE (XEXP (x, 0)) == MULT)
18712 {
18713 /* FNMA accounted in outer NEG. */
18714 if (outer_code == NEG)
18715 *total = 0;
18716 else
18717 *total = rs6000_cost->dmul;
18718 }
18719 else
18720 *total = rs6000_cost->fp;
18721 }
f0517163 18722 else if (mode == SFmode)
066cd967
DE
18723 {
18724 /* FNMA accounted in outer NEG. */
18725 if (outer_code == NEG && GET_CODE (XEXP (x, 0)) == MULT)
18726 *total = 0;
18727 else
18728 *total = rs6000_cost->fp;
18729 }
f0517163 18730 else
c4ad648e 18731 *total = COSTS_N_INSNS (1);
066cd967 18732 return false;
3c50106f
RH
18733
18734 case MULT:
c9dbf840 18735 if (GET_CODE (XEXP (x, 1)) == CONST_INT
279bb624 18736 && satisfies_constraint_I (XEXP (x, 1)))
3c50106f 18737 {
8b897cfa
RS
18738 if (INTVAL (XEXP (x, 1)) >= -256
18739 && INTVAL (XEXP (x, 1)) <= 255)
06a67bdd 18740 *total = rs6000_cost->mulsi_const9;
8b897cfa 18741 else
06a67bdd 18742 *total = rs6000_cost->mulsi_const;
3c50106f 18743 }
066cd967
DE
18744 /* FMA accounted in outer PLUS/MINUS. */
18745 else if ((mode == DFmode || mode == SFmode)
18746 && (outer_code == PLUS || outer_code == MINUS))
18747 *total = 0;
f0517163 18748 else if (mode == DFmode)
06a67bdd 18749 *total = rs6000_cost->dmul;
f0517163 18750 else if (mode == SFmode)
06a67bdd 18751 *total = rs6000_cost->fp;
f0517163 18752 else if (mode == DImode)
06a67bdd 18753 *total = rs6000_cost->muldi;
8b897cfa 18754 else
06a67bdd 18755 *total = rs6000_cost->mulsi;
066cd967 18756 return false;
3c50106f
RH
18757
18758 case DIV:
18759 case MOD:
f0517163
RS
18760 if (FLOAT_MODE_P (mode))
18761 {
06a67bdd
RS
18762 *total = mode == DFmode ? rs6000_cost->ddiv
18763 : rs6000_cost->sdiv;
066cd967 18764 return false;
f0517163 18765 }
5efb1046 18766 /* FALLTHRU */
3c50106f
RH
18767
18768 case UDIV:
18769 case UMOD:
627b6fe2
DJ
18770 if (GET_CODE (XEXP (x, 1)) == CONST_INT
18771 && exact_log2 (INTVAL (XEXP (x, 1))) >= 0)
18772 {
18773 if (code == DIV || code == MOD)
18774 /* Shift, addze */
18775 *total = COSTS_N_INSNS (2);
18776 else
18777 /* Shift */
18778 *total = COSTS_N_INSNS (1);
18779 }
c4ad648e 18780 else
627b6fe2
DJ
18781 {
18782 if (GET_MODE (XEXP (x, 1)) == DImode)
18783 *total = rs6000_cost->divdi;
18784 else
18785 *total = rs6000_cost->divsi;
18786 }
18787 /* Add in shift and subtract for MOD. */
18788 if (code == MOD || code == UMOD)
18789 *total += COSTS_N_INSNS (2);
066cd967 18790 return false;
3c50106f
RH
18791
18792 case FFS:
18793 *total = COSTS_N_INSNS (4);
066cd967 18794 return false;
3c50106f 18795
06a67bdd 18796 case NOT:
066cd967
DE
18797 if (outer_code == AND || outer_code == IOR || outer_code == XOR)
18798 {
18799 *total = 0;
18800 return false;
18801 }
18802 /* FALLTHRU */
18803
18804 case AND:
18805 case IOR:
18806 case XOR:
d5861a7a
DE
18807 case ZERO_EXTRACT:
18808 *total = COSTS_N_INSNS (1);
18809 return false;
18810
066cd967
DE
18811 case ASHIFT:
18812 case ASHIFTRT:
18813 case LSHIFTRT:
18814 case ROTATE:
18815 case ROTATERT:
d5861a7a 18816 /* Handle mul_highpart. */
066cd967
DE
18817 if (outer_code == TRUNCATE
18818 && GET_CODE (XEXP (x, 0)) == MULT)
18819 {
18820 if (mode == DImode)
18821 *total = rs6000_cost->muldi;
18822 else
18823 *total = rs6000_cost->mulsi;
18824 return true;
18825 }
d5861a7a
DE
18826 else if (outer_code == AND)
18827 *total = 0;
18828 else
18829 *total = COSTS_N_INSNS (1);
18830 return false;
18831
18832 case SIGN_EXTEND:
18833 case ZERO_EXTEND:
18834 if (GET_CODE (XEXP (x, 0)) == MEM)
18835 *total = 0;
18836 else
18837 *total = COSTS_N_INSNS (1);
066cd967 18838 return false;
06a67bdd 18839
066cd967
DE
18840 case COMPARE:
18841 case NEG:
18842 case ABS:
18843 if (!FLOAT_MODE_P (mode))
18844 {
18845 *total = COSTS_N_INSNS (1);
18846 return false;
18847 }
18848 /* FALLTHRU */
18849
18850 case FLOAT:
18851 case UNSIGNED_FLOAT:
18852 case FIX:
18853 case UNSIGNED_FIX:
06a67bdd
RS
18854 case FLOAT_TRUNCATE:
18855 *total = rs6000_cost->fp;
066cd967 18856 return false;
06a67bdd 18857
a2af5043
DJ
18858 case FLOAT_EXTEND:
18859 if (mode == DFmode)
18860 *total = 0;
18861 else
18862 *total = rs6000_cost->fp;
18863 return false;
18864
06a67bdd
RS
18865 case UNSPEC:
18866 switch (XINT (x, 1))
18867 {
18868 case UNSPEC_FRSP:
18869 *total = rs6000_cost->fp;
18870 return true;
18871
18872 default:
18873 break;
18874 }
18875 break;
18876
18877 case CALL:
18878 case IF_THEN_ELSE:
18879 if (optimize_size)
18880 {
18881 *total = COSTS_N_INSNS (1);
18882 return true;
18883 }
066cd967
DE
18884 else if (FLOAT_MODE_P (mode)
18885 && TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT && TARGET_FPRS)
18886 {
18887 *total = rs6000_cost->fp;
18888 return false;
18889 }
06a67bdd
RS
18890 break;
18891
c0600ecd
DE
18892 case EQ:
18893 case GTU:
18894 case LTU:
22e54023
DE
18895 /* Carry bit requires mode == Pmode.
18896 NEG or PLUS already counted so only add one. */
18897 if (mode == Pmode
18898 && (outer_code == NEG || outer_code == PLUS))
c0600ecd 18899 {
22e54023
DE
18900 *total = COSTS_N_INSNS (1);
18901 return true;
18902 }
18903 if (outer_code == SET)
18904 {
18905 if (XEXP (x, 1) == const0_rtx)
c0600ecd 18906 {
22e54023 18907 *total = COSTS_N_INSNS (2);
c0600ecd 18908 return true;
c0600ecd 18909 }
22e54023
DE
18910 else if (mode == Pmode)
18911 {
18912 *total = COSTS_N_INSNS (3);
18913 return false;
18914 }
18915 }
18916 /* FALLTHRU */
18917
18918 case GT:
18919 case LT:
18920 case UNORDERED:
18921 if (outer_code == SET && (XEXP (x, 1) == const0_rtx))
18922 {
18923 *total = COSTS_N_INSNS (2);
18924 return true;
c0600ecd 18925 }
22e54023
DE
18926 /* CC COMPARE. */
18927 if (outer_code == COMPARE)
18928 {
18929 *total = 0;
18930 return true;
18931 }
18932 break;
c0600ecd 18933
3c50106f 18934 default:
06a67bdd 18935 break;
3c50106f 18936 }
06a67bdd
RS
18937
18938 return false;
3c50106f
RH
18939}
18940
34bb030a
DE
18941/* A C expression returning the cost of moving data from a register of class
18942 CLASS1 to one of CLASS2. */
18943
18944int
f676971a 18945rs6000_register_move_cost (enum machine_mode mode,
a2369ed3 18946 enum reg_class from, enum reg_class to)
34bb030a
DE
18947{
18948 /* Moves from/to GENERAL_REGS. */
18949 if (reg_classes_intersect_p (to, GENERAL_REGS)
18950 || reg_classes_intersect_p (from, GENERAL_REGS))
18951 {
18952 if (! reg_classes_intersect_p (to, GENERAL_REGS))
18953 from = to;
18954
18955 if (from == FLOAT_REGS || from == ALTIVEC_REGS)
18956 return (rs6000_memory_move_cost (mode, from, 0)
18957 + rs6000_memory_move_cost (mode, GENERAL_REGS, 0));
18958
c4ad648e
AM
18959 /* It's more expensive to move CR_REGS than CR0_REGS because of the
18960 shift. */
34bb030a
DE
18961 else if (from == CR_REGS)
18962 return 4;
18963
18964 else
c4ad648e 18965 /* A move will cost one instruction per GPR moved. */
c8b622ff 18966 return 2 * hard_regno_nregs[0][mode];
34bb030a
DE
18967 }
18968
c4ad648e 18969 /* Moving between two similar registers is just one instruction. */
34bb030a
DE
18970 else if (reg_classes_intersect_p (to, from))
18971 return mode == TFmode ? 4 : 2;
18972
c4ad648e 18973 /* Everything else has to go through GENERAL_REGS. */
34bb030a 18974 else
f676971a 18975 return (rs6000_register_move_cost (mode, GENERAL_REGS, to)
34bb030a
DE
18976 + rs6000_register_move_cost (mode, from, GENERAL_REGS));
18977}
18978
18979/* A C expressions returning the cost of moving data of MODE from a register to
18980 or from memory. */
18981
18982int
f676971a 18983rs6000_memory_move_cost (enum machine_mode mode, enum reg_class class,
a2369ed3 18984 int in ATTRIBUTE_UNUSED)
34bb030a
DE
18985{
18986 if (reg_classes_intersect_p (class, GENERAL_REGS))
c8b622ff 18987 return 4 * hard_regno_nregs[0][mode];
34bb030a 18988 else if (reg_classes_intersect_p (class, FLOAT_REGS))
c8b622ff 18989 return 4 * hard_regno_nregs[32][mode];
34bb030a 18990 else if (reg_classes_intersect_p (class, ALTIVEC_REGS))
c8b622ff 18991 return 4 * hard_regno_nregs[FIRST_ALTIVEC_REGNO][mode];
34bb030a
DE
18992 else
18993 return 4 + rs6000_register_move_cost (mode, class, GENERAL_REGS);
18994}
18995
ef765ea9
DE
18996/* Newton-Raphson approximation of single-precision floating point divide n/d.
18997 Assumes no trapping math and finite arguments. */
18998
18999void
19000rs6000_emit_swdivsf (rtx res, rtx n, rtx d)
19001{
19002 rtx x0, e0, e1, y1, u0, v0, one;
19003
19004 x0 = gen_reg_rtx (SFmode);
19005 e0 = gen_reg_rtx (SFmode);
19006 e1 = gen_reg_rtx (SFmode);
19007 y1 = gen_reg_rtx (SFmode);
19008 u0 = gen_reg_rtx (SFmode);
19009 v0 = gen_reg_rtx (SFmode);
19010 one = force_reg (SFmode, CONST_DOUBLE_FROM_REAL_VALUE (dconst1, SFmode));
19011
19012 /* x0 = 1./d estimate */
19013 emit_insn (gen_rtx_SET (VOIDmode, x0,
19014 gen_rtx_UNSPEC (SFmode, gen_rtvec (1, d),
19015 UNSPEC_FRES)));
19016 /* e0 = 1. - d * x0 */
19017 emit_insn (gen_rtx_SET (VOIDmode, e0,
19018 gen_rtx_MINUS (SFmode, one,
19019 gen_rtx_MULT (SFmode, d, x0))));
19020 /* e1 = e0 + e0 * e0 */
19021 emit_insn (gen_rtx_SET (VOIDmode, e1,
19022 gen_rtx_PLUS (SFmode,
19023 gen_rtx_MULT (SFmode, e0, e0), e0)));
19024 /* y1 = x0 + e1 * x0 */
19025 emit_insn (gen_rtx_SET (VOIDmode, y1,
19026 gen_rtx_PLUS (SFmode,
19027 gen_rtx_MULT (SFmode, e1, x0), x0)));
19028 /* u0 = n * y1 */
19029 emit_insn (gen_rtx_SET (VOIDmode, u0,
19030 gen_rtx_MULT (SFmode, n, y1)));
19031 /* v0 = n - d * u0 */
19032 emit_insn (gen_rtx_SET (VOIDmode, v0,
19033 gen_rtx_MINUS (SFmode, n,
19034 gen_rtx_MULT (SFmode, d, u0))));
19035 /* res = u0 + v0 * y1 */
19036 emit_insn (gen_rtx_SET (VOIDmode, res,
19037 gen_rtx_PLUS (SFmode,
19038 gen_rtx_MULT (SFmode, v0, y1), u0)));
19039}
19040
19041/* Newton-Raphson approximation of double-precision floating point divide n/d.
19042 Assumes no trapping math and finite arguments. */
19043
19044void
19045rs6000_emit_swdivdf (rtx res, rtx n, rtx d)
19046{
19047 rtx x0, e0, e1, e2, y1, y2, y3, u0, v0, one;
19048
19049 x0 = gen_reg_rtx (DFmode);
19050 e0 = gen_reg_rtx (DFmode);
19051 e1 = gen_reg_rtx (DFmode);
19052 e2 = gen_reg_rtx (DFmode);
19053 y1 = gen_reg_rtx (DFmode);
19054 y2 = gen_reg_rtx (DFmode);
19055 y3 = gen_reg_rtx (DFmode);
19056 u0 = gen_reg_rtx (DFmode);
19057 v0 = gen_reg_rtx (DFmode);
19058 one = force_reg (DFmode, CONST_DOUBLE_FROM_REAL_VALUE (dconst1, DFmode));
19059
19060 /* x0 = 1./d estimate */
19061 emit_insn (gen_rtx_SET (VOIDmode, x0,
19062 gen_rtx_UNSPEC (DFmode, gen_rtvec (1, d),
19063 UNSPEC_FRES)));
19064 /* e0 = 1. - d * x0 */
19065 emit_insn (gen_rtx_SET (VOIDmode, e0,
19066 gen_rtx_MINUS (DFmode, one,
19067 gen_rtx_MULT (SFmode, d, x0))));
19068 /* y1 = x0 + e0 * x0 */
19069 emit_insn (gen_rtx_SET (VOIDmode, y1,
19070 gen_rtx_PLUS (DFmode,
19071 gen_rtx_MULT (DFmode, e0, x0), x0)));
19072 /* e1 = e0 * e0 */
19073 emit_insn (gen_rtx_SET (VOIDmode, e1,
19074 gen_rtx_MULT (DFmode, e0, e0)));
19075 /* y2 = y1 + e1 * y1 */
19076 emit_insn (gen_rtx_SET (VOIDmode, y2,
19077 gen_rtx_PLUS (DFmode,
19078 gen_rtx_MULT (DFmode, e1, y1), y1)));
19079 /* e2 = e1 * e1 */
19080 emit_insn (gen_rtx_SET (VOIDmode, e2,
19081 gen_rtx_MULT (DFmode, e1, e1)));
19082 /* y3 = y2 + e2 * y2 */
19083 emit_insn (gen_rtx_SET (VOIDmode, y3,
19084 gen_rtx_PLUS (DFmode,
19085 gen_rtx_MULT (DFmode, e2, y2), y2)));
19086 /* u0 = n * y3 */
19087 emit_insn (gen_rtx_SET (VOIDmode, u0,
19088 gen_rtx_MULT (DFmode, n, y3)));
19089 /* v0 = n - d * u0 */
19090 emit_insn (gen_rtx_SET (VOIDmode, v0,
19091 gen_rtx_MINUS (DFmode, n,
19092 gen_rtx_MULT (DFmode, d, u0))));
19093 /* res = u0 + v0 * y3 */
19094 emit_insn (gen_rtx_SET (VOIDmode, res,
19095 gen_rtx_PLUS (DFmode,
19096 gen_rtx_MULT (DFmode, v0, y3), u0)));
19097}
19098
ded9bf77
AH
19099/* Return an RTX representing where to find the function value of a
19100 function returning MODE. */
19101static rtx
19102rs6000_complex_function_value (enum machine_mode mode)
19103{
19104 unsigned int regno;
19105 rtx r1, r2;
19106 enum machine_mode inner = GET_MODE_INNER (mode);
fb7e4164 19107 unsigned int inner_bytes = GET_MODE_SIZE (inner);
ded9bf77 19108
18f63bfa
AH
19109 if (FLOAT_MODE_P (mode) && TARGET_HARD_FLOAT && TARGET_FPRS)
19110 regno = FP_ARG_RETURN;
354ed18f
AH
19111 else
19112 {
18f63bfa 19113 regno = GP_ARG_RETURN;
ded9bf77 19114
18f63bfa
AH
19115 /* 32-bit is OK since it'll go in r3/r4. */
19116 if (TARGET_32BIT && inner_bytes >= 4)
ded9bf77
AH
19117 return gen_rtx_REG (mode, regno);
19118 }
19119
18f63bfa
AH
19120 if (inner_bytes >= 8)
19121 return gen_rtx_REG (mode, regno);
19122
ded9bf77
AH
19123 r1 = gen_rtx_EXPR_LIST (inner, gen_rtx_REG (inner, regno),
19124 const0_rtx);
19125 r2 = gen_rtx_EXPR_LIST (inner, gen_rtx_REG (inner, regno + 1),
fb7e4164 19126 GEN_INT (inner_bytes));
ded9bf77
AH
19127 return gen_rtx_PARALLEL (mode, gen_rtvec (2, r1, r2));
19128}
19129
a6ebc39a
AH
19130/* Define how to find the value returned by a function.
19131 VALTYPE is the data type of the value (as a tree).
19132 If the precise function being called is known, FUNC is its FUNCTION_DECL;
19133 otherwise, FUNC is 0.
19134
19135 On the SPE, both FPs and vectors are returned in r3.
19136
19137 On RS/6000 an integer value is in r3 and a floating-point value is in
19138 fp1, unless -msoft-float. */
19139
19140rtx
19141rs6000_function_value (tree valtype, tree func ATTRIBUTE_UNUSED)
19142{
19143 enum machine_mode mode;
2a8fa26c 19144 unsigned int regno;
a6ebc39a 19145
594a51fe
SS
19146 /* Special handling for structs in darwin64. */
19147 if (rs6000_darwin64_abi
19148 && TYPE_MODE (valtype) == BLKmode
0b5383eb
DJ
19149 && TREE_CODE (valtype) == RECORD_TYPE
19150 && int_size_in_bytes (valtype) > 0)
594a51fe
SS
19151 {
19152 CUMULATIVE_ARGS valcum;
19153 rtx valret;
19154
0b5383eb 19155 valcum.words = 0;
594a51fe
SS
19156 valcum.fregno = FP_ARG_MIN_REG;
19157 valcum.vregno = ALTIVEC_ARG_MIN_REG;
0b5383eb
DJ
19158 /* Do a trial code generation as if this were going to be passed as
19159 an argument; if any part goes in memory, we return NULL. */
19160 valret = rs6000_darwin64_record_arg (&valcum, valtype, 1, true);
594a51fe
SS
19161 if (valret)
19162 return valret;
19163 /* Otherwise fall through to standard ABI rules. */
19164 }
19165
0e67400a
FJ
19166 if (TARGET_32BIT && TARGET_POWERPC64 && TYPE_MODE (valtype) == DImode)
19167 {
19168 /* Long long return value need be split in -mpowerpc64, 32bit ABI. */
19169 return gen_rtx_PARALLEL (DImode,
19170 gen_rtvec (2,
19171 gen_rtx_EXPR_LIST (VOIDmode,
19172 gen_rtx_REG (SImode, GP_ARG_RETURN),
19173 const0_rtx),
19174 gen_rtx_EXPR_LIST (VOIDmode,
19175 gen_rtx_REG (SImode,
19176 GP_ARG_RETURN + 1),
19177 GEN_INT (4))));
19178 }
0f086e42
FJ
19179 if (TARGET_32BIT && TARGET_POWERPC64 && TYPE_MODE (valtype) == DCmode)
19180 {
19181 return gen_rtx_PARALLEL (DCmode,
19182 gen_rtvec (4,
19183 gen_rtx_EXPR_LIST (VOIDmode,
19184 gen_rtx_REG (SImode, GP_ARG_RETURN),
19185 const0_rtx),
19186 gen_rtx_EXPR_LIST (VOIDmode,
19187 gen_rtx_REG (SImode,
19188 GP_ARG_RETURN + 1),
19189 GEN_INT (4)),
19190 gen_rtx_EXPR_LIST (VOIDmode,
19191 gen_rtx_REG (SImode,
19192 GP_ARG_RETURN + 2),
19193 GEN_INT (8)),
19194 gen_rtx_EXPR_LIST (VOIDmode,
19195 gen_rtx_REG (SImode,
19196 GP_ARG_RETURN + 3),
19197 GEN_INT (12))));
19198 }
602ea4d3 19199
a6ebc39a
AH
19200 if ((INTEGRAL_TYPE_P (valtype)
19201 && TYPE_PRECISION (valtype) < BITS_PER_WORD)
19202 || POINTER_TYPE_P (valtype))
b78d48dd 19203 mode = TARGET_32BIT ? SImode : DImode;
a6ebc39a
AH
19204 else
19205 mode = TYPE_MODE (valtype);
19206
00b79d54
BE
19207 if (DECIMAL_FLOAT_MODE_P (mode))
19208 regno = GP_ARG_RETURN;
19209 else if (SCALAR_FLOAT_TYPE_P (valtype) && TARGET_HARD_FLOAT && TARGET_FPRS)
2a8fa26c 19210 regno = FP_ARG_RETURN;
ded9bf77 19211 else if (TREE_CODE (valtype) == COMPLEX_TYPE
42ba5130 19212 && targetm.calls.split_complex_arg)
ded9bf77 19213 return rs6000_complex_function_value (mode);
44688022 19214 else if (TREE_CODE (valtype) == VECTOR_TYPE
d0b2079e 19215 && TARGET_ALTIVEC && TARGET_ALTIVEC_ABI
23ba09f0 19216 && ALTIVEC_VECTOR_MODE (mode))
a6ebc39a 19217 regno = ALTIVEC_ARG_RETURN;
18f63bfa
AH
19218 else if (TARGET_E500_DOUBLE && TARGET_HARD_FLOAT
19219 && (mode == DFmode || mode == DCmode))
19220 return spe_build_register_parallel (mode, GP_ARG_RETURN);
a6ebc39a
AH
19221 else
19222 regno = GP_ARG_RETURN;
19223
19224 return gen_rtx_REG (mode, regno);
19225}
19226
ded9bf77
AH
19227/* Define how to find the value returned by a library function
19228 assuming the value has mode MODE. */
19229rtx
19230rs6000_libcall_value (enum machine_mode mode)
19231{
19232 unsigned int regno;
19233
2e6c9641
FJ
19234 if (TARGET_32BIT && TARGET_POWERPC64 && mode == DImode)
19235 {
19236 /* Long long return value need be split in -mpowerpc64, 32bit ABI. */
19237 return gen_rtx_PARALLEL (DImode,
19238 gen_rtvec (2,
19239 gen_rtx_EXPR_LIST (VOIDmode,
19240 gen_rtx_REG (SImode, GP_ARG_RETURN),
19241 const0_rtx),
19242 gen_rtx_EXPR_LIST (VOIDmode,
19243 gen_rtx_REG (SImode,
19244 GP_ARG_RETURN + 1),
19245 GEN_INT (4))));
19246 }
19247
00b79d54
BE
19248 if (DECIMAL_FLOAT_MODE_P (mode))
19249 regno = GP_ARG_RETURN;
19250 else if (SCALAR_FLOAT_MODE_P (mode)
ded9bf77
AH
19251 && TARGET_HARD_FLOAT && TARGET_FPRS)
19252 regno = FP_ARG_RETURN;
44688022
AM
19253 else if (ALTIVEC_VECTOR_MODE (mode)
19254 && TARGET_ALTIVEC && TARGET_ALTIVEC_ABI)
ded9bf77 19255 regno = ALTIVEC_ARG_RETURN;
42ba5130 19256 else if (COMPLEX_MODE_P (mode) && targetm.calls.split_complex_arg)
ded9bf77 19257 return rs6000_complex_function_value (mode);
18f63bfa
AH
19258 else if (TARGET_E500_DOUBLE && TARGET_HARD_FLOAT
19259 && (mode == DFmode || mode == DCmode))
19260 return spe_build_register_parallel (mode, GP_ARG_RETURN);
ded9bf77
AH
19261 else
19262 regno = GP_ARG_RETURN;
19263
19264 return gen_rtx_REG (mode, regno);
19265}
19266
d1d0c603
JJ
19267/* Define the offset between two registers, FROM to be eliminated and its
19268 replacement TO, at the start of a routine. */
19269HOST_WIDE_INT
19270rs6000_initial_elimination_offset (int from, int to)
19271{
19272 rs6000_stack_t *info = rs6000_stack_info ();
19273 HOST_WIDE_INT offset;
19274
7d5175e1 19275 if (from == HARD_FRAME_POINTER_REGNUM && to == STACK_POINTER_REGNUM)
d1d0c603 19276 offset = info->push_p ? 0 : -info->total_size;
7d5175e1
JJ
19277 else if (from == FRAME_POINTER_REGNUM && to == STACK_POINTER_REGNUM)
19278 {
19279 offset = info->push_p ? 0 : -info->total_size;
19280 if (FRAME_GROWS_DOWNWARD)
5b667039 19281 offset += info->fixed_size + info->vars_size + info->parm_size;
7d5175e1
JJ
19282 }
19283 else if (from == FRAME_POINTER_REGNUM && to == HARD_FRAME_POINTER_REGNUM)
19284 offset = FRAME_GROWS_DOWNWARD
5b667039 19285 ? info->fixed_size + info->vars_size + info->parm_size
7d5175e1
JJ
19286 : 0;
19287 else if (from == ARG_POINTER_REGNUM && to == HARD_FRAME_POINTER_REGNUM)
d1d0c603
JJ
19288 offset = info->total_size;
19289 else if (from == ARG_POINTER_REGNUM && to == STACK_POINTER_REGNUM)
19290 offset = info->push_p ? info->total_size : 0;
19291 else if (from == RS6000_PIC_OFFSET_TABLE_REGNUM)
19292 offset = 0;
19293 else
37409796 19294 gcc_unreachable ();
d1d0c603
JJ
19295
19296 return offset;
19297}
19298
58646b77 19299/* Return true if TYPE is a SPE or AltiVec opaque type. */
62e1dfcf 19300
c8e4f0e9 19301static bool
58646b77 19302rs6000_is_opaque_type (tree type)
62e1dfcf 19303{
58646b77 19304 return (type == opaque_V2SI_type_node
2abe3e28 19305 || type == opaque_V2SF_type_node
58646b77
PB
19306 || type == opaque_p_V2SI_type_node
19307 || type == opaque_V4SI_type_node);
62e1dfcf
NC
19308}
19309
96714395 19310static rtx
a2369ed3 19311rs6000_dwarf_register_span (rtx reg)
96714395
AH
19312{
19313 unsigned regno;
19314
4d4cbc0e
AH
19315 if (TARGET_SPE
19316 && (SPE_VECTOR_MODE (GET_MODE (reg))
19317 || (TARGET_E500_DOUBLE && GET_MODE (reg) == DFmode)))
19318 ;
19319 else
96714395
AH
19320 return NULL_RTX;
19321
19322 regno = REGNO (reg);
19323
19324 /* The duality of the SPE register size wreaks all kinds of havoc.
19325 This is a way of distinguishing r0 in 32-bits from r0 in
19326 64-bits. */
19327 return
19328 gen_rtx_PARALLEL (VOIDmode,
3bd104d1
AH
19329 BYTES_BIG_ENDIAN
19330 ? gen_rtvec (2,
19331 gen_rtx_REG (SImode, regno + 1200),
19332 gen_rtx_REG (SImode, regno))
19333 : gen_rtvec (2,
19334 gen_rtx_REG (SImode, regno),
19335 gen_rtx_REG (SImode, regno + 1200)));
96714395
AH
19336}
19337
93c9d1ba
AM
19338/* Map internal gcc register numbers to DWARF2 register numbers. */
19339
19340unsigned int
19341rs6000_dbx_register_number (unsigned int regno)
19342{
19343 if (regno <= 63 || write_symbols != DWARF2_DEBUG)
19344 return regno;
19345 if (regno == MQ_REGNO)
19346 return 100;
19347 if (regno == LINK_REGISTER_REGNUM)
19348 return 108;
19349 if (regno == COUNT_REGISTER_REGNUM)
19350 return 109;
19351 if (CR_REGNO_P (regno))
19352 return regno - CR0_REGNO + 86;
19353 if (regno == XER_REGNO)
19354 return 101;
19355 if (ALTIVEC_REGNO_P (regno))
19356 return regno - FIRST_ALTIVEC_REGNO + 1124;
19357 if (regno == VRSAVE_REGNO)
19358 return 356;
19359 if (regno == VSCR_REGNO)
19360 return 67;
19361 if (regno == SPE_ACC_REGNO)
19362 return 99;
19363 if (regno == SPEFSCR_REGNO)
19364 return 612;
19365 /* SPE high reg number. We get these values of regno from
19366 rs6000_dwarf_register_span. */
37409796
NS
19367 gcc_assert (regno >= 1200 && regno < 1232);
19368 return regno;
93c9d1ba
AM
19369}
19370
93f90be6 19371/* target hook eh_return_filter_mode */
f676971a 19372static enum machine_mode
93f90be6
FJ
19373rs6000_eh_return_filter_mode (void)
19374{
19375 return TARGET_32BIT ? SImode : word_mode;
19376}
19377
00b79d54
BE
19378/* Target hook for scalar_mode_supported_p. */
19379static bool
19380rs6000_scalar_mode_supported_p (enum machine_mode mode)
19381{
19382 if (DECIMAL_FLOAT_MODE_P (mode))
19383 return true;
19384 else
19385 return default_scalar_mode_supported_p (mode);
19386}
19387
f676971a
EC
19388/* Target hook for vector_mode_supported_p. */
19389static bool
19390rs6000_vector_mode_supported_p (enum machine_mode mode)
19391{
19392
19393 if (TARGET_SPE && SPE_VECTOR_MODE (mode))
19394 return true;
19395
19396 else if (TARGET_ALTIVEC && ALTIVEC_VECTOR_MODE (mode))
19397 return true;
19398
19399 else
19400 return false;
19401}
19402
bb8df8a6
EC
19403/* Target hook for invalid_arg_for_unprototyped_fn. */
19404static const char *
4d3e6fae
FJ
19405invalid_arg_for_unprototyped_fn (tree typelist, tree funcdecl, tree val)
19406{
19407 return (!rs6000_darwin64_abi
19408 && typelist == 0
19409 && TREE_CODE (TREE_TYPE (val)) == VECTOR_TYPE
19410 && (funcdecl == NULL_TREE
19411 || (TREE_CODE (funcdecl) == FUNCTION_DECL
19412 && DECL_BUILT_IN_CLASS (funcdecl) != BUILT_IN_MD)))
19413 ? N_("AltiVec argument passed to unprototyped function")
19414 : NULL;
19415}
19416
3aebbe5f
JJ
19417/* For TARGET_SECURE_PLT 32-bit PIC code we can save PIC register
19418 setup by using __stack_chk_fail_local hidden function instead of
19419 calling __stack_chk_fail directly. Otherwise it is better to call
19420 __stack_chk_fail directly. */
19421
19422static tree
19423rs6000_stack_protect_fail (void)
19424{
19425 return (DEFAULT_ABI == ABI_V4 && TARGET_SECURE_PLT && flag_pic)
19426 ? default_hidden_stack_protect_fail ()
19427 : default_external_stack_protect_fail ();
19428}
19429
17211ab5 19430#include "gt-rs6000.h"