]> git.ipfire.org Git - thirdparty/gcc.git/blob - gcc/config/rs6000/rs6000.c
Stack usage support
[thirdparty/gcc.git] / gcc / config / rs6000 / rs6000.c
1 /* Subroutines used for code generation on IBM RS/6000.
2 Copyright (C) 1991, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
3 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010
4 Free Software Foundation, Inc.
5 Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu)
6
7 This file is part of GCC.
8
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 3, or (at your
12 option) any later version.
13
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.
18
19 You should have received a copy of the GNU General Public License
20 along with GCC; see the file COPYING3. If not see
21 <http://www.gnu.org/licenses/>. */
22
23 #include "config.h"
24 #include "system.h"
25 #include "coretypes.h"
26 #include "tm.h"
27 #include "rtl.h"
28 #include "regs.h"
29 #include "hard-reg-set.h"
30 #include "insn-config.h"
31 #include "conditions.h"
32 #include "insn-attr.h"
33 #include "flags.h"
34 #include "recog.h"
35 #include "obstack.h"
36 #include "tree.h"
37 #include "expr.h"
38 #include "optabs.h"
39 #include "except.h"
40 #include "function.h"
41 #include "output.h"
42 #include "basic-block.h"
43 #include "integrate.h"
44 #include "diagnostic-core.h"
45 #include "toplev.h"
46 #include "ggc.h"
47 #include "hashtab.h"
48 #include "tm_p.h"
49 #include "target.h"
50 #include "target-def.h"
51 #include "langhooks.h"
52 #include "reload.h"
53 #include "cfglayout.h"
54 #include "sched-int.h"
55 #include "gimple.h"
56 #include "tree-flow.h"
57 #include "intl.h"
58 #include "params.h"
59 #include "tm-constrs.h"
60 #if TARGET_XCOFF
61 #include "xcoffout.h" /* get declarations of xcoff_*_section_name */
62 #endif
63 #if TARGET_MACHO
64 #include "gstab.h" /* for N_SLINE */
65 #endif
66
67 #ifndef TARGET_NO_PROTOTYPE
68 #define TARGET_NO_PROTOTYPE 0
69 #endif
70
71 #define min(A,B) ((A) < (B) ? (A) : (B))
72 #define max(A,B) ((A) > (B) ? (A) : (B))
73
74 /* Structure used to define the rs6000 stack */
75 typedef 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 */
82 int push_p; /* true if we need to allocate stack space */
83 int calls_p; /* true if the function makes any calls */
84 int world_save_p; /* true if we're saving *everything*:
85 r13-r31, cr, f14-f31, vrsave, v20-v31 */
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 */
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) */
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 */
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;
110 HOST_WIDE_INT total_size; /* total bytes allocated for stack */
111 int spe_64bit_regs_used;
112 } rs6000_stack_t;
113
114 /* A C structure for machine-specific, per-function data.
115 This is added to the cfun structure. */
116 typedef struct GTY(()) machine_function
117 {
118 /* Some local-dynamic symbol. */
119 const char *some_ld_name;
120 /* Whether the instruction chain has been scanned already. */
121 int insn_chain_scanned_p;
122 /* Flags if __builtin_return_address (n) with n >= 1 was used. */
123 int ra_needs_full_frame;
124 /* Flags if __builtin_return_address (0) was used. */
125 int ra_need_lr;
126 /* Cache lr_save_p after expansion of builtin_eh_return. */
127 int lr_save_state;
128 /* Offset from virtual_stack_vars_rtx to the start of the ABI_V4
129 varargs save area. */
130 HOST_WIDE_INT varargs_save_offset;
131 /* Temporary stack slot to use for SDmode copies. This slot is
132 64-bits wide and is allocated early enough so that the offset
133 does not overflow the 16-bit load/store offset field. */
134 rtx sdmode_stack_slot;
135 } machine_function;
136
137 /* Target cpu type */
138
139 enum processor_type rs6000_cpu;
140 struct rs6000_cpu_select rs6000_select[3] =
141 {
142 /* switch name, tune arch */
143 { (const char *)0, "--with-cpu=", 1, 1 },
144 { (const char *)0, "-mcpu=", 1, 1 },
145 { (const char *)0, "-mtune=", 1, 0 },
146 };
147
148 /* Always emit branch hint bits. */
149 static GTY(()) bool rs6000_always_hint;
150
151 /* Schedule instructions for group formation. */
152 static GTY(()) bool rs6000_sched_groups;
153
154 /* Align branch targets. */
155 static GTY(()) bool rs6000_align_branch_targets;
156
157 /* Support for -msched-costly-dep option. */
158 const char *rs6000_sched_costly_dep_str;
159 enum rs6000_dependence_cost rs6000_sched_costly_dep;
160
161 /* Support for -minsert-sched-nops option. */
162 const char *rs6000_sched_insert_nops_str;
163 enum rs6000_nop_insertion rs6000_sched_insert_nops;
164
165 /* Support targetm.vectorize.builtin_mask_for_load. */
166 static GTY(()) tree altivec_builtin_mask_for_load;
167
168 /* Size of long double. */
169 int rs6000_long_double_type_size;
170
171 /* IEEE quad extended precision long double. */
172 int rs6000_ieeequad;
173
174 /* Nonzero to use AltiVec ABI. */
175 int rs6000_altivec_abi;
176
177 /* Nonzero if we want SPE SIMD instructions. */
178 int rs6000_spe;
179
180 /* Nonzero if we want SPE ABI extensions. */
181 int rs6000_spe_abi;
182
183 /* Nonzero if floating point operations are done in the GPRs. */
184 int rs6000_float_gprs = 0;
185
186 /* Nonzero if we want Darwin's struct-by-value-in-regs ABI. */
187 int rs6000_darwin64_abi;
188
189 /* Set to nonzero once AIX common-mode calls have been defined. */
190 static GTY(()) int common_mode_defined;
191
192 /* Label number of label created for -mrelocatable, to call to so we can
193 get the address of the GOT section */
194 int rs6000_pic_labelno;
195
196 #ifdef USING_ELFOS_H
197 /* Which abi to adhere to */
198 const char *rs6000_abi_name;
199
200 /* Semantics of the small data area */
201 enum rs6000_sdata_type rs6000_sdata = SDATA_DATA;
202
203 /* Which small data model to use */
204 const char *rs6000_sdata_name = (char *)0;
205
206 /* Counter for labels which are to be placed in .fixup. */
207 int fixuplabelno = 0;
208 #endif
209
210 /* Bit size of immediate TLS offsets and string from which it is decoded. */
211 int rs6000_tls_size = 32;
212 const char *rs6000_tls_size_string;
213
214 /* ABI enumeration available for subtarget to use. */
215 enum rs6000_abi rs6000_current_abi;
216
217 /* Whether to use variant of AIX ABI for PowerPC64 Linux. */
218 int dot_symbols;
219
220 /* Debug flags */
221 const char *rs6000_debug_name;
222 int rs6000_debug_stack; /* debug stack applications */
223 int rs6000_debug_arg; /* debug argument handling */
224 int rs6000_debug_reg; /* debug register classes */
225 int rs6000_debug_addr; /* debug memory addressing */
226 int rs6000_debug_cost; /* debug rtx_costs */
227
228 /* Specify the machine mode that pointers have. After generation of rtl, the
229 compiler makes no further distinction between pointers and any other objects
230 of this machine mode. The type is unsigned since not all things that
231 include rs6000.h also include machmode.h. */
232 unsigned rs6000_pmode;
233
234 /* Width in bits of a pointer. */
235 unsigned rs6000_pointer_size;
236
237
238 /* Value is TRUE if register/mode pair is acceptable. */
239 bool rs6000_hard_regno_mode_ok_p[NUM_MACHINE_MODES][FIRST_PSEUDO_REGISTER];
240
241 /* Maximum number of registers needed for a given register class and mode. */
242 unsigned char rs6000_class_max_nregs[NUM_MACHINE_MODES][LIM_REG_CLASSES];
243
244 /* How many registers are needed for a given register and mode. */
245 unsigned char rs6000_hard_regno_nregs[NUM_MACHINE_MODES][FIRST_PSEUDO_REGISTER];
246
247 /* Map register number to register class. */
248 enum reg_class rs6000_regno_regclass[FIRST_PSEUDO_REGISTER];
249
250 /* Reload functions based on the type and the vector unit. */
251 static enum insn_code rs6000_vector_reload[NUM_MACHINE_MODES][2];
252
253 /* Built in types. */
254 tree rs6000_builtin_types[RS6000_BTI_MAX];
255 tree rs6000_builtin_decls[RS6000_BUILTIN_COUNT];
256
257 const char *rs6000_traceback_name;
258 static enum {
259 traceback_default = 0,
260 traceback_none,
261 traceback_part,
262 traceback_full
263 } rs6000_traceback;
264
265 /* Flag to say the TOC is initialized */
266 int toc_initialized;
267 char toc_label_name[10];
268
269 /* Cached value of rs6000_variable_issue. This is cached in
270 rs6000_variable_issue hook and returned from rs6000_sched_reorder2. */
271 static short cached_can_issue_more;
272
273 static GTY(()) section *read_only_data_section;
274 static GTY(()) section *private_data_section;
275 static GTY(()) section *read_only_private_data_section;
276 static GTY(()) section *sdata2_section;
277 static GTY(()) section *toc_section;
278
279 /* Control alignment for fields within structures. */
280 /* String from -malign-XXXXX. */
281 int rs6000_alignment_flags;
282
283 /* Code model for 64-bit linux. */
284 enum rs6000_cmodel cmodel;
285
286 /* True for any options that were explicitly set. */
287 static struct {
288 bool aix_struct_ret; /* True if -maix-struct-ret was used. */
289 bool alignment; /* True if -malign- was used. */
290 bool spe_abi; /* True if -mabi=spe/no-spe was used. */
291 bool altivec_abi; /* True if -mabi=altivec/no-altivec used. */
292 bool spe; /* True if -mspe= was used. */
293 bool float_gprs; /* True if -mfloat-gprs= was used. */
294 bool long_double; /* True if -mlong-double- was used. */
295 bool ieee; /* True if -mabi=ieee/ibmlongdouble used. */
296 bool vrsave; /* True if -mvrsave was used. */
297 bool cmodel; /* True if -mcmodel was used. */
298 } rs6000_explicit_options;
299
300 struct builtin_description
301 {
302 /* mask is not const because we're going to alter it below. This
303 nonsense will go away when we rewrite the -march infrastructure
304 to give us more target flag bits. */
305 unsigned int mask;
306 const enum insn_code icode;
307 const char *const name;
308 const enum rs6000_builtins code;
309 };
310
311 /* Describe the vector unit used for modes. */
312 enum rs6000_vector rs6000_vector_unit[NUM_MACHINE_MODES];
313 enum rs6000_vector rs6000_vector_mem[NUM_MACHINE_MODES];
314
315 /* Register classes for various constraints that are based on the target
316 switches. */
317 enum reg_class rs6000_constraints[RS6000_CONSTRAINT_MAX];
318
319 /* Describe the alignment of a vector. */
320 int rs6000_vector_align[NUM_MACHINE_MODES];
321
322 /* Map selected modes to types for builtins. */
323 static GTY(()) tree builtin_mode_to_type[MAX_MACHINE_MODE][2];
324
325 /* What modes to automatically generate reciprocal divide estimate (fre) and
326 reciprocal sqrt (frsqrte) for. */
327 unsigned char rs6000_recip_bits[MAX_MACHINE_MODE];
328
329 /* Masks to determine which reciprocal esitmate instructions to generate
330 automatically. */
331 enum rs6000_recip_mask {
332 RECIP_SF_DIV = 0x001, /* Use divide estimate */
333 RECIP_DF_DIV = 0x002,
334 RECIP_V4SF_DIV = 0x004,
335 RECIP_V2DF_DIV = 0x008,
336
337 RECIP_SF_RSQRT = 0x010, /* Use reciprocal sqrt estimate. */
338 RECIP_DF_RSQRT = 0x020,
339 RECIP_V4SF_RSQRT = 0x040,
340 RECIP_V2DF_RSQRT = 0x080,
341
342 /* Various combination of flags for -mrecip=xxx. */
343 RECIP_NONE = 0,
344 RECIP_ALL = (RECIP_SF_DIV | RECIP_DF_DIV | RECIP_V4SF_DIV
345 | RECIP_V2DF_DIV | RECIP_SF_RSQRT | RECIP_DF_RSQRT
346 | RECIP_V4SF_RSQRT | RECIP_V2DF_RSQRT),
347
348 RECIP_HIGH_PRECISION = RECIP_ALL,
349
350 /* On low precision machines like the power5, don't enable double precision
351 reciprocal square root estimate, since it isn't accurate enough. */
352 RECIP_LOW_PRECISION = (RECIP_ALL & ~(RECIP_DF_RSQRT | RECIP_V2DF_RSQRT))
353 };
354
355 static unsigned int rs6000_recip_control;
356 static const char *rs6000_recip_name;
357
358 /* -mrecip options. */
359 static struct
360 {
361 const char *string; /* option name */
362 unsigned int mask; /* mask bits to set */
363 } recip_options[] = {
364 { "all", RECIP_ALL },
365 { "none", RECIP_NONE },
366 { "div", (RECIP_SF_DIV | RECIP_DF_DIV | RECIP_V4SF_DIV
367 | RECIP_V2DF_DIV) },
368 { "divf", (RECIP_SF_DIV | RECIP_V4SF_DIV) },
369 { "divd", (RECIP_DF_DIV | RECIP_V2DF_DIV) },
370 { "rsqrt", (RECIP_SF_RSQRT | RECIP_DF_RSQRT | RECIP_V4SF_RSQRT
371 | RECIP_V2DF_RSQRT) },
372 { "rsqrtf", (RECIP_SF_RSQRT | RECIP_V4SF_RSQRT) },
373 { "rsqrtd", (RECIP_DF_RSQRT | RECIP_V2DF_RSQRT) },
374 };
375
376 /* 2 argument gen function typedef. */
377 typedef rtx (*gen_2arg_fn_t) (rtx, rtx, rtx);
378
379 \f
380 /* Target cpu costs. */
381
382 struct processor_costs {
383 const int mulsi; /* cost of SImode multiplication. */
384 const int mulsi_const; /* cost of SImode multiplication by constant. */
385 const int mulsi_const9; /* cost of SImode mult by short constant. */
386 const int muldi; /* cost of DImode multiplication. */
387 const int divsi; /* cost of SImode division. */
388 const int divdi; /* cost of DImode division. */
389 const int fp; /* cost of simple SFmode and DFmode insns. */
390 const int dmul; /* cost of DFmode multiplication (and fmadd). */
391 const int sdiv; /* cost of SFmode division (fdivs). */
392 const int ddiv; /* cost of DFmode division (fdiv). */
393 const int cache_line_size; /* cache line size in bytes. */
394 const int l1_cache_size; /* size of l1 cache, in kilobytes. */
395 const int l2_cache_size; /* size of l2 cache, in kilobytes. */
396 const int simultaneous_prefetches; /* number of parallel prefetch
397 operations. */
398 };
399
400 const struct processor_costs *rs6000_cost;
401
402 /* Processor costs (relative to an add) */
403
404 /* Instruction size costs on 32bit processors. */
405 static const
406 struct processor_costs size32_cost = {
407 COSTS_N_INSNS (1), /* mulsi */
408 COSTS_N_INSNS (1), /* mulsi_const */
409 COSTS_N_INSNS (1), /* mulsi_const9 */
410 COSTS_N_INSNS (1), /* muldi */
411 COSTS_N_INSNS (1), /* divsi */
412 COSTS_N_INSNS (1), /* divdi */
413 COSTS_N_INSNS (1), /* fp */
414 COSTS_N_INSNS (1), /* dmul */
415 COSTS_N_INSNS (1), /* sdiv */
416 COSTS_N_INSNS (1), /* ddiv */
417 32,
418 0,
419 0,
420 0,
421 };
422
423 /* Instruction size costs on 64bit processors. */
424 static const
425 struct processor_costs size64_cost = {
426 COSTS_N_INSNS (1), /* mulsi */
427 COSTS_N_INSNS (1), /* mulsi_const */
428 COSTS_N_INSNS (1), /* mulsi_const9 */
429 COSTS_N_INSNS (1), /* muldi */
430 COSTS_N_INSNS (1), /* divsi */
431 COSTS_N_INSNS (1), /* divdi */
432 COSTS_N_INSNS (1), /* fp */
433 COSTS_N_INSNS (1), /* dmul */
434 COSTS_N_INSNS (1), /* sdiv */
435 COSTS_N_INSNS (1), /* ddiv */
436 128,
437 0,
438 0,
439 0,
440 };
441
442 /* Instruction costs on RIOS1 processors. */
443 static const
444 struct processor_costs rios1_cost = {
445 COSTS_N_INSNS (5), /* mulsi */
446 COSTS_N_INSNS (4), /* mulsi_const */
447 COSTS_N_INSNS (3), /* mulsi_const9 */
448 COSTS_N_INSNS (5), /* muldi */
449 COSTS_N_INSNS (19), /* divsi */
450 COSTS_N_INSNS (19), /* divdi */
451 COSTS_N_INSNS (2), /* fp */
452 COSTS_N_INSNS (2), /* dmul */
453 COSTS_N_INSNS (19), /* sdiv */
454 COSTS_N_INSNS (19), /* ddiv */
455 128, /* cache line size */
456 64, /* l1 cache */
457 512, /* l2 cache */
458 0, /* streams */
459 };
460
461 /* Instruction costs on RIOS2 processors. */
462 static const
463 struct processor_costs rios2_cost = {
464 COSTS_N_INSNS (2), /* mulsi */
465 COSTS_N_INSNS (2), /* mulsi_const */
466 COSTS_N_INSNS (2), /* mulsi_const9 */
467 COSTS_N_INSNS (2), /* muldi */
468 COSTS_N_INSNS (13), /* divsi */
469 COSTS_N_INSNS (13), /* divdi */
470 COSTS_N_INSNS (2), /* fp */
471 COSTS_N_INSNS (2), /* dmul */
472 COSTS_N_INSNS (17), /* sdiv */
473 COSTS_N_INSNS (17), /* ddiv */
474 256, /* cache line size */
475 256, /* l1 cache */
476 1024, /* l2 cache */
477 0, /* streams */
478 };
479
480 /* Instruction costs on RS64A processors. */
481 static const
482 struct processor_costs rs64a_cost = {
483 COSTS_N_INSNS (20), /* mulsi */
484 COSTS_N_INSNS (12), /* mulsi_const */
485 COSTS_N_INSNS (8), /* mulsi_const9 */
486 COSTS_N_INSNS (34), /* muldi */
487 COSTS_N_INSNS (65), /* divsi */
488 COSTS_N_INSNS (67), /* divdi */
489 COSTS_N_INSNS (4), /* fp */
490 COSTS_N_INSNS (4), /* dmul */
491 COSTS_N_INSNS (31), /* sdiv */
492 COSTS_N_INSNS (31), /* ddiv */
493 128, /* cache line size */
494 128, /* l1 cache */
495 2048, /* l2 cache */
496 1, /* streams */
497 };
498
499 /* Instruction costs on MPCCORE processors. */
500 static const
501 struct processor_costs mpccore_cost = {
502 COSTS_N_INSNS (2), /* mulsi */
503 COSTS_N_INSNS (2), /* mulsi_const */
504 COSTS_N_INSNS (2), /* mulsi_const9 */
505 COSTS_N_INSNS (2), /* muldi */
506 COSTS_N_INSNS (6), /* divsi */
507 COSTS_N_INSNS (6), /* divdi */
508 COSTS_N_INSNS (4), /* fp */
509 COSTS_N_INSNS (5), /* dmul */
510 COSTS_N_INSNS (10), /* sdiv */
511 COSTS_N_INSNS (17), /* ddiv */
512 32, /* cache line size */
513 4, /* l1 cache */
514 16, /* l2 cache */
515 1, /* streams */
516 };
517
518 /* Instruction costs on PPC403 processors. */
519 static const
520 struct processor_costs ppc403_cost = {
521 COSTS_N_INSNS (4), /* mulsi */
522 COSTS_N_INSNS (4), /* mulsi_const */
523 COSTS_N_INSNS (4), /* mulsi_const9 */
524 COSTS_N_INSNS (4), /* muldi */
525 COSTS_N_INSNS (33), /* divsi */
526 COSTS_N_INSNS (33), /* divdi */
527 COSTS_N_INSNS (11), /* fp */
528 COSTS_N_INSNS (11), /* dmul */
529 COSTS_N_INSNS (11), /* sdiv */
530 COSTS_N_INSNS (11), /* ddiv */
531 32, /* cache line size */
532 4, /* l1 cache */
533 16, /* l2 cache */
534 1, /* streams */
535 };
536
537 /* Instruction costs on PPC405 processors. */
538 static const
539 struct processor_costs ppc405_cost = {
540 COSTS_N_INSNS (5), /* mulsi */
541 COSTS_N_INSNS (4), /* mulsi_const */
542 COSTS_N_INSNS (3), /* mulsi_const9 */
543 COSTS_N_INSNS (5), /* muldi */
544 COSTS_N_INSNS (35), /* divsi */
545 COSTS_N_INSNS (35), /* divdi */
546 COSTS_N_INSNS (11), /* fp */
547 COSTS_N_INSNS (11), /* dmul */
548 COSTS_N_INSNS (11), /* sdiv */
549 COSTS_N_INSNS (11), /* ddiv */
550 32, /* cache line size */
551 16, /* l1 cache */
552 128, /* l2 cache */
553 1, /* streams */
554 };
555
556 /* Instruction costs on PPC440 processors. */
557 static const
558 struct processor_costs ppc440_cost = {
559 COSTS_N_INSNS (3), /* mulsi */
560 COSTS_N_INSNS (2), /* mulsi_const */
561 COSTS_N_INSNS (2), /* mulsi_const9 */
562 COSTS_N_INSNS (3), /* muldi */
563 COSTS_N_INSNS (34), /* divsi */
564 COSTS_N_INSNS (34), /* divdi */
565 COSTS_N_INSNS (5), /* fp */
566 COSTS_N_INSNS (5), /* dmul */
567 COSTS_N_INSNS (19), /* sdiv */
568 COSTS_N_INSNS (33), /* ddiv */
569 32, /* cache line size */
570 32, /* l1 cache */
571 256, /* l2 cache */
572 1, /* streams */
573 };
574
575 /* Instruction costs on PPC476 processors. */
576 static const
577 struct processor_costs ppc476_cost = {
578 COSTS_N_INSNS (4), /* mulsi */
579 COSTS_N_INSNS (4), /* mulsi_const */
580 COSTS_N_INSNS (4), /* mulsi_const9 */
581 COSTS_N_INSNS (4), /* muldi */
582 COSTS_N_INSNS (11), /* divsi */
583 COSTS_N_INSNS (11), /* divdi */
584 COSTS_N_INSNS (6), /* fp */
585 COSTS_N_INSNS (6), /* dmul */
586 COSTS_N_INSNS (19), /* sdiv */
587 COSTS_N_INSNS (33), /* ddiv */
588 32, /* l1 cache line size */
589 32, /* l1 cache */
590 512, /* l2 cache */
591 1, /* streams */
592 };
593
594 /* Instruction costs on PPC601 processors. */
595 static const
596 struct processor_costs ppc601_cost = {
597 COSTS_N_INSNS (5), /* mulsi */
598 COSTS_N_INSNS (5), /* mulsi_const */
599 COSTS_N_INSNS (5), /* mulsi_const9 */
600 COSTS_N_INSNS (5), /* muldi */
601 COSTS_N_INSNS (36), /* divsi */
602 COSTS_N_INSNS (36), /* divdi */
603 COSTS_N_INSNS (4), /* fp */
604 COSTS_N_INSNS (5), /* dmul */
605 COSTS_N_INSNS (17), /* sdiv */
606 COSTS_N_INSNS (31), /* ddiv */
607 32, /* cache line size */
608 32, /* l1 cache */
609 256, /* l2 cache */
610 1, /* streams */
611 };
612
613 /* Instruction costs on PPC603 processors. */
614 static const
615 struct processor_costs ppc603_cost = {
616 COSTS_N_INSNS (5), /* mulsi */
617 COSTS_N_INSNS (3), /* mulsi_const */
618 COSTS_N_INSNS (2), /* mulsi_const9 */
619 COSTS_N_INSNS (5), /* muldi */
620 COSTS_N_INSNS (37), /* divsi */
621 COSTS_N_INSNS (37), /* divdi */
622 COSTS_N_INSNS (3), /* fp */
623 COSTS_N_INSNS (4), /* dmul */
624 COSTS_N_INSNS (18), /* sdiv */
625 COSTS_N_INSNS (33), /* ddiv */
626 32, /* cache line size */
627 8, /* l1 cache */
628 64, /* l2 cache */
629 1, /* streams */
630 };
631
632 /* Instruction costs on PPC604 processors. */
633 static const
634 struct processor_costs ppc604_cost = {
635 COSTS_N_INSNS (4), /* mulsi */
636 COSTS_N_INSNS (4), /* mulsi_const */
637 COSTS_N_INSNS (4), /* mulsi_const9 */
638 COSTS_N_INSNS (4), /* muldi */
639 COSTS_N_INSNS (20), /* divsi */
640 COSTS_N_INSNS (20), /* divdi */
641 COSTS_N_INSNS (3), /* fp */
642 COSTS_N_INSNS (3), /* dmul */
643 COSTS_N_INSNS (18), /* sdiv */
644 COSTS_N_INSNS (32), /* ddiv */
645 32, /* cache line size */
646 16, /* l1 cache */
647 512, /* l2 cache */
648 1, /* streams */
649 };
650
651 /* Instruction costs on PPC604e processors. */
652 static const
653 struct processor_costs ppc604e_cost = {
654 COSTS_N_INSNS (2), /* mulsi */
655 COSTS_N_INSNS (2), /* mulsi_const */
656 COSTS_N_INSNS (2), /* mulsi_const9 */
657 COSTS_N_INSNS (2), /* muldi */
658 COSTS_N_INSNS (20), /* divsi */
659 COSTS_N_INSNS (20), /* divdi */
660 COSTS_N_INSNS (3), /* fp */
661 COSTS_N_INSNS (3), /* dmul */
662 COSTS_N_INSNS (18), /* sdiv */
663 COSTS_N_INSNS (32), /* ddiv */
664 32, /* cache line size */
665 32, /* l1 cache */
666 1024, /* l2 cache */
667 1, /* streams */
668 };
669
670 /* Instruction costs on PPC620 processors. */
671 static const
672 struct processor_costs ppc620_cost = {
673 COSTS_N_INSNS (5), /* mulsi */
674 COSTS_N_INSNS (4), /* mulsi_const */
675 COSTS_N_INSNS (3), /* mulsi_const9 */
676 COSTS_N_INSNS (7), /* muldi */
677 COSTS_N_INSNS (21), /* divsi */
678 COSTS_N_INSNS (37), /* divdi */
679 COSTS_N_INSNS (3), /* fp */
680 COSTS_N_INSNS (3), /* dmul */
681 COSTS_N_INSNS (18), /* sdiv */
682 COSTS_N_INSNS (32), /* ddiv */
683 128, /* cache line size */
684 32, /* l1 cache */
685 1024, /* l2 cache */
686 1, /* streams */
687 };
688
689 /* Instruction costs on PPC630 processors. */
690 static const
691 struct processor_costs ppc630_cost = {
692 COSTS_N_INSNS (5), /* mulsi */
693 COSTS_N_INSNS (4), /* mulsi_const */
694 COSTS_N_INSNS (3), /* mulsi_const9 */
695 COSTS_N_INSNS (7), /* muldi */
696 COSTS_N_INSNS (21), /* divsi */
697 COSTS_N_INSNS (37), /* divdi */
698 COSTS_N_INSNS (3), /* fp */
699 COSTS_N_INSNS (3), /* dmul */
700 COSTS_N_INSNS (17), /* sdiv */
701 COSTS_N_INSNS (21), /* ddiv */
702 128, /* cache line size */
703 64, /* l1 cache */
704 1024, /* l2 cache */
705 1, /* streams */
706 };
707
708 /* Instruction costs on Cell processor. */
709 /* COSTS_N_INSNS (1) ~ one add. */
710 static const
711 struct processor_costs ppccell_cost = {
712 COSTS_N_INSNS (9/2)+2, /* mulsi */
713 COSTS_N_INSNS (6/2), /* mulsi_const */
714 COSTS_N_INSNS (6/2), /* mulsi_const9 */
715 COSTS_N_INSNS (15/2)+2, /* muldi */
716 COSTS_N_INSNS (38/2), /* divsi */
717 COSTS_N_INSNS (70/2), /* divdi */
718 COSTS_N_INSNS (10/2), /* fp */
719 COSTS_N_INSNS (10/2), /* dmul */
720 COSTS_N_INSNS (74/2), /* sdiv */
721 COSTS_N_INSNS (74/2), /* ddiv */
722 128, /* cache line size */
723 32, /* l1 cache */
724 512, /* l2 cache */
725 6, /* streams */
726 };
727
728 /* Instruction costs on PPC750 and PPC7400 processors. */
729 static const
730 struct processor_costs ppc750_cost = {
731 COSTS_N_INSNS (5), /* mulsi */
732 COSTS_N_INSNS (3), /* mulsi_const */
733 COSTS_N_INSNS (2), /* mulsi_const9 */
734 COSTS_N_INSNS (5), /* muldi */
735 COSTS_N_INSNS (17), /* divsi */
736 COSTS_N_INSNS (17), /* divdi */
737 COSTS_N_INSNS (3), /* fp */
738 COSTS_N_INSNS (3), /* dmul */
739 COSTS_N_INSNS (17), /* sdiv */
740 COSTS_N_INSNS (31), /* ddiv */
741 32, /* cache line size */
742 32, /* l1 cache */
743 512, /* l2 cache */
744 1, /* streams */
745 };
746
747 /* Instruction costs on PPC7450 processors. */
748 static const
749 struct processor_costs ppc7450_cost = {
750 COSTS_N_INSNS (4), /* mulsi */
751 COSTS_N_INSNS (3), /* mulsi_const */
752 COSTS_N_INSNS (3), /* mulsi_const9 */
753 COSTS_N_INSNS (4), /* muldi */
754 COSTS_N_INSNS (23), /* divsi */
755 COSTS_N_INSNS (23), /* divdi */
756 COSTS_N_INSNS (5), /* fp */
757 COSTS_N_INSNS (5), /* dmul */
758 COSTS_N_INSNS (21), /* sdiv */
759 COSTS_N_INSNS (35), /* ddiv */
760 32, /* cache line size */
761 32, /* l1 cache */
762 1024, /* l2 cache */
763 1, /* streams */
764 };
765
766 /* Instruction costs on PPC8540 processors. */
767 static const
768 struct processor_costs ppc8540_cost = {
769 COSTS_N_INSNS (4), /* mulsi */
770 COSTS_N_INSNS (4), /* mulsi_const */
771 COSTS_N_INSNS (4), /* mulsi_const9 */
772 COSTS_N_INSNS (4), /* muldi */
773 COSTS_N_INSNS (19), /* divsi */
774 COSTS_N_INSNS (19), /* divdi */
775 COSTS_N_INSNS (4), /* fp */
776 COSTS_N_INSNS (4), /* dmul */
777 COSTS_N_INSNS (29), /* sdiv */
778 COSTS_N_INSNS (29), /* ddiv */
779 32, /* cache line size */
780 32, /* l1 cache */
781 256, /* l2 cache */
782 1, /* prefetch streams /*/
783 };
784
785 /* Instruction costs on E300C2 and E300C3 cores. */
786 static const
787 struct processor_costs ppce300c2c3_cost = {
788 COSTS_N_INSNS (4), /* mulsi */
789 COSTS_N_INSNS (4), /* mulsi_const */
790 COSTS_N_INSNS (4), /* mulsi_const9 */
791 COSTS_N_INSNS (4), /* muldi */
792 COSTS_N_INSNS (19), /* divsi */
793 COSTS_N_INSNS (19), /* divdi */
794 COSTS_N_INSNS (3), /* fp */
795 COSTS_N_INSNS (4), /* dmul */
796 COSTS_N_INSNS (18), /* sdiv */
797 COSTS_N_INSNS (33), /* ddiv */
798 32,
799 16, /* l1 cache */
800 16, /* l2 cache */
801 1, /* prefetch streams /*/
802 };
803
804 /* Instruction costs on PPCE500MC processors. */
805 static const
806 struct processor_costs ppce500mc_cost = {
807 COSTS_N_INSNS (4), /* mulsi */
808 COSTS_N_INSNS (4), /* mulsi_const */
809 COSTS_N_INSNS (4), /* mulsi_const9 */
810 COSTS_N_INSNS (4), /* muldi */
811 COSTS_N_INSNS (14), /* divsi */
812 COSTS_N_INSNS (14), /* divdi */
813 COSTS_N_INSNS (8), /* fp */
814 COSTS_N_INSNS (10), /* dmul */
815 COSTS_N_INSNS (36), /* sdiv */
816 COSTS_N_INSNS (66), /* ddiv */
817 64, /* cache line size */
818 32, /* l1 cache */
819 128, /* l2 cache */
820 1, /* prefetch streams /*/
821 };
822
823 /* Instruction costs on PPCE500MC64 processors. */
824 static const
825 struct processor_costs ppce500mc64_cost = {
826 COSTS_N_INSNS (4), /* mulsi */
827 COSTS_N_INSNS (4), /* mulsi_const */
828 COSTS_N_INSNS (4), /* mulsi_const9 */
829 COSTS_N_INSNS (4), /* muldi */
830 COSTS_N_INSNS (14), /* divsi */
831 COSTS_N_INSNS (14), /* divdi */
832 COSTS_N_INSNS (4), /* fp */
833 COSTS_N_INSNS (10), /* dmul */
834 COSTS_N_INSNS (36), /* sdiv */
835 COSTS_N_INSNS (66), /* ddiv */
836 64, /* cache line size */
837 32, /* l1 cache */
838 128, /* l2 cache */
839 1, /* prefetch streams /*/
840 };
841
842 /* Instruction costs on AppliedMicro Titan processors. */
843 static const
844 struct processor_costs titan_cost = {
845 COSTS_N_INSNS (5), /* mulsi */
846 COSTS_N_INSNS (5), /* mulsi_const */
847 COSTS_N_INSNS (5), /* mulsi_const9 */
848 COSTS_N_INSNS (5), /* muldi */
849 COSTS_N_INSNS (18), /* divsi */
850 COSTS_N_INSNS (18), /* divdi */
851 COSTS_N_INSNS (10), /* fp */
852 COSTS_N_INSNS (10), /* dmul */
853 COSTS_N_INSNS (46), /* sdiv */
854 COSTS_N_INSNS (72), /* ddiv */
855 32, /* cache line size */
856 32, /* l1 cache */
857 512, /* l2 cache */
858 1, /* prefetch streams /*/
859 };
860
861 /* Instruction costs on POWER4 and POWER5 processors. */
862 static const
863 struct processor_costs power4_cost = {
864 COSTS_N_INSNS (3), /* mulsi */
865 COSTS_N_INSNS (2), /* mulsi_const */
866 COSTS_N_INSNS (2), /* mulsi_const9 */
867 COSTS_N_INSNS (4), /* muldi */
868 COSTS_N_INSNS (18), /* divsi */
869 COSTS_N_INSNS (34), /* divdi */
870 COSTS_N_INSNS (3), /* fp */
871 COSTS_N_INSNS (3), /* dmul */
872 COSTS_N_INSNS (17), /* sdiv */
873 COSTS_N_INSNS (17), /* ddiv */
874 128, /* cache line size */
875 32, /* l1 cache */
876 1024, /* l2 cache */
877 8, /* prefetch streams /*/
878 };
879
880 /* Instruction costs on POWER6 processors. */
881 static const
882 struct processor_costs power6_cost = {
883 COSTS_N_INSNS (8), /* mulsi */
884 COSTS_N_INSNS (8), /* mulsi_const */
885 COSTS_N_INSNS (8), /* mulsi_const9 */
886 COSTS_N_INSNS (8), /* muldi */
887 COSTS_N_INSNS (22), /* divsi */
888 COSTS_N_INSNS (28), /* divdi */
889 COSTS_N_INSNS (3), /* fp */
890 COSTS_N_INSNS (3), /* dmul */
891 COSTS_N_INSNS (13), /* sdiv */
892 COSTS_N_INSNS (16), /* ddiv */
893 128, /* cache line size */
894 64, /* l1 cache */
895 2048, /* l2 cache */
896 16, /* prefetch streams */
897 };
898
899 /* Instruction costs on POWER7 processors. */
900 static const
901 struct processor_costs power7_cost = {
902 COSTS_N_INSNS (2), /* mulsi */
903 COSTS_N_INSNS (2), /* mulsi_const */
904 COSTS_N_INSNS (2), /* mulsi_const9 */
905 COSTS_N_INSNS (2), /* muldi */
906 COSTS_N_INSNS (18), /* divsi */
907 COSTS_N_INSNS (34), /* divdi */
908 COSTS_N_INSNS (3), /* fp */
909 COSTS_N_INSNS (3), /* dmul */
910 COSTS_N_INSNS (13), /* sdiv */
911 COSTS_N_INSNS (16), /* ddiv */
912 128, /* cache line size */
913 32, /* l1 cache */
914 256, /* l2 cache */
915 12, /* prefetch streams */
916 };
917
918 /* Instruction costs on POWER A2 processors. */
919 static const
920 struct processor_costs ppca2_cost = {
921 COSTS_N_INSNS (16), /* mulsi */
922 COSTS_N_INSNS (16), /* mulsi_const */
923 COSTS_N_INSNS (16), /* mulsi_const9 */
924 COSTS_N_INSNS (16), /* muldi */
925 COSTS_N_INSNS (22), /* divsi */
926 COSTS_N_INSNS (28), /* divdi */
927 COSTS_N_INSNS (3), /* fp */
928 COSTS_N_INSNS (3), /* dmul */
929 COSTS_N_INSNS (59), /* sdiv */
930 COSTS_N_INSNS (72), /* ddiv */
931 64,
932 16, /* l1 cache */
933 2048, /* l2 cache */
934 16, /* prefetch streams */
935 };
936
937 \f
938 /* Table that classifies rs6000 builtin functions (pure, const, etc.). */
939 #undef RS6000_BUILTIN
940 #undef RS6000_BUILTIN_EQUATE
941 #define RS6000_BUILTIN(NAME, TYPE) TYPE,
942 #define RS6000_BUILTIN_EQUATE(NAME, VALUE)
943
944 static const enum rs6000_btc builtin_classify[(int)RS6000_BUILTIN_COUNT] =
945 {
946 #include "rs6000-builtin.def"
947 };
948
949 #undef RS6000_BUILTIN
950 #undef RS6000_BUILTIN_EQUATE
951
952 /* Support for -mveclibabi=<xxx> to control which vector library to use. */
953 static tree (*rs6000_veclib_handler) (tree, tree, tree);
954
955 \f
956 static bool rs6000_function_ok_for_sibcall (tree, tree);
957 static const char *rs6000_invalid_within_doloop (const_rtx);
958 static bool rs6000_legitimate_address_p (enum machine_mode, rtx, bool);
959 static bool rs6000_debug_legitimate_address_p (enum machine_mode, rtx, bool);
960 static rtx rs6000_generate_compare (rtx, enum machine_mode);
961 static void rs6000_emit_stack_tie (void);
962 static void rs6000_frame_related (rtx, rtx, HOST_WIDE_INT, rtx, rtx);
963 static bool spe_func_has_64bit_regs_p (void);
964 static void emit_frame_save (rtx, rtx, enum machine_mode, unsigned int,
965 int, HOST_WIDE_INT);
966 static rtx gen_frame_mem_offset (enum machine_mode, rtx, int);
967 static unsigned rs6000_hash_constant (rtx);
968 static unsigned toc_hash_function (const void *);
969 static int toc_hash_eq (const void *, const void *);
970 static bool reg_offset_addressing_ok_p (enum machine_mode);
971 static bool virtual_stack_registers_memory_p (rtx);
972 static bool constant_pool_expr_p (rtx);
973 static bool legitimate_small_data_p (enum machine_mode, rtx);
974 static bool legitimate_lo_sum_address_p (enum machine_mode, rtx, int);
975 static struct machine_function * rs6000_init_machine_status (void);
976 static bool rs6000_assemble_integer (rtx, unsigned int, int);
977 static bool no_global_regs_above (int, bool);
978 #ifdef HAVE_GAS_HIDDEN
979 static void rs6000_assemble_visibility (tree, int);
980 #endif
981 static int rs6000_ra_ever_killed (void);
982 static bool rs6000_attribute_takes_identifier_p (const_tree);
983 static tree rs6000_handle_longcall_attribute (tree *, tree, tree, int, bool *);
984 static tree rs6000_handle_altivec_attribute (tree *, tree, tree, int, bool *);
985 static bool rs6000_ms_bitfield_layout_p (const_tree);
986 static tree rs6000_handle_struct_attribute (tree *, tree, tree, int, bool *);
987 static void rs6000_eliminate_indexed_memrefs (rtx operands[2]);
988 static const char *rs6000_mangle_type (const_tree);
989 static void rs6000_set_default_type_attributes (tree);
990 static rtx rs6000_savres_routine_sym (rs6000_stack_t *, bool, bool, bool);
991 static rtx rs6000_emit_stack_reset (rs6000_stack_t *, rtx, rtx, int, bool);
992 static rtx rs6000_make_savres_rtx (rs6000_stack_t *, rtx, int,
993 enum machine_mode, bool, bool, bool);
994 static bool rs6000_reg_live_or_pic_offset_p (int);
995 static tree rs6000_builtin_vectorized_libmass (tree, tree, tree);
996 static tree rs6000_builtin_vectorized_function (tree, tree, tree);
997 static int rs6000_savres_strategy (rs6000_stack_t *, bool, int, int);
998 static void rs6000_restore_saved_cr (rtx, int);
999 static void rs6000_output_function_prologue (FILE *, HOST_WIDE_INT);
1000 static void rs6000_output_function_epilogue (FILE *, HOST_WIDE_INT);
1001 static void rs6000_output_mi_thunk (FILE *, tree, HOST_WIDE_INT, HOST_WIDE_INT,
1002 tree);
1003 static rtx rs6000_emit_set_long_const (rtx, HOST_WIDE_INT, HOST_WIDE_INT);
1004 static bool rs6000_return_in_memory (const_tree, const_tree);
1005 static rtx rs6000_function_value (const_tree, const_tree, bool);
1006 static void rs6000_file_start (void);
1007 #if TARGET_ELF
1008 static int rs6000_elf_reloc_rw_mask (void);
1009 static void rs6000_elf_asm_out_constructor (rtx, int);
1010 static void rs6000_elf_asm_out_destructor (rtx, int);
1011 static void rs6000_elf_end_indicate_exec_stack (void) ATTRIBUTE_UNUSED;
1012 static void rs6000_elf_asm_init_sections (void);
1013 static section *rs6000_elf_select_rtx_section (enum machine_mode, rtx,
1014 unsigned HOST_WIDE_INT);
1015 static void rs6000_elf_encode_section_info (tree, rtx, int)
1016 ATTRIBUTE_UNUSED;
1017 #endif
1018 static bool rs6000_use_blocks_for_constant_p (enum machine_mode, const_rtx);
1019 static void rs6000_alloc_sdmode_stack_slot (void);
1020 static void rs6000_instantiate_decls (void);
1021 #if TARGET_XCOFF
1022 static void rs6000_xcoff_asm_output_anchor (rtx);
1023 static void rs6000_xcoff_asm_globalize_label (FILE *, const char *);
1024 static void rs6000_xcoff_asm_init_sections (void);
1025 static int rs6000_xcoff_reloc_rw_mask (void);
1026 static void rs6000_xcoff_asm_named_section (const char *, unsigned int, tree);
1027 static section *rs6000_xcoff_select_section (tree, int,
1028 unsigned HOST_WIDE_INT);
1029 static void rs6000_xcoff_unique_section (tree, int);
1030 static section *rs6000_xcoff_select_rtx_section
1031 (enum machine_mode, rtx, unsigned HOST_WIDE_INT);
1032 static const char * rs6000_xcoff_strip_name_encoding (const char *);
1033 static unsigned int rs6000_xcoff_section_type_flags (tree, const char *, int);
1034 static void rs6000_xcoff_file_start (void);
1035 static void rs6000_xcoff_file_end (void);
1036 #endif
1037 static int rs6000_variable_issue (FILE *, int, rtx, int);
1038 static int rs6000_register_move_cost (enum machine_mode,
1039 reg_class_t, reg_class_t);
1040 static int rs6000_memory_move_cost (enum machine_mode, reg_class_t, bool);
1041 static bool rs6000_rtx_costs (rtx, int, int, int *, bool);
1042 static bool rs6000_debug_rtx_costs (rtx, int, int, int *, bool);
1043 static int rs6000_debug_address_cost (rtx, bool);
1044 static int rs6000_adjust_cost (rtx, rtx, rtx, int);
1045 static int rs6000_debug_adjust_cost (rtx, rtx, rtx, int);
1046 static void rs6000_sched_init (FILE *, int, int);
1047 static bool is_microcoded_insn (rtx);
1048 static bool is_nonpipeline_insn (rtx);
1049 static bool is_cracked_insn (rtx);
1050 static bool is_branch_slot_insn (rtx);
1051 static bool is_load_insn (rtx);
1052 static rtx get_store_dest (rtx pat);
1053 static bool is_store_insn (rtx);
1054 static bool set_to_load_agen (rtx,rtx);
1055 static bool adjacent_mem_locations (rtx,rtx);
1056 static int rs6000_adjust_priority (rtx, int);
1057 static int rs6000_issue_rate (void);
1058 static bool rs6000_is_costly_dependence (dep_t, int, int);
1059 static rtx get_next_active_insn (rtx, rtx);
1060 static bool insn_terminates_group_p (rtx , enum group_termination);
1061 static bool insn_must_be_first_in_group (rtx);
1062 static bool insn_must_be_last_in_group (rtx);
1063 static bool is_costly_group (rtx *, rtx);
1064 static int force_new_group (int, FILE *, rtx *, rtx, bool *, int, int *);
1065 static int redefine_groups (FILE *, int, rtx, rtx);
1066 static int pad_groups (FILE *, int, rtx, rtx);
1067 static void rs6000_sched_finish (FILE *, int);
1068 static int rs6000_sched_reorder (FILE *, int, rtx *, int *, int);
1069 static int rs6000_sched_reorder2 (FILE *, int, rtx *, int *, int);
1070 static int rs6000_use_sched_lookahead (void);
1071 static int rs6000_use_sched_lookahead_guard (rtx);
1072 static void * rs6000_alloc_sched_context (void);
1073 static void rs6000_init_sched_context (void *, bool);
1074 static void rs6000_set_sched_context (void *);
1075 static void rs6000_free_sched_context (void *);
1076 static tree rs6000_builtin_reciprocal (unsigned int, bool, bool);
1077 static tree rs6000_builtin_mask_for_load (void);
1078 static tree rs6000_builtin_mul_widen_even (tree);
1079 static tree rs6000_builtin_mul_widen_odd (tree);
1080 static tree rs6000_builtin_conversion (unsigned int, tree, tree);
1081 static tree rs6000_builtin_vec_perm (tree, tree *);
1082 static bool rs6000_builtin_support_vector_misalignment (enum
1083 machine_mode,
1084 const_tree,
1085 int, bool);
1086 static int rs6000_builtin_vectorization_cost (enum vect_cost_for_stmt,
1087 tree, int);
1088
1089 static void def_builtin (int, const char *, tree, int);
1090 static bool rs6000_vector_alignment_reachable (const_tree, bool);
1091 static void rs6000_init_builtins (void);
1092 static tree rs6000_builtin_decl (unsigned, bool);
1093
1094 static rtx rs6000_expand_unop_builtin (enum insn_code, tree, rtx);
1095 static rtx rs6000_expand_binop_builtin (enum insn_code, tree, rtx);
1096 static rtx rs6000_expand_ternop_builtin (enum insn_code, tree, rtx);
1097 static rtx rs6000_expand_builtin (tree, rtx, rtx, enum machine_mode, int);
1098 static void altivec_init_builtins (void);
1099 static unsigned builtin_hash_function (const void *);
1100 static int builtin_hash_eq (const void *, const void *);
1101 static tree builtin_function_type (enum machine_mode, enum machine_mode,
1102 enum machine_mode, enum machine_mode,
1103 enum rs6000_builtins, const char *name);
1104 static void rs6000_common_init_builtins (void);
1105 static void rs6000_init_libfuncs (void);
1106
1107 static void paired_init_builtins (void);
1108 static rtx paired_expand_builtin (tree, rtx, bool *);
1109 static rtx paired_expand_lv_builtin (enum insn_code, tree, rtx);
1110 static rtx paired_expand_stv_builtin (enum insn_code, tree);
1111 static rtx paired_expand_predicate_builtin (enum insn_code, tree, rtx);
1112
1113 static void enable_mask_for_builtins (struct builtin_description *, int,
1114 enum rs6000_builtins,
1115 enum rs6000_builtins);
1116 static void spe_init_builtins (void);
1117 static rtx spe_expand_builtin (tree, rtx, bool *);
1118 static rtx spe_expand_stv_builtin (enum insn_code, tree);
1119 static rtx spe_expand_predicate_builtin (enum insn_code, tree, rtx);
1120 static rtx spe_expand_evsel_builtin (enum insn_code, tree, rtx);
1121 static int rs6000_emit_int_cmove (rtx, rtx, rtx, rtx);
1122 static rs6000_stack_t *rs6000_stack_info (void);
1123 static void debug_stack_info (rs6000_stack_t *);
1124
1125 static rtx altivec_expand_builtin (tree, rtx, bool *);
1126 static rtx altivec_expand_ld_builtin (tree, rtx, bool *);
1127 static rtx altivec_expand_st_builtin (tree, rtx, bool *);
1128 static rtx altivec_expand_dst_builtin (tree, rtx, bool *);
1129 static rtx altivec_expand_abs_builtin (enum insn_code, tree, rtx);
1130 static rtx altivec_expand_predicate_builtin (enum insn_code, tree, rtx);
1131 static rtx altivec_expand_stv_builtin (enum insn_code, tree);
1132 static rtx altivec_expand_vec_init_builtin (tree, tree, rtx);
1133 static rtx altivec_expand_vec_set_builtin (tree);
1134 static rtx altivec_expand_vec_ext_builtin (tree, rtx);
1135 static int get_element_number (tree, tree);
1136 static bool rs6000_handle_option (size_t, const char *, int);
1137 static void rs6000_parse_tls_size_option (void);
1138 static void rs6000_parse_yes_no_option (const char *, const char *, int *);
1139 static int first_altivec_reg_to_save (void);
1140 static unsigned int compute_vrsave_mask (void);
1141 static void compute_save_world_info (rs6000_stack_t *info_ptr);
1142 static void is_altivec_return_reg (rtx, void *);
1143 static rtx generate_set_vrsave (rtx, rs6000_stack_t *, int);
1144 int easy_vector_constant (rtx, enum machine_mode);
1145 static rtx rs6000_dwarf_register_span (rtx);
1146 static void rs6000_init_dwarf_reg_sizes_extra (tree);
1147 static rtx rs6000_legitimize_address (rtx, rtx, enum machine_mode);
1148 static rtx rs6000_debug_legitimize_address (rtx, rtx, enum machine_mode);
1149 static rtx rs6000_legitimize_tls_address (rtx, enum tls_model);
1150 static void rs6000_output_dwarf_dtprel (FILE *, int, rtx) ATTRIBUTE_UNUSED;
1151 static rtx rs6000_delegitimize_address (rtx);
1152 static rtx rs6000_tls_get_addr (void);
1153 static rtx rs6000_got_sym (void);
1154 static int rs6000_tls_symbol_ref_1 (rtx *, void *);
1155 static const char *rs6000_get_some_local_dynamic_name (void);
1156 static int rs6000_get_some_local_dynamic_name_1 (rtx *, void *);
1157 static rtx rs6000_complex_function_value (enum machine_mode);
1158 static rtx rs6000_spe_function_arg (const CUMULATIVE_ARGS *,
1159 enum machine_mode, const_tree);
1160 static void rs6000_darwin64_record_arg_advance_flush (CUMULATIVE_ARGS *,
1161 HOST_WIDE_INT, int);
1162 static void rs6000_darwin64_record_arg_advance_recurse (CUMULATIVE_ARGS *,
1163 const_tree,
1164 HOST_WIDE_INT);
1165 static void rs6000_darwin64_record_arg_flush (CUMULATIVE_ARGS *,
1166 HOST_WIDE_INT,
1167 rtx[], int *);
1168 static void rs6000_darwin64_record_arg_recurse (CUMULATIVE_ARGS *,
1169 const_tree, HOST_WIDE_INT,
1170 rtx[], int *);
1171 static rtx rs6000_darwin64_record_arg (CUMULATIVE_ARGS *, const_tree, bool, bool);
1172 static rtx rs6000_mixed_function_arg (enum machine_mode, const_tree, int);
1173 static void rs6000_function_arg_advance (CUMULATIVE_ARGS *, enum machine_mode,
1174 const_tree, bool);
1175 static rtx rs6000_function_arg (CUMULATIVE_ARGS *, enum machine_mode,
1176 const_tree, bool);
1177 static void rs6000_move_block_from_reg (int regno, rtx x, int nregs);
1178 static void setup_incoming_varargs (CUMULATIVE_ARGS *,
1179 enum machine_mode, tree,
1180 int *, int);
1181 static bool rs6000_pass_by_reference (CUMULATIVE_ARGS *, enum machine_mode,
1182 const_tree, bool);
1183 static int rs6000_arg_partial_bytes (CUMULATIVE_ARGS *, enum machine_mode,
1184 tree, bool);
1185 static const char *invalid_arg_for_unprototyped_fn (const_tree, const_tree, const_tree);
1186 #if TARGET_MACHO
1187 static void macho_branch_islands (void);
1188 static int no_previous_def (tree function_name);
1189 static tree get_prev_label (tree function_name);
1190 static void rs6000_darwin_file_start (void);
1191 #endif
1192
1193 static tree rs6000_build_builtin_va_list (void);
1194 static void rs6000_va_start (tree, rtx);
1195 static tree rs6000_gimplify_va_arg (tree, tree, gimple_seq *, gimple_seq *);
1196 static bool rs6000_must_pass_in_stack (enum machine_mode, const_tree);
1197 static bool rs6000_scalar_mode_supported_p (enum machine_mode);
1198 static bool rs6000_vector_mode_supported_p (enum machine_mode);
1199 static rtx rs6000_emit_vector_compare_inner (enum rtx_code, rtx, rtx);
1200 static rtx rs6000_emit_vector_compare (enum rtx_code, rtx, rtx,
1201 enum machine_mode);
1202 static tree rs6000_stack_protect_fail (void);
1203
1204 static rtx rs6000_legitimize_reload_address (rtx, enum machine_mode, int, int,
1205 int, int *);
1206
1207 static rtx rs6000_debug_legitimize_reload_address (rtx, enum machine_mode, int,
1208 int, int, int *);
1209
1210 rtx (*rs6000_legitimize_reload_address_ptr) (rtx, enum machine_mode, int, int,
1211 int, int *)
1212 = rs6000_legitimize_reload_address;
1213
1214 static bool rs6000_mode_dependent_address_p (const_rtx);
1215 static bool rs6000_mode_dependent_address (const_rtx);
1216 static bool rs6000_debug_mode_dependent_address (const_rtx);
1217 static bool (*rs6000_mode_dependent_address_ptr) (const_rtx)
1218 = rs6000_mode_dependent_address;
1219
1220 static enum reg_class rs6000_secondary_reload_class (enum reg_class,
1221 enum machine_mode, rtx);
1222 static enum reg_class rs6000_debug_secondary_reload_class (enum reg_class,
1223 enum machine_mode,
1224 rtx);
1225 enum reg_class (*rs6000_secondary_reload_class_ptr) (enum reg_class,
1226 enum machine_mode, rtx)
1227 = rs6000_secondary_reload_class;
1228
1229 static enum reg_class rs6000_preferred_reload_class (rtx, enum reg_class);
1230 static enum reg_class rs6000_debug_preferred_reload_class (rtx,
1231 enum reg_class);
1232 enum reg_class (*rs6000_preferred_reload_class_ptr) (rtx, enum reg_class)
1233 = rs6000_preferred_reload_class;
1234
1235 static bool rs6000_secondary_memory_needed (enum reg_class, enum reg_class,
1236 enum machine_mode);
1237
1238 static bool rs6000_debug_secondary_memory_needed (enum reg_class,
1239 enum reg_class,
1240 enum machine_mode);
1241
1242 bool (*rs6000_secondary_memory_needed_ptr) (enum reg_class, enum reg_class,
1243 enum machine_mode)
1244 = rs6000_secondary_memory_needed;
1245
1246 static bool rs6000_cannot_change_mode_class (enum machine_mode,
1247 enum machine_mode,
1248 enum reg_class);
1249 static bool rs6000_debug_cannot_change_mode_class (enum machine_mode,
1250 enum machine_mode,
1251 enum reg_class);
1252
1253 bool (*rs6000_cannot_change_mode_class_ptr) (enum machine_mode,
1254 enum machine_mode,
1255 enum reg_class)
1256 = rs6000_cannot_change_mode_class;
1257
1258 static reg_class_t rs6000_secondary_reload (bool, rtx, reg_class_t,
1259 enum machine_mode,
1260 struct secondary_reload_info *);
1261
1262 static const reg_class_t *rs6000_ira_cover_classes (void);
1263
1264 const int INSN_NOT_AVAILABLE = -1;
1265 static enum machine_mode rs6000_eh_return_filter_mode (void);
1266 static bool rs6000_can_eliminate (const int, const int);
1267 static void rs6000_trampoline_init (rtx, tree, rtx);
1268
1269 /* Hash table stuff for keeping track of TOC entries. */
1270
1271 struct GTY(()) toc_hash_struct
1272 {
1273 /* `key' will satisfy CONSTANT_P; in fact, it will satisfy
1274 ASM_OUTPUT_SPECIAL_POOL_ENTRY_P. */
1275 rtx key;
1276 enum machine_mode key_mode;
1277 int labelno;
1278 };
1279
1280 static GTY ((param_is (struct toc_hash_struct))) htab_t toc_hash_table;
1281
1282 /* Hash table to keep track of the argument types for builtin functions. */
1283
1284 struct GTY(()) builtin_hash_struct
1285 {
1286 tree type;
1287 enum machine_mode mode[4]; /* return value + 3 arguments. */
1288 unsigned char uns_p[4]; /* and whether the types are unsigned. */
1289 };
1290
1291 static GTY ((param_is (struct builtin_hash_struct))) htab_t builtin_hash_table;
1292 \f
1293 /* Default register names. */
1294 char rs6000_reg_names[][8] =
1295 {
1296 "0", "1", "2", "3", "4", "5", "6", "7",
1297 "8", "9", "10", "11", "12", "13", "14", "15",
1298 "16", "17", "18", "19", "20", "21", "22", "23",
1299 "24", "25", "26", "27", "28", "29", "30", "31",
1300 "0", "1", "2", "3", "4", "5", "6", "7",
1301 "8", "9", "10", "11", "12", "13", "14", "15",
1302 "16", "17", "18", "19", "20", "21", "22", "23",
1303 "24", "25", "26", "27", "28", "29", "30", "31",
1304 "mq", "lr", "ctr","ap",
1305 "0", "1", "2", "3", "4", "5", "6", "7",
1306 "ca",
1307 /* AltiVec registers. */
1308 "0", "1", "2", "3", "4", "5", "6", "7",
1309 "8", "9", "10", "11", "12", "13", "14", "15",
1310 "16", "17", "18", "19", "20", "21", "22", "23",
1311 "24", "25", "26", "27", "28", "29", "30", "31",
1312 "vrsave", "vscr",
1313 /* SPE registers. */
1314 "spe_acc", "spefscr",
1315 /* Soft frame pointer. */
1316 "sfp"
1317 };
1318
1319 #ifdef TARGET_REGNAMES
1320 static const char alt_reg_names[][8] =
1321 {
1322 "%r0", "%r1", "%r2", "%r3", "%r4", "%r5", "%r6", "%r7",
1323 "%r8", "%r9", "%r10", "%r11", "%r12", "%r13", "%r14", "%r15",
1324 "%r16", "%r17", "%r18", "%r19", "%r20", "%r21", "%r22", "%r23",
1325 "%r24", "%r25", "%r26", "%r27", "%r28", "%r29", "%r30", "%r31",
1326 "%f0", "%f1", "%f2", "%f3", "%f4", "%f5", "%f6", "%f7",
1327 "%f8", "%f9", "%f10", "%f11", "%f12", "%f13", "%f14", "%f15",
1328 "%f16", "%f17", "%f18", "%f19", "%f20", "%f21", "%f22", "%f23",
1329 "%f24", "%f25", "%f26", "%f27", "%f28", "%f29", "%f30", "%f31",
1330 "mq", "lr", "ctr", "ap",
1331 "%cr0", "%cr1", "%cr2", "%cr3", "%cr4", "%cr5", "%cr6", "%cr7",
1332 "ca",
1333 /* AltiVec registers. */
1334 "%v0", "%v1", "%v2", "%v3", "%v4", "%v5", "%v6", "%v7",
1335 "%v8", "%v9", "%v10", "%v11", "%v12", "%v13", "%v14", "%v15",
1336 "%v16", "%v17", "%v18", "%v19", "%v20", "%v21", "%v22", "%v23",
1337 "%v24", "%v25", "%v26", "%v27", "%v28", "%v29", "%v30", "%v31",
1338 "vrsave", "vscr",
1339 /* SPE registers. */
1340 "spe_acc", "spefscr",
1341 /* Soft frame pointer. */
1342 "sfp"
1343 };
1344 #endif
1345
1346 /* Table of valid machine attributes. */
1347
1348 static const struct attribute_spec rs6000_attribute_table[] =
1349 {
1350 /* { name, min_len, max_len, decl_req, type_req, fn_type_req, handler } */
1351 { "altivec", 1, 1, false, true, false, rs6000_handle_altivec_attribute },
1352 { "longcall", 0, 0, false, true, true, rs6000_handle_longcall_attribute },
1353 { "shortcall", 0, 0, false, true, true, rs6000_handle_longcall_attribute },
1354 { "ms_struct", 0, 0, false, false, false, rs6000_handle_struct_attribute },
1355 { "gcc_struct", 0, 0, false, false, false, rs6000_handle_struct_attribute },
1356 #ifdef SUBTARGET_ATTRIBUTE_TABLE
1357 SUBTARGET_ATTRIBUTE_TABLE,
1358 #endif
1359 { NULL, 0, 0, false, false, false, NULL }
1360 };
1361 \f
1362 #ifndef MASK_STRICT_ALIGN
1363 #define MASK_STRICT_ALIGN 0
1364 #endif
1365 #ifndef TARGET_PROFILE_KERNEL
1366 #define TARGET_PROFILE_KERNEL 0
1367 #endif
1368
1369 /* The VRSAVE bitmask puts bit %v0 as the most significant bit. */
1370 #define ALTIVEC_REG_BIT(REGNO) (0x80000000 >> ((REGNO) - FIRST_ALTIVEC_REGNO))
1371 \f
1372 /* Initialize the GCC target structure. */
1373 #undef TARGET_ATTRIBUTE_TABLE
1374 #define TARGET_ATTRIBUTE_TABLE rs6000_attribute_table
1375 #undef TARGET_SET_DEFAULT_TYPE_ATTRIBUTES
1376 #define TARGET_SET_DEFAULT_TYPE_ATTRIBUTES rs6000_set_default_type_attributes
1377 #undef TARGET_ATTRIBUTE_TAKES_IDENTIFIER_P
1378 #define TARGET_ATTRIBUTE_TAKES_IDENTIFIER_P rs6000_attribute_takes_identifier_p
1379
1380 #undef TARGET_ASM_ALIGNED_DI_OP
1381 #define TARGET_ASM_ALIGNED_DI_OP DOUBLE_INT_ASM_OP
1382
1383 /* Default unaligned ops are only provided for ELF. Find the ops needed
1384 for non-ELF systems. */
1385 #ifndef OBJECT_FORMAT_ELF
1386 #if TARGET_XCOFF
1387 /* For XCOFF. rs6000_assemble_integer will handle unaligned DIs on
1388 64-bit targets. */
1389 #undef TARGET_ASM_UNALIGNED_HI_OP
1390 #define TARGET_ASM_UNALIGNED_HI_OP "\t.vbyte\t2,"
1391 #undef TARGET_ASM_UNALIGNED_SI_OP
1392 #define TARGET_ASM_UNALIGNED_SI_OP "\t.vbyte\t4,"
1393 #undef TARGET_ASM_UNALIGNED_DI_OP
1394 #define TARGET_ASM_UNALIGNED_DI_OP "\t.vbyte\t8,"
1395 #else
1396 /* For Darwin. */
1397 #undef TARGET_ASM_UNALIGNED_HI_OP
1398 #define TARGET_ASM_UNALIGNED_HI_OP "\t.short\t"
1399 #undef TARGET_ASM_UNALIGNED_SI_OP
1400 #define TARGET_ASM_UNALIGNED_SI_OP "\t.long\t"
1401 #undef TARGET_ASM_UNALIGNED_DI_OP
1402 #define TARGET_ASM_UNALIGNED_DI_OP "\t.quad\t"
1403 #undef TARGET_ASM_ALIGNED_DI_OP
1404 #define TARGET_ASM_ALIGNED_DI_OP "\t.quad\t"
1405 #endif
1406 #endif
1407
1408 /* This hook deals with fixups for relocatable code and DI-mode objects
1409 in 64-bit code. */
1410 #undef TARGET_ASM_INTEGER
1411 #define TARGET_ASM_INTEGER rs6000_assemble_integer
1412
1413 #ifdef HAVE_GAS_HIDDEN
1414 #undef TARGET_ASM_ASSEMBLE_VISIBILITY
1415 #define TARGET_ASM_ASSEMBLE_VISIBILITY rs6000_assemble_visibility
1416 #endif
1417
1418 #undef TARGET_HAVE_TLS
1419 #define TARGET_HAVE_TLS HAVE_AS_TLS
1420
1421 #undef TARGET_CANNOT_FORCE_CONST_MEM
1422 #define TARGET_CANNOT_FORCE_CONST_MEM rs6000_tls_referenced_p
1423
1424 #undef TARGET_DELEGITIMIZE_ADDRESS
1425 #define TARGET_DELEGITIMIZE_ADDRESS rs6000_delegitimize_address
1426
1427 #undef TARGET_ASM_FUNCTION_PROLOGUE
1428 #define TARGET_ASM_FUNCTION_PROLOGUE rs6000_output_function_prologue
1429 #undef TARGET_ASM_FUNCTION_EPILOGUE
1430 #define TARGET_ASM_FUNCTION_EPILOGUE rs6000_output_function_epilogue
1431
1432 #undef TARGET_LEGITIMIZE_ADDRESS
1433 #define TARGET_LEGITIMIZE_ADDRESS rs6000_legitimize_address
1434
1435 #undef TARGET_SCHED_VARIABLE_ISSUE
1436 #define TARGET_SCHED_VARIABLE_ISSUE rs6000_variable_issue
1437
1438 #undef TARGET_SCHED_ISSUE_RATE
1439 #define TARGET_SCHED_ISSUE_RATE rs6000_issue_rate
1440 #undef TARGET_SCHED_ADJUST_COST
1441 #define TARGET_SCHED_ADJUST_COST rs6000_adjust_cost
1442 #undef TARGET_SCHED_ADJUST_PRIORITY
1443 #define TARGET_SCHED_ADJUST_PRIORITY rs6000_adjust_priority
1444 #undef TARGET_SCHED_IS_COSTLY_DEPENDENCE
1445 #define TARGET_SCHED_IS_COSTLY_DEPENDENCE rs6000_is_costly_dependence
1446 #undef TARGET_SCHED_INIT
1447 #define TARGET_SCHED_INIT rs6000_sched_init
1448 #undef TARGET_SCHED_FINISH
1449 #define TARGET_SCHED_FINISH rs6000_sched_finish
1450 #undef TARGET_SCHED_REORDER
1451 #define TARGET_SCHED_REORDER rs6000_sched_reorder
1452 #undef TARGET_SCHED_REORDER2
1453 #define TARGET_SCHED_REORDER2 rs6000_sched_reorder2
1454
1455 #undef TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DFA_LOOKAHEAD
1456 #define TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DFA_LOOKAHEAD rs6000_use_sched_lookahead
1457
1458 #undef TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DFA_LOOKAHEAD_GUARD
1459 #define TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DFA_LOOKAHEAD_GUARD rs6000_use_sched_lookahead_guard
1460
1461 #undef TARGET_SCHED_ALLOC_SCHED_CONTEXT
1462 #define TARGET_SCHED_ALLOC_SCHED_CONTEXT rs6000_alloc_sched_context
1463 #undef TARGET_SCHED_INIT_SCHED_CONTEXT
1464 #define TARGET_SCHED_INIT_SCHED_CONTEXT rs6000_init_sched_context
1465 #undef TARGET_SCHED_SET_SCHED_CONTEXT
1466 #define TARGET_SCHED_SET_SCHED_CONTEXT rs6000_set_sched_context
1467 #undef TARGET_SCHED_FREE_SCHED_CONTEXT
1468 #define TARGET_SCHED_FREE_SCHED_CONTEXT rs6000_free_sched_context
1469
1470 #undef TARGET_VECTORIZE_BUILTIN_MASK_FOR_LOAD
1471 #define TARGET_VECTORIZE_BUILTIN_MASK_FOR_LOAD rs6000_builtin_mask_for_load
1472 #undef TARGET_VECTORIZE_BUILTIN_MUL_WIDEN_EVEN
1473 #define TARGET_VECTORIZE_BUILTIN_MUL_WIDEN_EVEN rs6000_builtin_mul_widen_even
1474 #undef TARGET_VECTORIZE_BUILTIN_MUL_WIDEN_ODD
1475 #define TARGET_VECTORIZE_BUILTIN_MUL_WIDEN_ODD rs6000_builtin_mul_widen_odd
1476 #undef TARGET_VECTORIZE_BUILTIN_CONVERSION
1477 #define TARGET_VECTORIZE_BUILTIN_CONVERSION rs6000_builtin_conversion
1478 #undef TARGET_VECTORIZE_BUILTIN_VEC_PERM
1479 #define TARGET_VECTORIZE_BUILTIN_VEC_PERM rs6000_builtin_vec_perm
1480 #undef TARGET_VECTORIZE_SUPPORT_VECTOR_MISALIGNMENT
1481 #define TARGET_VECTORIZE_SUPPORT_VECTOR_MISALIGNMENT \
1482 rs6000_builtin_support_vector_misalignment
1483 #undef TARGET_VECTORIZE_VECTOR_ALIGNMENT_REACHABLE
1484 #define TARGET_VECTORIZE_VECTOR_ALIGNMENT_REACHABLE rs6000_vector_alignment_reachable
1485 #undef TARGET_VECTORIZE_BUILTIN_VECTORIZATION_COST
1486 #define TARGET_VECTORIZE_BUILTIN_VECTORIZATION_COST \
1487 rs6000_builtin_vectorization_cost
1488
1489 #undef TARGET_INIT_BUILTINS
1490 #define TARGET_INIT_BUILTINS rs6000_init_builtins
1491 #undef TARGET_BUILTIN_DECL
1492 #define TARGET_BUILTIN_DECL rs6000_builtin_decl
1493
1494 #undef TARGET_EXPAND_BUILTIN
1495 #define TARGET_EXPAND_BUILTIN rs6000_expand_builtin
1496
1497 #undef TARGET_MANGLE_TYPE
1498 #define TARGET_MANGLE_TYPE rs6000_mangle_type
1499
1500 #undef TARGET_INIT_LIBFUNCS
1501 #define TARGET_INIT_LIBFUNCS rs6000_init_libfuncs
1502
1503 #if TARGET_MACHO
1504 #undef TARGET_BINDS_LOCAL_P
1505 #define TARGET_BINDS_LOCAL_P darwin_binds_local_p
1506 #endif
1507
1508 #undef TARGET_MS_BITFIELD_LAYOUT_P
1509 #define TARGET_MS_BITFIELD_LAYOUT_P rs6000_ms_bitfield_layout_p
1510
1511 #undef TARGET_ASM_OUTPUT_MI_THUNK
1512 #define TARGET_ASM_OUTPUT_MI_THUNK rs6000_output_mi_thunk
1513
1514 #undef TARGET_ASM_CAN_OUTPUT_MI_THUNK
1515 #define TARGET_ASM_CAN_OUTPUT_MI_THUNK hook_bool_const_tree_hwi_hwi_const_tree_true
1516
1517 #undef TARGET_FUNCTION_OK_FOR_SIBCALL
1518 #define TARGET_FUNCTION_OK_FOR_SIBCALL rs6000_function_ok_for_sibcall
1519
1520 #undef TARGET_INVALID_WITHIN_DOLOOP
1521 #define TARGET_INVALID_WITHIN_DOLOOP rs6000_invalid_within_doloop
1522
1523 #undef TARGET_REGISTER_MOVE_COST
1524 #define TARGET_REGISTER_MOVE_COST rs6000_register_move_cost
1525 #undef TARGET_MEMORY_MOVE_COST
1526 #define TARGET_MEMORY_MOVE_COST rs6000_memory_move_cost
1527 #undef TARGET_RTX_COSTS
1528 #define TARGET_RTX_COSTS rs6000_rtx_costs
1529 #undef TARGET_ADDRESS_COST
1530 #define TARGET_ADDRESS_COST hook_int_rtx_bool_0
1531
1532 #undef TARGET_DWARF_REGISTER_SPAN
1533 #define TARGET_DWARF_REGISTER_SPAN rs6000_dwarf_register_span
1534
1535 #undef TARGET_INIT_DWARF_REG_SIZES_EXTRA
1536 #define TARGET_INIT_DWARF_REG_SIZES_EXTRA rs6000_init_dwarf_reg_sizes_extra
1537
1538 /* On rs6000, function arguments are promoted, as are function return
1539 values. */
1540 #undef TARGET_PROMOTE_FUNCTION_MODE
1541 #define TARGET_PROMOTE_FUNCTION_MODE default_promote_function_mode_always_promote
1542
1543 #undef TARGET_RETURN_IN_MEMORY
1544 #define TARGET_RETURN_IN_MEMORY rs6000_return_in_memory
1545
1546 #undef TARGET_SETUP_INCOMING_VARARGS
1547 #define TARGET_SETUP_INCOMING_VARARGS setup_incoming_varargs
1548
1549 /* Always strict argument naming on rs6000. */
1550 #undef TARGET_STRICT_ARGUMENT_NAMING
1551 #define TARGET_STRICT_ARGUMENT_NAMING hook_bool_CUMULATIVE_ARGS_true
1552 #undef TARGET_PRETEND_OUTGOING_VARARGS_NAMED
1553 #define TARGET_PRETEND_OUTGOING_VARARGS_NAMED hook_bool_CUMULATIVE_ARGS_true
1554 #undef TARGET_SPLIT_COMPLEX_ARG
1555 #define TARGET_SPLIT_COMPLEX_ARG hook_bool_const_tree_true
1556 #undef TARGET_MUST_PASS_IN_STACK
1557 #define TARGET_MUST_PASS_IN_STACK rs6000_must_pass_in_stack
1558 #undef TARGET_PASS_BY_REFERENCE
1559 #define TARGET_PASS_BY_REFERENCE rs6000_pass_by_reference
1560 #undef TARGET_ARG_PARTIAL_BYTES
1561 #define TARGET_ARG_PARTIAL_BYTES rs6000_arg_partial_bytes
1562 #undef TARGET_FUNCTION_ARG_ADVANCE
1563 #define TARGET_FUNCTION_ARG_ADVANCE rs6000_function_arg_advance
1564 #undef TARGET_FUNCTION_ARG
1565 #define TARGET_FUNCTION_ARG rs6000_function_arg
1566
1567 #undef TARGET_BUILD_BUILTIN_VA_LIST
1568 #define TARGET_BUILD_BUILTIN_VA_LIST rs6000_build_builtin_va_list
1569
1570 #undef TARGET_EXPAND_BUILTIN_VA_START
1571 #define TARGET_EXPAND_BUILTIN_VA_START rs6000_va_start
1572
1573 #undef TARGET_GIMPLIFY_VA_ARG_EXPR
1574 #define TARGET_GIMPLIFY_VA_ARG_EXPR rs6000_gimplify_va_arg
1575
1576 #undef TARGET_EH_RETURN_FILTER_MODE
1577 #define TARGET_EH_RETURN_FILTER_MODE rs6000_eh_return_filter_mode
1578
1579 #undef TARGET_SCALAR_MODE_SUPPORTED_P
1580 #define TARGET_SCALAR_MODE_SUPPORTED_P rs6000_scalar_mode_supported_p
1581
1582 #undef TARGET_VECTOR_MODE_SUPPORTED_P
1583 #define TARGET_VECTOR_MODE_SUPPORTED_P rs6000_vector_mode_supported_p
1584
1585 #undef TARGET_INVALID_ARG_FOR_UNPROTOTYPED_FN
1586 #define TARGET_INVALID_ARG_FOR_UNPROTOTYPED_FN invalid_arg_for_unprototyped_fn
1587
1588 #undef TARGET_HANDLE_OPTION
1589 #define TARGET_HANDLE_OPTION rs6000_handle_option
1590
1591 #undef TARGET_VECTORIZE_BUILTIN_VECTORIZED_FUNCTION
1592 #define TARGET_VECTORIZE_BUILTIN_VECTORIZED_FUNCTION \
1593 rs6000_builtin_vectorized_function
1594
1595 #undef TARGET_DEFAULT_TARGET_FLAGS
1596 #define TARGET_DEFAULT_TARGET_FLAGS \
1597 (TARGET_DEFAULT)
1598
1599 #undef TARGET_STACK_PROTECT_FAIL
1600 #define TARGET_STACK_PROTECT_FAIL rs6000_stack_protect_fail
1601
1602 /* MPC604EUM 3.5.2 Weak Consistency between Multiple Processors
1603 The PowerPC architecture requires only weak consistency among
1604 processors--that is, memory accesses between processors need not be
1605 sequentially consistent and memory accesses among processors can occur
1606 in any order. The ability to order memory accesses weakly provides
1607 opportunities for more efficient use of the system bus. Unless a
1608 dependency exists, the 604e allows read operations to precede store
1609 operations. */
1610 #undef TARGET_RELAXED_ORDERING
1611 #define TARGET_RELAXED_ORDERING true
1612
1613 #ifdef HAVE_AS_TLS
1614 #undef TARGET_ASM_OUTPUT_DWARF_DTPREL
1615 #define TARGET_ASM_OUTPUT_DWARF_DTPREL rs6000_output_dwarf_dtprel
1616 #endif
1617
1618 /* Use a 32-bit anchor range. This leads to sequences like:
1619
1620 addis tmp,anchor,high
1621 add dest,tmp,low
1622
1623 where tmp itself acts as an anchor, and can be shared between
1624 accesses to the same 64k page. */
1625 #undef TARGET_MIN_ANCHOR_OFFSET
1626 #define TARGET_MIN_ANCHOR_OFFSET -0x7fffffff - 1
1627 #undef TARGET_MAX_ANCHOR_OFFSET
1628 #define TARGET_MAX_ANCHOR_OFFSET 0x7fffffff
1629 #undef TARGET_USE_BLOCKS_FOR_CONSTANT_P
1630 #define TARGET_USE_BLOCKS_FOR_CONSTANT_P rs6000_use_blocks_for_constant_p
1631
1632 #undef TARGET_BUILTIN_RECIPROCAL
1633 #define TARGET_BUILTIN_RECIPROCAL rs6000_builtin_reciprocal
1634
1635 #undef TARGET_EXPAND_TO_RTL_HOOK
1636 #define TARGET_EXPAND_TO_RTL_HOOK rs6000_alloc_sdmode_stack_slot
1637
1638 #undef TARGET_INSTANTIATE_DECLS
1639 #define TARGET_INSTANTIATE_DECLS rs6000_instantiate_decls
1640
1641 #undef TARGET_SECONDARY_RELOAD
1642 #define TARGET_SECONDARY_RELOAD rs6000_secondary_reload
1643
1644 #undef TARGET_IRA_COVER_CLASSES
1645 #define TARGET_IRA_COVER_CLASSES rs6000_ira_cover_classes
1646
1647 #undef TARGET_LEGITIMATE_ADDRESS_P
1648 #define TARGET_LEGITIMATE_ADDRESS_P rs6000_legitimate_address_p
1649
1650 #undef TARGET_MODE_DEPENDENT_ADDRESS_P
1651 #define TARGET_MODE_DEPENDENT_ADDRESS_P rs6000_mode_dependent_address_p
1652
1653 #undef TARGET_CAN_ELIMINATE
1654 #define TARGET_CAN_ELIMINATE rs6000_can_eliminate
1655
1656 #undef TARGET_TRAMPOLINE_INIT
1657 #define TARGET_TRAMPOLINE_INIT rs6000_trampoline_init
1658
1659 #undef TARGET_FUNCTION_VALUE
1660 #define TARGET_FUNCTION_VALUE rs6000_function_value
1661
1662 struct gcc_target targetm = TARGET_INITIALIZER;
1663 \f
1664 /* Return number of consecutive hard regs needed starting at reg REGNO
1665 to hold something of mode MODE.
1666 This is ordinarily the length in words of a value of mode MODE
1667 but can be less for certain modes in special long registers.
1668
1669 For the SPE, GPRs are 64 bits but only 32 bits are visible in
1670 scalar instructions. The upper 32 bits are only available to the
1671 SIMD instructions.
1672
1673 POWER and PowerPC GPRs hold 32 bits worth;
1674 PowerPC64 GPRs and FPRs point register holds 64 bits worth. */
1675
1676 static int
1677 rs6000_hard_regno_nregs_internal (int regno, enum machine_mode mode)
1678 {
1679 unsigned HOST_WIDE_INT reg_size;
1680
1681 if (FP_REGNO_P (regno))
1682 reg_size = (VECTOR_MEM_VSX_P (mode)
1683 ? UNITS_PER_VSX_WORD
1684 : UNITS_PER_FP_WORD);
1685
1686 else if (SPE_SIMD_REGNO_P (regno) && TARGET_SPE && SPE_VECTOR_MODE (mode))
1687 reg_size = UNITS_PER_SPE_WORD;
1688
1689 else if (ALTIVEC_REGNO_P (regno))
1690 reg_size = UNITS_PER_ALTIVEC_WORD;
1691
1692 /* The value returned for SCmode in the E500 double case is 2 for
1693 ABI compatibility; storing an SCmode value in a single register
1694 would require function_arg and rs6000_spe_function_arg to handle
1695 SCmode so as to pass the value correctly in a pair of
1696 registers. */
1697 else if (TARGET_E500_DOUBLE && FLOAT_MODE_P (mode) && mode != SCmode
1698 && !DECIMAL_FLOAT_MODE_P (mode))
1699 reg_size = UNITS_PER_FP_WORD;
1700
1701 else
1702 reg_size = UNITS_PER_WORD;
1703
1704 return (GET_MODE_SIZE (mode) + reg_size - 1) / reg_size;
1705 }
1706
1707 /* Value is 1 if hard register REGNO can hold a value of machine-mode
1708 MODE. */
1709 static int
1710 rs6000_hard_regno_mode_ok (int regno, enum machine_mode mode)
1711 {
1712 int last_regno = regno + rs6000_hard_regno_nregs[mode][regno] - 1;
1713
1714 /* VSX registers that overlap the FPR registers are larger than for non-VSX
1715 implementations. Don't allow an item to be split between a FP register
1716 and an Altivec register. */
1717 if (VECTOR_MEM_VSX_P (mode))
1718 {
1719 if (FP_REGNO_P (regno))
1720 return FP_REGNO_P (last_regno);
1721
1722 if (ALTIVEC_REGNO_P (regno))
1723 return ALTIVEC_REGNO_P (last_regno);
1724 }
1725
1726 /* The GPRs can hold any mode, but values bigger than one register
1727 cannot go past R31. */
1728 if (INT_REGNO_P (regno))
1729 return INT_REGNO_P (last_regno);
1730
1731 /* The float registers (except for VSX vector modes) can only hold floating
1732 modes and DImode. This excludes the 32-bit decimal float mode for
1733 now. */
1734 if (FP_REGNO_P (regno))
1735 {
1736 if (SCALAR_FLOAT_MODE_P (mode)
1737 && (mode != TDmode || (regno % 2) == 0)
1738 && FP_REGNO_P (last_regno))
1739 return 1;
1740
1741 if (GET_MODE_CLASS (mode) == MODE_INT
1742 && GET_MODE_SIZE (mode) == UNITS_PER_FP_WORD)
1743 return 1;
1744
1745 if (PAIRED_SIMD_REGNO_P (regno) && TARGET_PAIRED_FLOAT
1746 && PAIRED_VECTOR_MODE (mode))
1747 return 1;
1748
1749 return 0;
1750 }
1751
1752 /* The CR register can only hold CC modes. */
1753 if (CR_REGNO_P (regno))
1754 return GET_MODE_CLASS (mode) == MODE_CC;
1755
1756 if (CA_REGNO_P (regno))
1757 return mode == BImode;
1758
1759 /* AltiVec only in AldyVec registers. */
1760 if (ALTIVEC_REGNO_P (regno))
1761 return VECTOR_MEM_ALTIVEC_OR_VSX_P (mode);
1762
1763 /* ...but GPRs can hold SIMD data on the SPE in one register. */
1764 if (SPE_SIMD_REGNO_P (regno) && TARGET_SPE && SPE_VECTOR_MODE (mode))
1765 return 1;
1766
1767 /* We cannot put TImode anywhere except general register and it must be able
1768 to fit within the register set. In the future, allow TImode in the
1769 Altivec or VSX registers. */
1770
1771 return GET_MODE_SIZE (mode) <= UNITS_PER_WORD;
1772 }
1773
1774 /* Print interesting facts about registers. */
1775 static void
1776 rs6000_debug_reg_print (int first_regno, int last_regno, const char *reg_name)
1777 {
1778 int r, m;
1779
1780 for (r = first_regno; r <= last_regno; ++r)
1781 {
1782 const char *comma = "";
1783 int len;
1784
1785 if (first_regno == last_regno)
1786 fprintf (stderr, "%s:\t", reg_name);
1787 else
1788 fprintf (stderr, "%s%d:\t", reg_name, r - first_regno);
1789
1790 len = 8;
1791 for (m = 0; m < NUM_MACHINE_MODES; ++m)
1792 if (rs6000_hard_regno_mode_ok_p[m][r] && rs6000_hard_regno_nregs[m][r])
1793 {
1794 if (len > 70)
1795 {
1796 fprintf (stderr, ",\n\t");
1797 len = 8;
1798 comma = "";
1799 }
1800
1801 if (rs6000_hard_regno_nregs[m][r] > 1)
1802 len += fprintf (stderr, "%s%s/%d", comma, GET_MODE_NAME (m),
1803 rs6000_hard_regno_nregs[m][r]);
1804 else
1805 len += fprintf (stderr, "%s%s", comma, GET_MODE_NAME (m));
1806
1807 comma = ", ";
1808 }
1809
1810 if (call_used_regs[r])
1811 {
1812 if (len > 70)
1813 {
1814 fprintf (stderr, ",\n\t");
1815 len = 8;
1816 comma = "";
1817 }
1818
1819 len += fprintf (stderr, "%s%s", comma, "call-used");
1820 comma = ", ";
1821 }
1822
1823 if (fixed_regs[r])
1824 {
1825 if (len > 70)
1826 {
1827 fprintf (stderr, ",\n\t");
1828 len = 8;
1829 comma = "";
1830 }
1831
1832 len += fprintf (stderr, "%s%s", comma, "fixed");
1833 comma = ", ";
1834 }
1835
1836 if (len > 70)
1837 {
1838 fprintf (stderr, ",\n\t");
1839 comma = "";
1840 }
1841
1842 fprintf (stderr, "%sregno = %d\n", comma, r);
1843 }
1844 }
1845
1846 /* Print various interesting information with -mdebug=reg. */
1847 static void
1848 rs6000_debug_reg_global (void)
1849 {
1850 const char *nl = (const char *)0;
1851 int m;
1852 char costly_num[20];
1853 char nop_num[20];
1854 const char *costly_str;
1855 const char *nop_str;
1856
1857 /* Map enum rs6000_vector to string. */
1858 static const char *rs6000_debug_vector_unit[] = {
1859 "none",
1860 "altivec",
1861 "vsx",
1862 "paired",
1863 "spe",
1864 "other"
1865 };
1866
1867 fprintf (stderr, "Register information: (last virtual reg = %d)\n",
1868 LAST_VIRTUAL_REGISTER);
1869 rs6000_debug_reg_print (0, 31, "gr");
1870 rs6000_debug_reg_print (32, 63, "fp");
1871 rs6000_debug_reg_print (FIRST_ALTIVEC_REGNO,
1872 LAST_ALTIVEC_REGNO,
1873 "vs");
1874 rs6000_debug_reg_print (LR_REGNO, LR_REGNO, "lr");
1875 rs6000_debug_reg_print (CTR_REGNO, CTR_REGNO, "ctr");
1876 rs6000_debug_reg_print (CR0_REGNO, CR7_REGNO, "cr");
1877 rs6000_debug_reg_print (MQ_REGNO, MQ_REGNO, "mq");
1878 rs6000_debug_reg_print (CA_REGNO, CA_REGNO, "ca");
1879 rs6000_debug_reg_print (VRSAVE_REGNO, VRSAVE_REGNO, "vrsave");
1880 rs6000_debug_reg_print (VSCR_REGNO, VSCR_REGNO, "vscr");
1881 rs6000_debug_reg_print (SPE_ACC_REGNO, SPE_ACC_REGNO, "spe_a");
1882 rs6000_debug_reg_print (SPEFSCR_REGNO, SPEFSCR_REGNO, "spe_f");
1883
1884 fprintf (stderr,
1885 "\n"
1886 "d reg_class = %s\n"
1887 "f reg_class = %s\n"
1888 "v reg_class = %s\n"
1889 "wa reg_class = %s\n"
1890 "wd reg_class = %s\n"
1891 "wf reg_class = %s\n"
1892 "ws reg_class = %s\n\n",
1893 reg_class_names[rs6000_constraints[RS6000_CONSTRAINT_d]],
1894 reg_class_names[rs6000_constraints[RS6000_CONSTRAINT_f]],
1895 reg_class_names[rs6000_constraints[RS6000_CONSTRAINT_v]],
1896 reg_class_names[rs6000_constraints[RS6000_CONSTRAINT_wa]],
1897 reg_class_names[rs6000_constraints[RS6000_CONSTRAINT_wd]],
1898 reg_class_names[rs6000_constraints[RS6000_CONSTRAINT_wf]],
1899 reg_class_names[rs6000_constraints[RS6000_CONSTRAINT_ws]]);
1900
1901 for (m = 0; m < NUM_MACHINE_MODES; ++m)
1902 if (rs6000_vector_unit[m] || rs6000_vector_mem[m])
1903 {
1904 nl = "\n";
1905 fprintf (stderr, "Vector mode: %-5s arithmetic: %-8s move: %-8s\n",
1906 GET_MODE_NAME (m),
1907 rs6000_debug_vector_unit[ rs6000_vector_unit[m] ],
1908 rs6000_debug_vector_unit[ rs6000_vector_mem[m] ]);
1909 }
1910
1911 if (nl)
1912 fputs (nl, stderr);
1913
1914 if (rs6000_recip_control)
1915 {
1916 fprintf (stderr, "\nReciprocal mask = 0x%x\n", rs6000_recip_control);
1917
1918 for (m = 0; m < NUM_MACHINE_MODES; ++m)
1919 if (rs6000_recip_bits[m])
1920 {
1921 fprintf (stderr,
1922 "Reciprocal estimate mode: %-5s divide: %s rsqrt: %s\n",
1923 GET_MODE_NAME (m),
1924 (RS6000_RECIP_AUTO_RE_P (m)
1925 ? "auto"
1926 : (RS6000_RECIP_HAVE_RE_P (m) ? "have" : "none")),
1927 (RS6000_RECIP_AUTO_RSQRTE_P (m)
1928 ? "auto"
1929 : (RS6000_RECIP_HAVE_RSQRTE_P (m) ? "have" : "none")));
1930 }
1931
1932 fputs ("\n", stderr);
1933 }
1934
1935 switch (rs6000_sched_costly_dep)
1936 {
1937 case max_dep_latency:
1938 costly_str = "max_dep_latency";
1939 break;
1940
1941 case no_dep_costly:
1942 costly_str = "no_dep_costly";
1943 break;
1944
1945 case all_deps_costly:
1946 costly_str = "all_deps_costly";
1947 break;
1948
1949 case true_store_to_load_dep_costly:
1950 costly_str = "true_store_to_load_dep_costly";
1951 break;
1952
1953 case store_to_load_dep_costly:
1954 costly_str = "store_to_load_dep_costly";
1955 break;
1956
1957 default:
1958 costly_str = costly_num;
1959 sprintf (costly_num, "%d", (int)rs6000_sched_costly_dep);
1960 break;
1961 }
1962
1963 switch (rs6000_sched_insert_nops)
1964 {
1965 case sched_finish_regroup_exact:
1966 nop_str = "sched_finish_regroup_exact";
1967 break;
1968
1969 case sched_finish_pad_groups:
1970 nop_str = "sched_finish_pad_groups";
1971 break;
1972
1973 case sched_finish_none:
1974 nop_str = "sched_finish_none";
1975 break;
1976
1977 default:
1978 nop_str = nop_num;
1979 sprintf (nop_num, "%d", (int)rs6000_sched_insert_nops);
1980 break;
1981 }
1982
1983 fprintf (stderr,
1984 "always_hint = %s\n"
1985 "align_branch_targets = %s\n"
1986 "sched_restricted_insns_priority = %d\n"
1987 "sched_costly_dep = %s\n"
1988 "sched_insert_nops = %s\n\n",
1989 rs6000_always_hint ? "true" : "false",
1990 rs6000_align_branch_targets ? "true" : "false",
1991 (int)rs6000_sched_restricted_insns_priority,
1992 costly_str, nop_str);
1993 }
1994
1995 /* Initialize the various global tables that are based on register size. */
1996 static void
1997 rs6000_init_hard_regno_mode_ok (void)
1998 {
1999 int r, m, c;
2000 int align64;
2001 int align32;
2002
2003 /* Precalculate REGNO_REG_CLASS. */
2004 rs6000_regno_regclass[0] = GENERAL_REGS;
2005 for (r = 1; r < 32; ++r)
2006 rs6000_regno_regclass[r] = BASE_REGS;
2007
2008 for (r = 32; r < 64; ++r)
2009 rs6000_regno_regclass[r] = FLOAT_REGS;
2010
2011 for (r = 64; r < FIRST_PSEUDO_REGISTER; ++r)
2012 rs6000_regno_regclass[r] = NO_REGS;
2013
2014 for (r = FIRST_ALTIVEC_REGNO; r <= LAST_ALTIVEC_REGNO; ++r)
2015 rs6000_regno_regclass[r] = ALTIVEC_REGS;
2016
2017 rs6000_regno_regclass[CR0_REGNO] = CR0_REGS;
2018 for (r = CR1_REGNO; r <= CR7_REGNO; ++r)
2019 rs6000_regno_regclass[r] = CR_REGS;
2020
2021 rs6000_regno_regclass[MQ_REGNO] = MQ_REGS;
2022 rs6000_regno_regclass[LR_REGNO] = LINK_REGS;
2023 rs6000_regno_regclass[CTR_REGNO] = CTR_REGS;
2024 rs6000_regno_regclass[CA_REGNO] = CA_REGS;
2025 rs6000_regno_regclass[VRSAVE_REGNO] = VRSAVE_REGS;
2026 rs6000_regno_regclass[VSCR_REGNO] = VRSAVE_REGS;
2027 rs6000_regno_regclass[SPE_ACC_REGNO] = SPE_ACC_REGS;
2028 rs6000_regno_regclass[SPEFSCR_REGNO] = SPEFSCR_REGS;
2029 rs6000_regno_regclass[ARG_POINTER_REGNUM] = BASE_REGS;
2030 rs6000_regno_regclass[FRAME_POINTER_REGNUM] = BASE_REGS;
2031
2032 /* Precalculate vector information, this must be set up before the
2033 rs6000_hard_regno_nregs_internal below. */
2034 for (m = 0; m < NUM_MACHINE_MODES; ++m)
2035 {
2036 rs6000_vector_unit[m] = rs6000_vector_mem[m] = VECTOR_NONE;
2037 rs6000_vector_reload[m][0] = CODE_FOR_nothing;
2038 rs6000_vector_reload[m][1] = CODE_FOR_nothing;
2039 }
2040
2041 for (c = 0; c < (int)(int)RS6000_CONSTRAINT_MAX; c++)
2042 rs6000_constraints[c] = NO_REGS;
2043
2044 /* The VSX hardware allows native alignment for vectors, but control whether the compiler
2045 believes it can use native alignment or still uses 128-bit alignment. */
2046 if (TARGET_VSX && !TARGET_VSX_ALIGN_128)
2047 {
2048 align64 = 64;
2049 align32 = 32;
2050 }
2051 else
2052 {
2053 align64 = 128;
2054 align32 = 128;
2055 }
2056
2057 /* V2DF mode, VSX only. */
2058 if (TARGET_VSX)
2059 {
2060 rs6000_vector_unit[V2DFmode] = VECTOR_VSX;
2061 rs6000_vector_mem[V2DFmode] = VECTOR_VSX;
2062 rs6000_vector_align[V2DFmode] = align64;
2063 }
2064
2065 /* V4SF mode, either VSX or Altivec. */
2066 if (TARGET_VSX)
2067 {
2068 rs6000_vector_unit[V4SFmode] = VECTOR_VSX;
2069 rs6000_vector_mem[V4SFmode] = VECTOR_VSX;
2070 rs6000_vector_align[V4SFmode] = align32;
2071 }
2072 else if (TARGET_ALTIVEC)
2073 {
2074 rs6000_vector_unit[V4SFmode] = VECTOR_ALTIVEC;
2075 rs6000_vector_mem[V4SFmode] = VECTOR_ALTIVEC;
2076 rs6000_vector_align[V4SFmode] = align32;
2077 }
2078
2079 /* V16QImode, V8HImode, V4SImode are Altivec only, but possibly do VSX loads
2080 and stores. */
2081 if (TARGET_ALTIVEC)
2082 {
2083 rs6000_vector_unit[V4SImode] = VECTOR_ALTIVEC;
2084 rs6000_vector_unit[V8HImode] = VECTOR_ALTIVEC;
2085 rs6000_vector_unit[V16QImode] = VECTOR_ALTIVEC;
2086 rs6000_vector_align[V4SImode] = align32;
2087 rs6000_vector_align[V8HImode] = align32;
2088 rs6000_vector_align[V16QImode] = align32;
2089
2090 if (TARGET_VSX)
2091 {
2092 rs6000_vector_mem[V4SImode] = VECTOR_VSX;
2093 rs6000_vector_mem[V8HImode] = VECTOR_VSX;
2094 rs6000_vector_mem[V16QImode] = VECTOR_VSX;
2095 }
2096 else
2097 {
2098 rs6000_vector_mem[V4SImode] = VECTOR_ALTIVEC;
2099 rs6000_vector_mem[V8HImode] = VECTOR_ALTIVEC;
2100 rs6000_vector_mem[V16QImode] = VECTOR_ALTIVEC;
2101 }
2102 }
2103
2104 /* V2DImode, only allow under VSX, which can do V2DI insert/splat/extract.
2105 Altivec doesn't have 64-bit support. */
2106 if (TARGET_VSX)
2107 {
2108 rs6000_vector_mem[V2DImode] = VECTOR_VSX;
2109 rs6000_vector_unit[V2DImode] = VECTOR_NONE;
2110 rs6000_vector_align[V2DImode] = align64;
2111 }
2112
2113 /* DFmode, see if we want to use the VSX unit. */
2114 if (TARGET_VSX && TARGET_VSX_SCALAR_DOUBLE)
2115 {
2116 rs6000_vector_unit[DFmode] = VECTOR_VSX;
2117 rs6000_vector_mem[DFmode]
2118 = (TARGET_VSX_SCALAR_MEMORY ? VECTOR_VSX : VECTOR_NONE);
2119 rs6000_vector_align[DFmode] = align64;
2120 }
2121
2122 /* TODO add SPE and paired floating point vector support. */
2123
2124 /* Register class constaints for the constraints that depend on compile
2125 switches. */
2126 if (TARGET_HARD_FLOAT && TARGET_FPRS)
2127 rs6000_constraints[RS6000_CONSTRAINT_f] = FLOAT_REGS;
2128
2129 if (TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT)
2130 rs6000_constraints[RS6000_CONSTRAINT_d] = FLOAT_REGS;
2131
2132 if (TARGET_VSX)
2133 {
2134 /* At present, we just use VSX_REGS, but we have different constraints
2135 based on the use, in case we want to fine tune the default register
2136 class used. wa = any VSX register, wf = register class to use for
2137 V4SF, wd = register class to use for V2DF, and ws = register classs to
2138 use for DF scalars. */
2139 rs6000_constraints[RS6000_CONSTRAINT_wa] = VSX_REGS;
2140 rs6000_constraints[RS6000_CONSTRAINT_wf] = VSX_REGS;
2141 rs6000_constraints[RS6000_CONSTRAINT_wd] = VSX_REGS;
2142 rs6000_constraints[RS6000_CONSTRAINT_ws] = (TARGET_VSX_SCALAR_MEMORY
2143 ? VSX_REGS
2144 : FLOAT_REGS);
2145 }
2146
2147 if (TARGET_ALTIVEC)
2148 rs6000_constraints[RS6000_CONSTRAINT_v] = ALTIVEC_REGS;
2149
2150 /* Set up the reload helper functions. */
2151 if (TARGET_VSX || TARGET_ALTIVEC)
2152 {
2153 if (TARGET_64BIT)
2154 {
2155 rs6000_vector_reload[V16QImode][0] = CODE_FOR_reload_v16qi_di_store;
2156 rs6000_vector_reload[V16QImode][1] = CODE_FOR_reload_v16qi_di_load;
2157 rs6000_vector_reload[V8HImode][0] = CODE_FOR_reload_v8hi_di_store;
2158 rs6000_vector_reload[V8HImode][1] = CODE_FOR_reload_v8hi_di_load;
2159 rs6000_vector_reload[V4SImode][0] = CODE_FOR_reload_v4si_di_store;
2160 rs6000_vector_reload[V4SImode][1] = CODE_FOR_reload_v4si_di_load;
2161 rs6000_vector_reload[V2DImode][0] = CODE_FOR_reload_v2di_di_store;
2162 rs6000_vector_reload[V2DImode][1] = CODE_FOR_reload_v2di_di_load;
2163 rs6000_vector_reload[V4SFmode][0] = CODE_FOR_reload_v4sf_di_store;
2164 rs6000_vector_reload[V4SFmode][1] = CODE_FOR_reload_v4sf_di_load;
2165 rs6000_vector_reload[V2DFmode][0] = CODE_FOR_reload_v2df_di_store;
2166 rs6000_vector_reload[V2DFmode][1] = CODE_FOR_reload_v2df_di_load;
2167 }
2168 else
2169 {
2170 rs6000_vector_reload[V16QImode][0] = CODE_FOR_reload_v16qi_si_store;
2171 rs6000_vector_reload[V16QImode][1] = CODE_FOR_reload_v16qi_si_load;
2172 rs6000_vector_reload[V8HImode][0] = CODE_FOR_reload_v8hi_si_store;
2173 rs6000_vector_reload[V8HImode][1] = CODE_FOR_reload_v8hi_si_load;
2174 rs6000_vector_reload[V4SImode][0] = CODE_FOR_reload_v4si_si_store;
2175 rs6000_vector_reload[V4SImode][1] = CODE_FOR_reload_v4si_si_load;
2176 rs6000_vector_reload[V2DImode][0] = CODE_FOR_reload_v2di_si_store;
2177 rs6000_vector_reload[V2DImode][1] = CODE_FOR_reload_v2di_si_load;
2178 rs6000_vector_reload[V4SFmode][0] = CODE_FOR_reload_v4sf_si_store;
2179 rs6000_vector_reload[V4SFmode][1] = CODE_FOR_reload_v4sf_si_load;
2180 rs6000_vector_reload[V2DFmode][0] = CODE_FOR_reload_v2df_si_store;
2181 rs6000_vector_reload[V2DFmode][1] = CODE_FOR_reload_v2df_si_load;
2182 }
2183 }
2184
2185 /* Precalculate HARD_REGNO_NREGS. */
2186 for (r = 0; r < FIRST_PSEUDO_REGISTER; ++r)
2187 for (m = 0; m < NUM_MACHINE_MODES; ++m)
2188 rs6000_hard_regno_nregs[m][r]
2189 = rs6000_hard_regno_nregs_internal (r, (enum machine_mode)m);
2190
2191 /* Precalculate HARD_REGNO_MODE_OK. */
2192 for (r = 0; r < FIRST_PSEUDO_REGISTER; ++r)
2193 for (m = 0; m < NUM_MACHINE_MODES; ++m)
2194 if (rs6000_hard_regno_mode_ok (r, (enum machine_mode)m))
2195 rs6000_hard_regno_mode_ok_p[m][r] = true;
2196
2197 /* Precalculate CLASS_MAX_NREGS sizes. */
2198 for (c = 0; c < LIM_REG_CLASSES; ++c)
2199 {
2200 int reg_size;
2201
2202 if (TARGET_VSX && VSX_REG_CLASS_P (c))
2203 reg_size = UNITS_PER_VSX_WORD;
2204
2205 else if (c == ALTIVEC_REGS)
2206 reg_size = UNITS_PER_ALTIVEC_WORD;
2207
2208 else if (c == FLOAT_REGS)
2209 reg_size = UNITS_PER_FP_WORD;
2210
2211 else
2212 reg_size = UNITS_PER_WORD;
2213
2214 for (m = 0; m < NUM_MACHINE_MODES; ++m)
2215 rs6000_class_max_nregs[m][c]
2216 = (GET_MODE_SIZE (m) + reg_size - 1) / reg_size;
2217 }
2218
2219 if (TARGET_E500_DOUBLE)
2220 rs6000_class_max_nregs[DFmode][GENERAL_REGS] = 1;
2221
2222 /* Calculate which modes to automatically generate code to use a the
2223 reciprocal divide and square root instructions. In the future, possibly
2224 automatically generate the instructions even if the user did not specify
2225 -mrecip. The older machines double precision reciprocal sqrt estimate is
2226 not accurate enough. */
2227 memset (rs6000_recip_bits, 0, sizeof (rs6000_recip_bits));
2228 if (TARGET_FRES)
2229 rs6000_recip_bits[SFmode] = RS6000_RECIP_MASK_HAVE_RE;
2230 if (TARGET_FRE)
2231 rs6000_recip_bits[DFmode] = RS6000_RECIP_MASK_HAVE_RE;
2232 if (VECTOR_UNIT_ALTIVEC_OR_VSX_P (V4SFmode))
2233 rs6000_recip_bits[V4SFmode] = RS6000_RECIP_MASK_HAVE_RE;
2234 if (VECTOR_UNIT_VSX_P (V2DFmode))
2235 rs6000_recip_bits[V2DFmode] = RS6000_RECIP_MASK_HAVE_RE;
2236
2237 if (TARGET_FRSQRTES)
2238 rs6000_recip_bits[SFmode] |= RS6000_RECIP_MASK_HAVE_RSQRTE;
2239 if (TARGET_FRSQRTE)
2240 rs6000_recip_bits[DFmode] |= RS6000_RECIP_MASK_HAVE_RSQRTE;
2241 if (VECTOR_UNIT_ALTIVEC_OR_VSX_P (V4SFmode))
2242 rs6000_recip_bits[V4SFmode] |= RS6000_RECIP_MASK_HAVE_RSQRTE;
2243 if (VECTOR_UNIT_VSX_P (V2DFmode))
2244 rs6000_recip_bits[V2DFmode] |= RS6000_RECIP_MASK_HAVE_RSQRTE;
2245
2246 if (rs6000_recip_control)
2247 {
2248 if (!TARGET_FUSED_MADD)
2249 warning (0, "-mrecip requires -mfused-madd");
2250 if (!flag_finite_math_only)
2251 warning (0, "-mrecip requires -ffinite-math or -ffast-math");
2252 if (flag_trapping_math)
2253 warning (0, "-mrecip requires -fno-trapping-math or -ffast-math");
2254 if (!flag_reciprocal_math)
2255 warning (0, "-mrecip requires -freciprocal-math or -ffast-math");
2256 if (TARGET_FUSED_MADD && flag_finite_math_only && !flag_trapping_math
2257 && flag_reciprocal_math)
2258 {
2259 if (RS6000_RECIP_HAVE_RE_P (SFmode)
2260 && (rs6000_recip_control & RECIP_SF_DIV) != 0)
2261 rs6000_recip_bits[SFmode] |= RS6000_RECIP_MASK_AUTO_RE;
2262
2263 if (RS6000_RECIP_HAVE_RE_P (DFmode)
2264 && (rs6000_recip_control & RECIP_DF_DIV) != 0)
2265 rs6000_recip_bits[DFmode] |= RS6000_RECIP_MASK_AUTO_RE;
2266
2267 if (RS6000_RECIP_HAVE_RE_P (V4SFmode)
2268 && (rs6000_recip_control & RECIP_V4SF_DIV) != 0)
2269 rs6000_recip_bits[V4SFmode] |= RS6000_RECIP_MASK_AUTO_RE;
2270
2271 if (RS6000_RECIP_HAVE_RE_P (V2DFmode)
2272 && (rs6000_recip_control & RECIP_V2DF_DIV) != 0)
2273 rs6000_recip_bits[V2DFmode] |= RS6000_RECIP_MASK_AUTO_RE;
2274
2275 if (RS6000_RECIP_HAVE_RSQRTE_P (SFmode)
2276 && (rs6000_recip_control & RECIP_SF_RSQRT) != 0)
2277 rs6000_recip_bits[SFmode] |= RS6000_RECIP_MASK_AUTO_RSQRTE;
2278
2279 if (RS6000_RECIP_HAVE_RSQRTE_P (DFmode)
2280 && (rs6000_recip_control & RECIP_DF_RSQRT) != 0)
2281 rs6000_recip_bits[DFmode] |= RS6000_RECIP_MASK_AUTO_RSQRTE;
2282
2283 if (RS6000_RECIP_HAVE_RSQRTE_P (V4SFmode)
2284 && (rs6000_recip_control & RECIP_V4SF_RSQRT) != 0)
2285 rs6000_recip_bits[V4SFmode] |= RS6000_RECIP_MASK_AUTO_RSQRTE;
2286
2287 if (RS6000_RECIP_HAVE_RSQRTE_P (V2DFmode)
2288 && (rs6000_recip_control & RECIP_V2DF_RSQRT) != 0)
2289 rs6000_recip_bits[V2DFmode] |= RS6000_RECIP_MASK_AUTO_RSQRTE;
2290 }
2291 }
2292
2293 if (TARGET_DEBUG_REG)
2294 rs6000_debug_reg_global ();
2295
2296 if (TARGET_DEBUG_COST || TARGET_DEBUG_REG)
2297 fprintf (stderr,
2298 "SImode variable mult cost = %d\n"
2299 "SImode constant mult cost = %d\n"
2300 "SImode short constant mult cost = %d\n"
2301 "DImode multipliciation cost = %d\n"
2302 "SImode division cost = %d\n"
2303 "DImode division cost = %d\n"
2304 "Simple fp operation cost = %d\n"
2305 "DFmode multiplication cost = %d\n"
2306 "SFmode division cost = %d\n"
2307 "DFmode division cost = %d\n"
2308 "cache line size = %d\n"
2309 "l1 cache size = %d\n"
2310 "l2 cache size = %d\n"
2311 "simultaneous prefetches = %d\n"
2312 "\n",
2313 rs6000_cost->mulsi,
2314 rs6000_cost->mulsi_const,
2315 rs6000_cost->mulsi_const9,
2316 rs6000_cost->muldi,
2317 rs6000_cost->divsi,
2318 rs6000_cost->divdi,
2319 rs6000_cost->fp,
2320 rs6000_cost->dmul,
2321 rs6000_cost->sdiv,
2322 rs6000_cost->ddiv,
2323 rs6000_cost->cache_line_size,
2324 rs6000_cost->l1_cache_size,
2325 rs6000_cost->l2_cache_size,
2326 rs6000_cost->simultaneous_prefetches);
2327 }
2328
2329 #if TARGET_MACHO
2330 /* The Darwin version of SUBTARGET_OVERRIDE_OPTIONS. */
2331
2332 static void
2333 darwin_rs6000_override_options (void)
2334 {
2335 /* The Darwin ABI always includes AltiVec, can't be (validly) turned
2336 off. */
2337 rs6000_altivec_abi = 1;
2338 TARGET_ALTIVEC_VRSAVE = 1;
2339 if (DEFAULT_ABI == ABI_DARWIN)
2340 {
2341 if (MACHO_DYNAMIC_NO_PIC_P)
2342 {
2343 if (flag_pic)
2344 warning (0, "-mdynamic-no-pic overrides -fpic or -fPIC");
2345 flag_pic = 0;
2346 }
2347 else if (flag_pic == 1)
2348 {
2349 flag_pic = 2;
2350 }
2351 if (TARGET_64BIT)
2352 darwin_one_byte_bool = 1;
2353 }
2354 if (TARGET_64BIT && ! TARGET_POWERPC64)
2355 {
2356 target_flags |= MASK_POWERPC64;
2357 warning (0, "-m64 requires PowerPC64 architecture, enabling");
2358 }
2359 if (flag_mkernel)
2360 {
2361 rs6000_default_long_calls = 1;
2362 target_flags |= MASK_SOFT_FLOAT;
2363 }
2364
2365 /* Make -m64 imply -maltivec. Darwin's 64-bit ABI includes
2366 Altivec. */
2367 if (!flag_mkernel && !flag_apple_kext
2368 && TARGET_64BIT
2369 && ! (target_flags_explicit & MASK_ALTIVEC))
2370 target_flags |= MASK_ALTIVEC;
2371
2372 /* Unless the user (not the configurer) has explicitly overridden
2373 it with -mcpu=G3 or -mno-altivec, then 10.5+ targets default to
2374 G4 unless targetting the kernel. */
2375 if (!flag_mkernel
2376 && !flag_apple_kext
2377 && strverscmp (darwin_macosx_version_min, "10.5") >= 0
2378 && ! (target_flags_explicit & MASK_ALTIVEC)
2379 && ! rs6000_select[1].string)
2380 {
2381 target_flags |= MASK_ALTIVEC;
2382 }
2383 }
2384 #endif
2385
2386 /* If not otherwise specified by a target, make 'long double' equivalent to
2387 'double'. */
2388
2389 #ifndef RS6000_DEFAULT_LONG_DOUBLE_SIZE
2390 #define RS6000_DEFAULT_LONG_DOUBLE_SIZE 64
2391 #endif
2392
2393 /* Override command line options. Mostly we process the processor
2394 type and sometimes adjust other TARGET_ options. */
2395
2396 void
2397 rs6000_override_options (const char *default_cpu)
2398 {
2399 size_t i, j;
2400 struct rs6000_cpu_select *ptr;
2401 int set_masks;
2402
2403 /* Simplifications for entries below. */
2404
2405 enum {
2406 POWERPC_BASE_MASK = MASK_POWERPC | MASK_NEW_MNEMONICS,
2407 POWERPC_7400_MASK = POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_ALTIVEC
2408 };
2409
2410 /* This table occasionally claims that a processor does not support
2411 a particular feature even though it does, but the feature is slower
2412 than the alternative. Thus, it shouldn't be relied on as a
2413 complete description of the processor's support.
2414
2415 Please keep this list in order, and don't forget to update the
2416 documentation in invoke.texi when adding a new processor or
2417 flag. */
2418 static struct ptt
2419 {
2420 const char *const name; /* Canonical processor name. */
2421 const enum processor_type processor; /* Processor type enum value. */
2422 const int target_enable; /* Target flags to enable. */
2423 } const processor_target_table[]
2424 = {{"401", PROCESSOR_PPC403, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
2425 {"403", PROCESSOR_PPC403,
2426 POWERPC_BASE_MASK | MASK_SOFT_FLOAT | MASK_STRICT_ALIGN},
2427 {"405", PROCESSOR_PPC405,
2428 POWERPC_BASE_MASK | MASK_SOFT_FLOAT | MASK_MULHW | MASK_DLMZB},
2429 {"405fp", PROCESSOR_PPC405,
2430 POWERPC_BASE_MASK | MASK_MULHW | MASK_DLMZB},
2431 {"440", PROCESSOR_PPC440,
2432 POWERPC_BASE_MASK | MASK_SOFT_FLOAT | MASK_MULHW | MASK_DLMZB},
2433 {"440fp", PROCESSOR_PPC440,
2434 POWERPC_BASE_MASK | MASK_MULHW | MASK_DLMZB},
2435 {"464", PROCESSOR_PPC440,
2436 POWERPC_BASE_MASK | MASK_SOFT_FLOAT | MASK_MULHW | MASK_DLMZB},
2437 {"464fp", PROCESSOR_PPC440,
2438 POWERPC_BASE_MASK | MASK_MULHW | MASK_DLMZB},
2439 {"476", PROCESSOR_PPC476,
2440 POWERPC_BASE_MASK | MASK_SOFT_FLOAT | MASK_PPC_GFXOPT | MASK_MFCRF
2441 | MASK_POPCNTB | MASK_FPRND | MASK_CMPB | MASK_MULHW | MASK_DLMZB},
2442 {"476fp", PROCESSOR_PPC476,
2443 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_MFCRF | MASK_POPCNTB
2444 | MASK_FPRND | MASK_CMPB | MASK_MULHW | MASK_DLMZB},
2445 {"505", PROCESSOR_MPCCORE, POWERPC_BASE_MASK},
2446 {"601", PROCESSOR_PPC601,
2447 MASK_POWER | POWERPC_BASE_MASK | MASK_MULTIPLE | MASK_STRING},
2448 {"602", PROCESSOR_PPC603, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
2449 {"603", PROCESSOR_PPC603, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
2450 {"603e", PROCESSOR_PPC603, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
2451 {"604", PROCESSOR_PPC604, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
2452 {"604e", PROCESSOR_PPC604e, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
2453 {"620", PROCESSOR_PPC620,
2454 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_POWERPC64},
2455 {"630", PROCESSOR_PPC630,
2456 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_POWERPC64},
2457 {"740", PROCESSOR_PPC750, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
2458 {"7400", PROCESSOR_PPC7400, POWERPC_7400_MASK},
2459 {"7450", PROCESSOR_PPC7450, POWERPC_7400_MASK},
2460 {"750", PROCESSOR_PPC750, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
2461 {"801", PROCESSOR_MPCCORE, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
2462 {"821", PROCESSOR_MPCCORE, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
2463 {"823", PROCESSOR_MPCCORE, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
2464 {"8540", PROCESSOR_PPC8540, POWERPC_BASE_MASK | MASK_STRICT_ALIGN
2465 | MASK_ISEL},
2466 /* 8548 has a dummy entry for now. */
2467 {"8548", PROCESSOR_PPC8540, POWERPC_BASE_MASK | MASK_STRICT_ALIGN
2468 | MASK_ISEL},
2469 {"a2", PROCESSOR_PPCA2,
2470 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_POWERPC64 | MASK_POPCNTB
2471 | MASK_CMPB | MASK_NO_UPDATE },
2472 {"e300c2", PROCESSOR_PPCE300C2, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
2473 {"e300c3", PROCESSOR_PPCE300C3, POWERPC_BASE_MASK},
2474 {"e500mc", PROCESSOR_PPCE500MC, POWERPC_BASE_MASK | MASK_PPC_GFXOPT
2475 | MASK_ISEL},
2476 {"e500mc64", PROCESSOR_PPCE500MC64, POWERPC_BASE_MASK | MASK_POWERPC64
2477 | MASK_PPC_GFXOPT | MASK_ISEL},
2478 {"860", PROCESSOR_MPCCORE, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
2479 {"970", PROCESSOR_POWER4,
2480 POWERPC_7400_MASK | MASK_PPC_GPOPT | MASK_MFCRF | MASK_POWERPC64},
2481 {"cell", PROCESSOR_CELL,
2482 POWERPC_7400_MASK | MASK_PPC_GPOPT | MASK_MFCRF | MASK_POWERPC64},
2483 {"common", PROCESSOR_COMMON, MASK_NEW_MNEMONICS},
2484 {"ec603e", PROCESSOR_PPC603, POWERPC_BASE_MASK | MASK_SOFT_FLOAT},
2485 {"G3", PROCESSOR_PPC750, POWERPC_BASE_MASK | MASK_PPC_GFXOPT},
2486 {"G4", PROCESSOR_PPC7450, POWERPC_7400_MASK},
2487 {"G5", PROCESSOR_POWER4,
2488 POWERPC_7400_MASK | MASK_PPC_GPOPT | MASK_MFCRF | MASK_POWERPC64},
2489 {"titan", PROCESSOR_TITAN,
2490 POWERPC_BASE_MASK | MASK_MULHW | MASK_DLMZB},
2491 {"power", PROCESSOR_POWER, MASK_POWER | MASK_MULTIPLE | MASK_STRING},
2492 {"power2", PROCESSOR_POWER,
2493 MASK_POWER | MASK_POWER2 | MASK_MULTIPLE | MASK_STRING},
2494 {"power3", PROCESSOR_PPC630,
2495 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_POWERPC64},
2496 {"power4", PROCESSOR_POWER4,
2497 POWERPC_BASE_MASK | MASK_POWERPC64 | MASK_PPC_GPOPT | MASK_PPC_GFXOPT
2498 | MASK_MFCRF},
2499 {"power5", PROCESSOR_POWER5,
2500 POWERPC_BASE_MASK | MASK_POWERPC64 | MASK_PPC_GPOPT | MASK_PPC_GFXOPT
2501 | MASK_MFCRF | MASK_POPCNTB},
2502 {"power5+", PROCESSOR_POWER5,
2503 POWERPC_BASE_MASK | MASK_POWERPC64 | MASK_PPC_GPOPT | MASK_PPC_GFXOPT
2504 | MASK_MFCRF | MASK_POPCNTB | MASK_FPRND},
2505 {"power6", PROCESSOR_POWER6,
2506 POWERPC_BASE_MASK | MASK_POWERPC64 | MASK_PPC_GPOPT | MASK_PPC_GFXOPT
2507 | MASK_MFCRF | MASK_POPCNTB | MASK_FPRND | MASK_CMPB | MASK_DFP
2508 | MASK_RECIP_PRECISION},
2509 {"power6x", PROCESSOR_POWER6,
2510 POWERPC_BASE_MASK | MASK_POWERPC64 | MASK_PPC_GPOPT | MASK_PPC_GFXOPT
2511 | MASK_MFCRF | MASK_POPCNTB | MASK_FPRND | MASK_CMPB | MASK_DFP
2512 | MASK_MFPGPR | MASK_RECIP_PRECISION},
2513 {"power7", PROCESSOR_POWER7, /* Don't add MASK_ISEL by default */
2514 POWERPC_7400_MASK | MASK_POWERPC64 | MASK_PPC_GPOPT | MASK_MFCRF
2515 | MASK_POPCNTB | MASK_FPRND | MASK_CMPB | MASK_DFP | MASK_POPCNTD
2516 | MASK_VSX | MASK_RECIP_PRECISION},
2517 {"powerpc", PROCESSOR_POWERPC, POWERPC_BASE_MASK},
2518 {"powerpc64", PROCESSOR_POWERPC64,
2519 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_POWERPC64},
2520 {"rios", PROCESSOR_RIOS1, MASK_POWER | MASK_MULTIPLE | MASK_STRING},
2521 {"rios1", PROCESSOR_RIOS1, MASK_POWER | MASK_MULTIPLE | MASK_STRING},
2522 {"rios2", PROCESSOR_RIOS2,
2523 MASK_POWER | MASK_POWER2 | MASK_MULTIPLE | MASK_STRING},
2524 {"rsc", PROCESSOR_PPC601, MASK_POWER | MASK_MULTIPLE | MASK_STRING},
2525 {"rsc1", PROCESSOR_PPC601, MASK_POWER | MASK_MULTIPLE | MASK_STRING},
2526 {"rs64", PROCESSOR_RS64A,
2527 POWERPC_BASE_MASK | MASK_PPC_GFXOPT | MASK_POWERPC64}
2528 };
2529
2530 const size_t ptt_size = ARRAY_SIZE (processor_target_table);
2531
2532 /* Some OSs don't support saving the high part of 64-bit registers on
2533 context switch. Other OSs don't support saving Altivec registers.
2534 On those OSs, we don't touch the MASK_POWERPC64 or MASK_ALTIVEC
2535 settings; if the user wants either, the user must explicitly specify
2536 them and we won't interfere with the user's specification. */
2537
2538 enum {
2539 POWER_MASKS = MASK_POWER | MASK_POWER2 | MASK_MULTIPLE | MASK_STRING,
2540 POWERPC_MASKS = (POWERPC_BASE_MASK | MASK_PPC_GPOPT | MASK_STRICT_ALIGN
2541 | MASK_PPC_GFXOPT | MASK_POWERPC64 | MASK_ALTIVEC
2542 | MASK_MFCRF | MASK_POPCNTB | MASK_FPRND | MASK_MULHW
2543 | MASK_DLMZB | MASK_CMPB | MASK_MFPGPR | MASK_DFP
2544 | MASK_POPCNTD | MASK_VSX | MASK_ISEL | MASK_NO_UPDATE
2545 | MASK_RECIP_PRECISION)
2546 };
2547
2548 /* Masks for instructions set at various powerpc ISAs. */
2549 enum {
2550 ISA_2_1_MASKS = MASK_MFCRF,
2551 ISA_2_2_MASKS = (ISA_2_1_MASKS | MASK_POPCNTB | MASK_FPRND),
2552
2553 /* For ISA 2.05, do not add MFPGPR, since it isn't in ISA 2.06, and don't
2554 add ALTIVEC, since in general it isn't a win on power6. In ISA 2.04,
2555 fsel, fre, fsqrt, etc. were no longer documented as optional. Group
2556 masks by server and embedded. */
2557 ISA_2_5_MASKS_EMBEDDED = (ISA_2_2_MASKS | MASK_CMPB | MASK_RECIP_PRECISION
2558 | MASK_PPC_GFXOPT | MASK_PPC_GPOPT),
2559 ISA_2_5_MASKS_SERVER = (ISA_2_5_MASKS_EMBEDDED | MASK_DFP),
2560
2561 /* For ISA 2.06, don't add ISEL, since in general it isn't a win, but
2562 altivec is a win so enable it. */
2563 ISA_2_6_MASKS_EMBEDDED = (ISA_2_5_MASKS_EMBEDDED | MASK_POPCNTD),
2564 ISA_2_6_MASKS_SERVER = (ISA_2_5_MASKS_SERVER | MASK_POPCNTD | MASK_ALTIVEC
2565 | MASK_VSX)
2566 };
2567
2568 /* Numerous experiment shows that IRA based loop pressure
2569 calculation works better for RTL loop invariant motion on targets
2570 with enough (>= 32) registers. It is an expensive optimization.
2571 So it is on only for peak performance. */
2572 if (optimize >= 3)
2573 flag_ira_loop_pressure = 1;
2574
2575 /* Set the pointer size. */
2576 if (TARGET_64BIT)
2577 {
2578 rs6000_pmode = (int)DImode;
2579 rs6000_pointer_size = 64;
2580 }
2581 else
2582 {
2583 rs6000_pmode = (int)SImode;
2584 rs6000_pointer_size = 32;
2585 }
2586
2587 set_masks = POWER_MASKS | POWERPC_MASKS | MASK_SOFT_FLOAT;
2588 #ifdef OS_MISSING_POWERPC64
2589 if (OS_MISSING_POWERPC64)
2590 set_masks &= ~MASK_POWERPC64;
2591 #endif
2592 #ifdef OS_MISSING_ALTIVEC
2593 if (OS_MISSING_ALTIVEC)
2594 set_masks &= ~MASK_ALTIVEC;
2595 #endif
2596
2597 /* Don't override by the processor default if given explicitly. */
2598 set_masks &= ~target_flags_explicit;
2599
2600 /* Identify the processor type. */
2601 rs6000_select[0].string = default_cpu;
2602 rs6000_cpu = TARGET_POWERPC64 ? PROCESSOR_DEFAULT64 : PROCESSOR_DEFAULT;
2603
2604 for (i = 0; i < ARRAY_SIZE (rs6000_select); i++)
2605 {
2606 ptr = &rs6000_select[i];
2607 if (ptr->string != (char *)0 && ptr->string[0] != '\0')
2608 {
2609 for (j = 0; j < ptt_size; j++)
2610 if (! strcmp (ptr->string, processor_target_table[j].name))
2611 {
2612 if (ptr->set_tune_p)
2613 rs6000_cpu = processor_target_table[j].processor;
2614
2615 if (ptr->set_arch_p)
2616 {
2617 target_flags &= ~set_masks;
2618 target_flags |= (processor_target_table[j].target_enable
2619 & set_masks);
2620 }
2621 break;
2622 }
2623
2624 if (j == ptt_size)
2625 error ("bad value (%s) for %s switch", ptr->string, ptr->name);
2626 }
2627 }
2628
2629 if (rs6000_cpu == PROCESSOR_PPCE300C2 || rs6000_cpu == PROCESSOR_PPCE300C3
2630 || rs6000_cpu == PROCESSOR_PPCE500MC || rs6000_cpu == PROCESSOR_PPCE500MC64)
2631 {
2632 if (TARGET_ALTIVEC)
2633 error ("AltiVec not supported in this target");
2634 if (TARGET_SPE)
2635 error ("Spe not supported in this target");
2636 }
2637
2638 /* Disable Cell microcode if we are optimizing for the Cell
2639 and not optimizing for size. */
2640 if (rs6000_gen_cell_microcode == -1)
2641 rs6000_gen_cell_microcode = !(rs6000_cpu == PROCESSOR_CELL
2642 && !optimize_size);
2643
2644 /* If we are optimizing big endian systems for space and it's OK to
2645 use instructions that would be microcoded on the Cell, use the
2646 load/store multiple and string instructions. */
2647 if (BYTES_BIG_ENDIAN && optimize_size && rs6000_gen_cell_microcode)
2648 target_flags |= ~target_flags_explicit & (MASK_MULTIPLE | MASK_STRING);
2649
2650 /* Don't allow -mmultiple or -mstring on little endian systems
2651 unless the cpu is a 750, because the hardware doesn't support the
2652 instructions used in little endian mode, and causes an alignment
2653 trap. The 750 does not cause an alignment trap (except when the
2654 target is unaligned). */
2655
2656 if (!BYTES_BIG_ENDIAN && rs6000_cpu != PROCESSOR_PPC750)
2657 {
2658 if (TARGET_MULTIPLE)
2659 {
2660 target_flags &= ~MASK_MULTIPLE;
2661 if ((target_flags_explicit & MASK_MULTIPLE) != 0)
2662 warning (0, "-mmultiple is not supported on little endian systems");
2663 }
2664
2665 if (TARGET_STRING)
2666 {
2667 target_flags &= ~MASK_STRING;
2668 if ((target_flags_explicit & MASK_STRING) != 0)
2669 warning (0, "-mstring is not supported on little endian systems");
2670 }
2671 }
2672
2673 /* Add some warnings for VSX. */
2674 if (TARGET_VSX)
2675 {
2676 const char *msg = NULL;
2677 if (!TARGET_HARD_FLOAT || !TARGET_FPRS
2678 || !TARGET_SINGLE_FLOAT || !TARGET_DOUBLE_FLOAT)
2679 {
2680 if (target_flags_explicit & MASK_VSX)
2681 msg = N_("-mvsx requires hardware floating point");
2682 else
2683 target_flags &= ~ MASK_VSX;
2684 }
2685 else if (TARGET_PAIRED_FLOAT)
2686 msg = N_("-mvsx and -mpaired are incompatible");
2687 /* The hardware will allow VSX and little endian, but until we make sure
2688 things like vector select, etc. work don't allow VSX on little endian
2689 systems at this point. */
2690 else if (!BYTES_BIG_ENDIAN)
2691 msg = N_("-mvsx used with little endian code");
2692 else if (TARGET_AVOID_XFORM > 0)
2693 msg = N_("-mvsx needs indexed addressing");
2694 else if (!TARGET_ALTIVEC && (target_flags_explicit & MASK_ALTIVEC))
2695 {
2696 if (target_flags_explicit & MASK_VSX)
2697 msg = N_("-mvsx and -mno-altivec are incompatible");
2698 else
2699 msg = N_("-mno-altivec disables vsx");
2700 }
2701
2702 if (msg)
2703 {
2704 warning (0, msg);
2705 target_flags &= ~ MASK_VSX;
2706 target_flags_explicit |= MASK_VSX;
2707 }
2708 }
2709
2710 /* For the newer switches (vsx, dfp, etc.) set some of the older options,
2711 unless the user explicitly used the -mno-<option> to disable the code. */
2712 if (TARGET_VSX)
2713 target_flags |= (ISA_2_6_MASKS_SERVER & ~target_flags_explicit);
2714 else if (TARGET_POPCNTD)
2715 target_flags |= (ISA_2_6_MASKS_EMBEDDED & ~target_flags_explicit);
2716 else if (TARGET_DFP)
2717 target_flags |= (ISA_2_5_MASKS_SERVER & ~target_flags_explicit);
2718 else if (TARGET_CMPB)
2719 target_flags |= (ISA_2_5_MASKS_EMBEDDED & ~target_flags_explicit);
2720 else if (TARGET_POPCNTB || TARGET_FPRND)
2721 target_flags |= (ISA_2_2_MASKS & ~target_flags_explicit);
2722 else if (TARGET_ALTIVEC)
2723 target_flags |= (MASK_PPC_GFXOPT & ~target_flags_explicit);
2724
2725 /* E500mc does "better" if we inline more aggressively. Respect the
2726 user's opinion, though. */
2727 if (rs6000_block_move_inline_limit == 0
2728 && (rs6000_cpu == PROCESSOR_PPCE500MC
2729 || rs6000_cpu == PROCESSOR_PPCE500MC64))
2730 rs6000_block_move_inline_limit = 128;
2731
2732 /* store_one_arg depends on expand_block_move to handle at least the
2733 size of reg_parm_stack_space. */
2734 if (rs6000_block_move_inline_limit < (TARGET_POWERPC64 ? 64 : 32))
2735 rs6000_block_move_inline_limit = (TARGET_POWERPC64 ? 64 : 32);
2736
2737 /* Set debug flags */
2738 if (rs6000_debug_name)
2739 {
2740 if (! strcmp (rs6000_debug_name, "all"))
2741 rs6000_debug_stack = rs6000_debug_arg = rs6000_debug_reg
2742 = rs6000_debug_addr = rs6000_debug_cost = 1;
2743 else if (! strcmp (rs6000_debug_name, "stack"))
2744 rs6000_debug_stack = 1;
2745 else if (! strcmp (rs6000_debug_name, "arg"))
2746 rs6000_debug_arg = 1;
2747 else if (! strcmp (rs6000_debug_name, "reg"))
2748 rs6000_debug_reg = 1;
2749 else if (! strcmp (rs6000_debug_name, "addr"))
2750 rs6000_debug_addr = 1;
2751 else if (! strcmp (rs6000_debug_name, "cost"))
2752 rs6000_debug_cost = 1;
2753 else
2754 error ("unknown -mdebug-%s switch", rs6000_debug_name);
2755
2756 /* If the appropriate debug option is enabled, replace the target hooks
2757 with debug versions that call the real version and then prints
2758 debugging information. */
2759 if (TARGET_DEBUG_COST)
2760 {
2761 targetm.rtx_costs = rs6000_debug_rtx_costs;
2762 targetm.address_cost = rs6000_debug_address_cost;
2763 targetm.sched.adjust_cost = rs6000_debug_adjust_cost;
2764 }
2765
2766 if (TARGET_DEBUG_ADDR)
2767 {
2768 targetm.legitimate_address_p = rs6000_debug_legitimate_address_p;
2769 targetm.legitimize_address = rs6000_debug_legitimize_address;
2770 rs6000_secondary_reload_class_ptr
2771 = rs6000_debug_secondary_reload_class;
2772 rs6000_secondary_memory_needed_ptr
2773 = rs6000_debug_secondary_memory_needed;
2774 rs6000_cannot_change_mode_class_ptr
2775 = rs6000_debug_cannot_change_mode_class;
2776 rs6000_preferred_reload_class_ptr
2777 = rs6000_debug_preferred_reload_class;
2778 rs6000_legitimize_reload_address_ptr
2779 = rs6000_debug_legitimize_reload_address;
2780 rs6000_mode_dependent_address_ptr
2781 = rs6000_debug_mode_dependent_address;
2782 }
2783 }
2784
2785 if (rs6000_traceback_name)
2786 {
2787 if (! strncmp (rs6000_traceback_name, "full", 4))
2788 rs6000_traceback = traceback_full;
2789 else if (! strncmp (rs6000_traceback_name, "part", 4))
2790 rs6000_traceback = traceback_part;
2791 else if (! strncmp (rs6000_traceback_name, "no", 2))
2792 rs6000_traceback = traceback_none;
2793 else
2794 error ("unknown -mtraceback arg %qs; expecting %<full%>, %<partial%> or %<none%>",
2795 rs6000_traceback_name);
2796 }
2797
2798 if (rs6000_veclibabi_name)
2799 {
2800 if (strcmp (rs6000_veclibabi_name, "mass") == 0)
2801 rs6000_veclib_handler = rs6000_builtin_vectorized_libmass;
2802 else
2803 error ("unknown vectorization library ABI type (%s) for "
2804 "-mveclibabi= switch", rs6000_veclibabi_name);
2805 }
2806
2807 if (!rs6000_explicit_options.long_double)
2808 rs6000_long_double_type_size = RS6000_DEFAULT_LONG_DOUBLE_SIZE;
2809
2810 #ifndef POWERPC_LINUX
2811 if (!rs6000_explicit_options.ieee)
2812 rs6000_ieeequad = 1;
2813 #endif
2814
2815 /* Enable Altivec ABI for AIX -maltivec. */
2816 if (TARGET_XCOFF && (TARGET_ALTIVEC || TARGET_VSX))
2817 rs6000_altivec_abi = 1;
2818
2819 /* The AltiVec ABI is the default for PowerPC-64 GNU/Linux. For
2820 PowerPC-32 GNU/Linux, -maltivec implies the AltiVec ABI. It can
2821 be explicitly overridden in either case. */
2822 if (TARGET_ELF)
2823 {
2824 if (!rs6000_explicit_options.altivec_abi
2825 && (TARGET_64BIT || TARGET_ALTIVEC || TARGET_VSX))
2826 rs6000_altivec_abi = 1;
2827
2828 /* Enable VRSAVE for AltiVec ABI, unless explicitly overridden. */
2829 if (!rs6000_explicit_options.vrsave)
2830 TARGET_ALTIVEC_VRSAVE = rs6000_altivec_abi;
2831 }
2832
2833 /* Set the Darwin64 ABI as default for 64-bit Darwin.
2834 So far, the only darwin64 targets are also MACH-O. */
2835 if (TARGET_MACHO
2836 && DEFAULT_ABI == ABI_DARWIN
2837 && TARGET_64BIT)
2838 {
2839 rs6000_darwin64_abi = 1;
2840 /* Default to natural alignment, for better performance. */
2841 rs6000_alignment_flags = MASK_ALIGN_NATURAL;
2842 }
2843
2844 /* Place FP constants in the constant pool instead of TOC
2845 if section anchors enabled. */
2846 if (flag_section_anchors)
2847 TARGET_NO_FP_IN_TOC = 1;
2848
2849 /* Handle -mtls-size option. */
2850 rs6000_parse_tls_size_option ();
2851
2852 #ifdef SUBTARGET_OVERRIDE_OPTIONS
2853 SUBTARGET_OVERRIDE_OPTIONS;
2854 #endif
2855 #ifdef SUBSUBTARGET_OVERRIDE_OPTIONS
2856 SUBSUBTARGET_OVERRIDE_OPTIONS;
2857 #endif
2858 #ifdef SUB3TARGET_OVERRIDE_OPTIONS
2859 SUB3TARGET_OVERRIDE_OPTIONS;
2860 #endif
2861
2862 if (TARGET_E500 || rs6000_cpu == PROCESSOR_PPCE500MC
2863 || rs6000_cpu == PROCESSOR_PPCE500MC64)
2864 {
2865 /* The e500 and e500mc do not have string instructions, and we set
2866 MASK_STRING above when optimizing for size. */
2867 if ((target_flags & MASK_STRING) != 0)
2868 target_flags = target_flags & ~MASK_STRING;
2869 }
2870 else if (rs6000_select[1].string != NULL)
2871 {
2872 /* For the powerpc-eabispe configuration, we set all these by
2873 default, so let's unset them if we manually set another
2874 CPU that is not the E500. */
2875 if (!rs6000_explicit_options.spe_abi)
2876 rs6000_spe_abi = 0;
2877 if (!rs6000_explicit_options.spe)
2878 rs6000_spe = 0;
2879 if (!rs6000_explicit_options.float_gprs)
2880 rs6000_float_gprs = 0;
2881 if (!(target_flags_explicit & MASK_ISEL))
2882 target_flags &= ~MASK_ISEL;
2883 }
2884
2885 /* Detect invalid option combinations with E500. */
2886 CHECK_E500_OPTIONS;
2887
2888 rs6000_always_hint = (rs6000_cpu != PROCESSOR_POWER4
2889 && rs6000_cpu != PROCESSOR_POWER5
2890 && rs6000_cpu != PROCESSOR_POWER6
2891 && rs6000_cpu != PROCESSOR_POWER7
2892 && rs6000_cpu != PROCESSOR_PPCA2
2893 && rs6000_cpu != PROCESSOR_CELL);
2894 rs6000_sched_groups = (rs6000_cpu == PROCESSOR_POWER4
2895 || rs6000_cpu == PROCESSOR_POWER5
2896 || rs6000_cpu == PROCESSOR_POWER7);
2897 rs6000_align_branch_targets = (rs6000_cpu == PROCESSOR_POWER4
2898 || rs6000_cpu == PROCESSOR_POWER5
2899 || rs6000_cpu == PROCESSOR_POWER6
2900 || rs6000_cpu == PROCESSOR_POWER7
2901 || rs6000_cpu == PROCESSOR_PPCE500MC
2902 || rs6000_cpu == PROCESSOR_PPCE500MC64);
2903
2904 /* Allow debug switches to override the above settings. */
2905 if (TARGET_ALWAYS_HINT > 0)
2906 rs6000_always_hint = TARGET_ALWAYS_HINT;
2907
2908 if (TARGET_SCHED_GROUPS > 0)
2909 rs6000_sched_groups = TARGET_SCHED_GROUPS;
2910
2911 if (TARGET_ALIGN_BRANCH_TARGETS > 0)
2912 rs6000_align_branch_targets = TARGET_ALIGN_BRANCH_TARGETS;
2913
2914 rs6000_sched_restricted_insns_priority
2915 = (rs6000_sched_groups ? 1 : 0);
2916
2917 /* Handle -msched-costly-dep option. */
2918 rs6000_sched_costly_dep
2919 = (rs6000_sched_groups ? store_to_load_dep_costly : no_dep_costly);
2920
2921 if (rs6000_sched_costly_dep_str)
2922 {
2923 if (! strcmp (rs6000_sched_costly_dep_str, "no"))
2924 rs6000_sched_costly_dep = no_dep_costly;
2925 else if (! strcmp (rs6000_sched_costly_dep_str, "all"))
2926 rs6000_sched_costly_dep = all_deps_costly;
2927 else if (! strcmp (rs6000_sched_costly_dep_str, "true_store_to_load"))
2928 rs6000_sched_costly_dep = true_store_to_load_dep_costly;
2929 else if (! strcmp (rs6000_sched_costly_dep_str, "store_to_load"))
2930 rs6000_sched_costly_dep = store_to_load_dep_costly;
2931 else
2932 rs6000_sched_costly_dep = ((enum rs6000_dependence_cost)
2933 atoi (rs6000_sched_costly_dep_str));
2934 }
2935
2936 /* Handle -minsert-sched-nops option. */
2937 rs6000_sched_insert_nops
2938 = (rs6000_sched_groups ? sched_finish_regroup_exact : sched_finish_none);
2939
2940 if (rs6000_sched_insert_nops_str)
2941 {
2942 if (! strcmp (rs6000_sched_insert_nops_str, "no"))
2943 rs6000_sched_insert_nops = sched_finish_none;
2944 else if (! strcmp (rs6000_sched_insert_nops_str, "pad"))
2945 rs6000_sched_insert_nops = sched_finish_pad_groups;
2946 else if (! strcmp (rs6000_sched_insert_nops_str, "regroup_exact"))
2947 rs6000_sched_insert_nops = sched_finish_regroup_exact;
2948 else
2949 rs6000_sched_insert_nops = ((enum rs6000_nop_insertion)
2950 atoi (rs6000_sched_insert_nops_str));
2951 }
2952
2953 #ifdef TARGET_REGNAMES
2954 /* If the user desires alternate register names, copy in the
2955 alternate names now. */
2956 if (TARGET_REGNAMES)
2957 memcpy (rs6000_reg_names, alt_reg_names, sizeof (rs6000_reg_names));
2958 #endif
2959
2960 /* Set aix_struct_return last, after the ABI is determined.
2961 If -maix-struct-return or -msvr4-struct-return was explicitly
2962 used, don't override with the ABI default. */
2963 if (!rs6000_explicit_options.aix_struct_ret)
2964 aix_struct_return = (DEFAULT_ABI != ABI_V4 || DRAFT_V4_STRUCT_RET);
2965
2966 #if 0
2967 /* IBM XL compiler defaults to unsigned bitfields. */
2968 if (TARGET_XL_COMPAT)
2969 flag_signed_bitfields = 0;
2970 #endif
2971
2972 if (TARGET_LONG_DOUBLE_128 && !TARGET_IEEEQUAD)
2973 REAL_MODE_FORMAT (TFmode) = &ibm_extended_format;
2974
2975 if (TARGET_TOC)
2976 ASM_GENERATE_INTERNAL_LABEL (toc_label_name, "LCTOC", 1);
2977
2978 /* We can only guarantee the availability of DI pseudo-ops when
2979 assembling for 64-bit targets. */
2980 if (!TARGET_64BIT)
2981 {
2982 targetm.asm_out.aligned_op.di = NULL;
2983 targetm.asm_out.unaligned_op.di = NULL;
2984 }
2985
2986 /* Set branch target alignment, if not optimizing for size. */
2987 if (!optimize_size)
2988 {
2989 /* Cell wants to be aligned 8byte for dual issue. Titan wants to be
2990 aligned 8byte to avoid misprediction by the branch predictor. */
2991 if (rs6000_cpu == PROCESSOR_TITAN
2992 || rs6000_cpu == PROCESSOR_CELL)
2993 {
2994 if (align_functions <= 0)
2995 align_functions = 8;
2996 if (align_jumps <= 0)
2997 align_jumps = 8;
2998 if (align_loops <= 0)
2999 align_loops = 8;
3000 }
3001 if (rs6000_align_branch_targets)
3002 {
3003 if (align_functions <= 0)
3004 align_functions = 16;
3005 if (align_jumps <= 0)
3006 align_jumps = 16;
3007 if (align_loops <= 0)
3008 align_loops = 16;
3009 }
3010 if (align_jumps_max_skip <= 0)
3011 align_jumps_max_skip = 15;
3012 if (align_loops_max_skip <= 0)
3013 align_loops_max_skip = 15;
3014 }
3015
3016 /* Arrange to save and restore machine status around nested functions. */
3017 init_machine_status = rs6000_init_machine_status;
3018
3019 /* We should always be splitting complex arguments, but we can't break
3020 Linux and Darwin ABIs at the moment. For now, only AIX is fixed. */
3021 if (DEFAULT_ABI != ABI_AIX)
3022 targetm.calls.split_complex_arg = NULL;
3023
3024 /* Initialize rs6000_cost with the appropriate target costs. */
3025 if (optimize_size)
3026 rs6000_cost = TARGET_POWERPC64 ? &size64_cost : &size32_cost;
3027 else
3028 switch (rs6000_cpu)
3029 {
3030 case PROCESSOR_RIOS1:
3031 rs6000_cost = &rios1_cost;
3032 break;
3033
3034 case PROCESSOR_RIOS2:
3035 rs6000_cost = &rios2_cost;
3036 break;
3037
3038 case PROCESSOR_RS64A:
3039 rs6000_cost = &rs64a_cost;
3040 break;
3041
3042 case PROCESSOR_MPCCORE:
3043 rs6000_cost = &mpccore_cost;
3044 break;
3045
3046 case PROCESSOR_PPC403:
3047 rs6000_cost = &ppc403_cost;
3048 break;
3049
3050 case PROCESSOR_PPC405:
3051 rs6000_cost = &ppc405_cost;
3052 break;
3053
3054 case PROCESSOR_PPC440:
3055 rs6000_cost = &ppc440_cost;
3056 break;
3057
3058 case PROCESSOR_PPC476:
3059 rs6000_cost = &ppc476_cost;
3060 break;
3061
3062 case PROCESSOR_PPC601:
3063 rs6000_cost = &ppc601_cost;
3064 break;
3065
3066 case PROCESSOR_PPC603:
3067 rs6000_cost = &ppc603_cost;
3068 break;
3069
3070 case PROCESSOR_PPC604:
3071 rs6000_cost = &ppc604_cost;
3072 break;
3073
3074 case PROCESSOR_PPC604e:
3075 rs6000_cost = &ppc604e_cost;
3076 break;
3077
3078 case PROCESSOR_PPC620:
3079 rs6000_cost = &ppc620_cost;
3080 break;
3081
3082 case PROCESSOR_PPC630:
3083 rs6000_cost = &ppc630_cost;
3084 break;
3085
3086 case PROCESSOR_CELL:
3087 rs6000_cost = &ppccell_cost;
3088 break;
3089
3090 case PROCESSOR_PPC750:
3091 case PROCESSOR_PPC7400:
3092 rs6000_cost = &ppc750_cost;
3093 break;
3094
3095 case PROCESSOR_PPC7450:
3096 rs6000_cost = &ppc7450_cost;
3097 break;
3098
3099 case PROCESSOR_PPC8540:
3100 rs6000_cost = &ppc8540_cost;
3101 break;
3102
3103 case PROCESSOR_PPCE300C2:
3104 case PROCESSOR_PPCE300C3:
3105 rs6000_cost = &ppce300c2c3_cost;
3106 break;
3107
3108 case PROCESSOR_PPCE500MC:
3109 rs6000_cost = &ppce500mc_cost;
3110 break;
3111
3112 case PROCESSOR_PPCE500MC64:
3113 rs6000_cost = &ppce500mc64_cost;
3114 break;
3115
3116 case PROCESSOR_TITAN:
3117 rs6000_cost = &titan_cost;
3118 break;
3119
3120 case PROCESSOR_POWER4:
3121 case PROCESSOR_POWER5:
3122 rs6000_cost = &power4_cost;
3123 break;
3124
3125 case PROCESSOR_POWER6:
3126 rs6000_cost = &power6_cost;
3127 break;
3128
3129 case PROCESSOR_POWER7:
3130 rs6000_cost = &power7_cost;
3131 break;
3132
3133 case PROCESSOR_PPCA2:
3134 rs6000_cost = &ppca2_cost;
3135 break;
3136
3137 default:
3138 gcc_unreachable ();
3139 }
3140
3141 if (!PARAM_SET_P (PARAM_SIMULTANEOUS_PREFETCHES))
3142 set_param_value ("simultaneous-prefetches",
3143 rs6000_cost->simultaneous_prefetches);
3144 if (!PARAM_SET_P (PARAM_L1_CACHE_SIZE))
3145 set_param_value ("l1-cache-size", rs6000_cost->l1_cache_size);
3146 if (!PARAM_SET_P (PARAM_L1_CACHE_LINE_SIZE))
3147 set_param_value ("l1-cache-line-size", rs6000_cost->cache_line_size);
3148 if (!PARAM_SET_P (PARAM_L2_CACHE_SIZE))
3149 set_param_value ("l2-cache-size", rs6000_cost->l2_cache_size);
3150
3151 /* If using typedef char *va_list, signal that __builtin_va_start (&ap, 0)
3152 can be optimized to ap = __builtin_next_arg (0). */
3153 if (DEFAULT_ABI != ABI_V4)
3154 targetm.expand_builtin_va_start = NULL;
3155
3156 /* Set up single/double float flags.
3157 If TARGET_HARD_FLOAT is set, but neither single or double is set,
3158 then set both flags. */
3159 if (TARGET_HARD_FLOAT && TARGET_FPRS
3160 && rs6000_single_float == 0 && rs6000_double_float == 0)
3161 rs6000_single_float = rs6000_double_float = 1;
3162
3163 /* Reset single and double FP flags if target is E500. */
3164 if (TARGET_E500)
3165 {
3166 rs6000_single_float = rs6000_double_float = 0;
3167 if (TARGET_E500_SINGLE)
3168 rs6000_single_float = 1;
3169 if (TARGET_E500_DOUBLE)
3170 rs6000_single_float = rs6000_double_float = 1;
3171 }
3172
3173 /* If not explicitly specified via option, decide whether to generate indexed
3174 load/store instructions. */
3175 if (TARGET_AVOID_XFORM == -1)
3176 /* Avoid indexed addressing when targeting Power6 in order to avoid
3177 the DERAT mispredict penalty. */
3178 TARGET_AVOID_XFORM = (rs6000_cpu == PROCESSOR_POWER6 && TARGET_CMPB);
3179
3180 /* Set the -mrecip options. */
3181 if (rs6000_recip_name)
3182 {
3183 char *p = ASTRDUP (rs6000_recip_name);
3184 char *q;
3185 unsigned int mask, i;
3186 bool invert;
3187
3188 while ((q = strtok (p, ",")) != NULL)
3189 {
3190 p = NULL;
3191 if (*q == '!')
3192 {
3193 invert = true;
3194 q++;
3195 }
3196 else
3197 invert = false;
3198
3199 if (!strcmp (q, "default"))
3200 mask = ((TARGET_RECIP_PRECISION)
3201 ? RECIP_HIGH_PRECISION : RECIP_LOW_PRECISION);
3202 else
3203 {
3204 for (i = 0; i < ARRAY_SIZE (recip_options); i++)
3205 if (!strcmp (q, recip_options[i].string))
3206 {
3207 mask = recip_options[i].mask;
3208 break;
3209 }
3210
3211 if (i == ARRAY_SIZE (recip_options))
3212 {
3213 error ("Unknown option for -mrecip=%s", q);
3214 invert = false;
3215 mask = 0;
3216 }
3217 }
3218
3219 if (invert)
3220 rs6000_recip_control &= ~mask;
3221 else
3222 rs6000_recip_control |= mask;
3223 }
3224 }
3225
3226 rs6000_init_hard_regno_mode_ok ();
3227 }
3228
3229 /* Implement targetm.vectorize.builtin_mask_for_load. */
3230 static tree
3231 rs6000_builtin_mask_for_load (void)
3232 {
3233 if (TARGET_ALTIVEC || TARGET_VSX)
3234 return altivec_builtin_mask_for_load;
3235 else
3236 return 0;
3237 }
3238
3239 /* Implement targetm.vectorize.builtin_conversion.
3240 Returns a decl of a function that implements conversion of an integer vector
3241 into a floating-point vector, or vice-versa. DEST_TYPE is the
3242 destination type and SRC_TYPE the source type of the conversion.
3243 Return NULL_TREE if it is not available. */
3244 static tree
3245 rs6000_builtin_conversion (unsigned int tcode, tree dest_type, tree src_type)
3246 {
3247 enum tree_code code = (enum tree_code) tcode;
3248
3249 switch (code)
3250 {
3251 case FIX_TRUNC_EXPR:
3252 switch (TYPE_MODE (dest_type))
3253 {
3254 case V2DImode:
3255 if (!VECTOR_UNIT_VSX_P (V2DFmode))
3256 return NULL_TREE;
3257
3258 return TYPE_UNSIGNED (dest_type)
3259 ? rs6000_builtin_decls[VSX_BUILTIN_XVCVDPUXDS_UNS]
3260 : rs6000_builtin_decls[VSX_BUILTIN_XVCVDPSXDS];
3261
3262 case V4SImode:
3263 if (VECTOR_UNIT_NONE_P (V4SImode) || VECTOR_UNIT_NONE_P (V4SFmode))
3264 return NULL_TREE;
3265
3266 return TYPE_UNSIGNED (dest_type)
3267 ? rs6000_builtin_decls[VECTOR_BUILTIN_FIXUNS_V4SF_V4SI]
3268 : rs6000_builtin_decls[VECTOR_BUILTIN_FIX_V4SF_V4SI];
3269
3270 default:
3271 return NULL_TREE;
3272 }
3273
3274 case FLOAT_EXPR:
3275 switch (TYPE_MODE (src_type))
3276 {
3277 case V2DImode:
3278 if (!VECTOR_UNIT_VSX_P (V2DFmode))
3279 return NULL_TREE;
3280
3281 return TYPE_UNSIGNED (src_type)
3282 ? rs6000_builtin_decls[VSX_BUILTIN_XVCVUXDDP]
3283 : rs6000_builtin_decls[VSX_BUILTIN_XVCVSXDDP];
3284
3285 case V4SImode:
3286 if (VECTOR_UNIT_NONE_P (V4SImode) || VECTOR_UNIT_NONE_P (V4SFmode))
3287 return NULL_TREE;
3288
3289 return TYPE_UNSIGNED (src_type)
3290 ? rs6000_builtin_decls[VECTOR_BUILTIN_UNSFLOAT_V4SI_V4SF]
3291 : rs6000_builtin_decls[VECTOR_BUILTIN_FLOAT_V4SI_V4SF];
3292
3293 default:
3294 return NULL_TREE;
3295 }
3296
3297 default:
3298 return NULL_TREE;
3299 }
3300 }
3301
3302 /* Implement targetm.vectorize.builtin_mul_widen_even. */
3303 static tree
3304 rs6000_builtin_mul_widen_even (tree type)
3305 {
3306 if (!TARGET_ALTIVEC)
3307 return NULL_TREE;
3308
3309 switch (TYPE_MODE (type))
3310 {
3311 case V8HImode:
3312 return TYPE_UNSIGNED (type)
3313 ? rs6000_builtin_decls[ALTIVEC_BUILTIN_VMULEUH_UNS]
3314 : rs6000_builtin_decls[ALTIVEC_BUILTIN_VMULESH];
3315
3316 case V16QImode:
3317 return TYPE_UNSIGNED (type)
3318 ? rs6000_builtin_decls[ALTIVEC_BUILTIN_VMULEUB_UNS]
3319 : rs6000_builtin_decls[ALTIVEC_BUILTIN_VMULESB];
3320 default:
3321 return NULL_TREE;
3322 }
3323 }
3324
3325 /* Implement targetm.vectorize.builtin_mul_widen_odd. */
3326 static tree
3327 rs6000_builtin_mul_widen_odd (tree type)
3328 {
3329 if (!TARGET_ALTIVEC)
3330 return NULL_TREE;
3331
3332 switch (TYPE_MODE (type))
3333 {
3334 case V8HImode:
3335 return TYPE_UNSIGNED (type)
3336 ? rs6000_builtin_decls[ALTIVEC_BUILTIN_VMULOUH_UNS]
3337 : rs6000_builtin_decls[ALTIVEC_BUILTIN_VMULOSH];
3338
3339 case V16QImode:
3340 return TYPE_UNSIGNED (type)
3341 ? rs6000_builtin_decls[ALTIVEC_BUILTIN_VMULOUB_UNS]
3342 : rs6000_builtin_decls[ALTIVEC_BUILTIN_VMULOSB];
3343 default:
3344 return NULL_TREE;
3345 }
3346 }
3347
3348
3349 /* Return true iff, data reference of TYPE can reach vector alignment (16)
3350 after applying N number of iterations. This routine does not determine
3351 how may iterations are required to reach desired alignment. */
3352
3353 static bool
3354 rs6000_vector_alignment_reachable (const_tree type ATTRIBUTE_UNUSED, bool is_packed)
3355 {
3356 if (is_packed)
3357 return false;
3358
3359 if (TARGET_32BIT)
3360 {
3361 if (rs6000_alignment_flags == MASK_ALIGN_NATURAL)
3362 return true;
3363
3364 if (rs6000_alignment_flags == MASK_ALIGN_POWER)
3365 return true;
3366
3367 return false;
3368 }
3369 else
3370 {
3371 if (TARGET_MACHO)
3372 return false;
3373
3374 /* Assuming that all other types are naturally aligned. CHECKME! */
3375 return true;
3376 }
3377 }
3378
3379 /* Return true if the vector misalignment factor is supported by the
3380 target. */
3381 bool
3382 rs6000_builtin_support_vector_misalignment (enum machine_mode mode,
3383 const_tree type,
3384 int misalignment,
3385 bool is_packed)
3386 {
3387 if (TARGET_VSX)
3388 {
3389 /* Return if movmisalign pattern is not supported for this mode. */
3390 if (optab_handler (movmisalign_optab, mode) == CODE_FOR_nothing)
3391 return false;
3392
3393 if (misalignment == -1)
3394 {
3395 /* Misalignment factor is unknown at compile time but we know
3396 it's word aligned. */
3397 if (rs6000_vector_alignment_reachable (type, is_packed))
3398 {
3399 int element_size = TREE_INT_CST_LOW (TYPE_SIZE (type));
3400
3401 if (element_size == 64 || element_size == 32)
3402 return true;
3403 }
3404
3405 return false;
3406 }
3407
3408 /* VSX supports word-aligned vector. */
3409 if (misalignment % 4 == 0)
3410 return true;
3411 }
3412 return false;
3413 }
3414
3415 /* Implement targetm.vectorize.builtin_vec_perm. */
3416 tree
3417 rs6000_builtin_vec_perm (tree type, tree *mask_element_type)
3418 {
3419 tree inner_type = TREE_TYPE (type);
3420 bool uns_p = TYPE_UNSIGNED (inner_type);
3421 tree d;
3422
3423 *mask_element_type = unsigned_char_type_node;
3424
3425 switch (TYPE_MODE (type))
3426 {
3427 case V16QImode:
3428 d = (uns_p
3429 ? rs6000_builtin_decls[ALTIVEC_BUILTIN_VPERM_16QI_UNS]
3430 : rs6000_builtin_decls[ALTIVEC_BUILTIN_VPERM_16QI]);
3431 break;
3432
3433 case V8HImode:
3434 d = (uns_p
3435 ? rs6000_builtin_decls[ALTIVEC_BUILTIN_VPERM_8HI_UNS]
3436 : rs6000_builtin_decls[ALTIVEC_BUILTIN_VPERM_8HI]);
3437 break;
3438
3439 case V4SImode:
3440 d = (uns_p
3441 ? rs6000_builtin_decls[ALTIVEC_BUILTIN_VPERM_4SI_UNS]
3442 : rs6000_builtin_decls[ALTIVEC_BUILTIN_VPERM_4SI]);
3443 break;
3444
3445 case V4SFmode:
3446 d = rs6000_builtin_decls[ALTIVEC_BUILTIN_VPERM_4SF];
3447 break;
3448
3449 case V2DFmode:
3450 if (!TARGET_ALLOW_DF_PERMUTE)
3451 return NULL_TREE;
3452
3453 d = rs6000_builtin_decls[ALTIVEC_BUILTIN_VPERM_2DF];
3454 break;
3455
3456 case V2DImode:
3457 if (!TARGET_ALLOW_DF_PERMUTE)
3458 return NULL_TREE;
3459
3460 d = (uns_p
3461 ? rs6000_builtin_decls[ALTIVEC_BUILTIN_VPERM_2DI_UNS]
3462 : rs6000_builtin_decls[ALTIVEC_BUILTIN_VPERM_2DI]);
3463 break;
3464
3465 default:
3466 return NULL_TREE;
3467 }
3468
3469 gcc_assert (d);
3470 return d;
3471 }
3472
3473
3474 /* Implement targetm.vectorize.builtin_vectorization_cost. */
3475 static int
3476 rs6000_builtin_vectorization_cost (enum vect_cost_for_stmt type_of_cost,
3477 tree vectype, int misalign)
3478 {
3479 unsigned elements;
3480
3481 switch (type_of_cost)
3482 {
3483 case scalar_stmt:
3484 case scalar_load:
3485 case scalar_store:
3486 case vector_stmt:
3487 case vector_load:
3488 case vector_store:
3489 case vec_to_scalar:
3490 case scalar_to_vec:
3491 case cond_branch_not_taken:
3492 case vec_perm:
3493 return 1;
3494
3495 case cond_branch_taken:
3496 return 3;
3497
3498 case unaligned_load:
3499 if (TARGET_VSX && TARGET_ALLOW_MOVMISALIGN)
3500 {
3501 elements = TYPE_VECTOR_SUBPARTS (vectype);
3502 if (elements == 2)
3503 /* Double word aligned. */
3504 return 2;
3505
3506 if (elements == 4)
3507 {
3508 switch (misalign)
3509 {
3510 case 8:
3511 /* Double word aligned. */
3512 return 2;
3513
3514 case -1:
3515 /* Unknown misalignment. */
3516 case 4:
3517 case 12:
3518 /* Word aligned. */
3519 return 22;
3520
3521 default:
3522 gcc_unreachable ();
3523 }
3524 }
3525 }
3526
3527 if (TARGET_ALTIVEC)
3528 /* Misaligned loads are not supported. */
3529 gcc_unreachable ();
3530
3531 return 2;
3532
3533 case unaligned_store:
3534 if (TARGET_VSX && TARGET_ALLOW_MOVMISALIGN)
3535 {
3536 elements = TYPE_VECTOR_SUBPARTS (vectype);
3537 if (elements == 2)
3538 /* Double word aligned. */
3539 return 2;
3540
3541 if (elements == 4)
3542 {
3543 switch (misalign)
3544 {
3545 case 8:
3546 /* Double word aligned. */
3547 return 2;
3548
3549 case -1:
3550 /* Unknown misalignment. */
3551 case 4:
3552 case 12:
3553 /* Word aligned. */
3554 return 23;
3555
3556 default:
3557 gcc_unreachable ();
3558 }
3559 }
3560 }
3561
3562 if (TARGET_ALTIVEC)
3563 /* Misaligned stores are not supported. */
3564 gcc_unreachable ();
3565
3566 return 2;
3567
3568 default:
3569 gcc_unreachable ();
3570 }
3571 }
3572
3573 /* Handle generic options of the form -mfoo=yes/no.
3574 NAME is the option name.
3575 VALUE is the option value.
3576 FLAG is the pointer to the flag where to store a 1 or 0, depending on
3577 whether the option value is 'yes' or 'no' respectively. */
3578 static void
3579 rs6000_parse_yes_no_option (const char *name, const char *value, int *flag)
3580 {
3581 if (value == 0)
3582 return;
3583 else if (!strcmp (value, "yes"))
3584 *flag = 1;
3585 else if (!strcmp (value, "no"))
3586 *flag = 0;
3587 else
3588 error ("unknown -m%s= option specified: '%s'", name, value);
3589 }
3590
3591 /* Validate and record the size specified with the -mtls-size option. */
3592
3593 static void
3594 rs6000_parse_tls_size_option (void)
3595 {
3596 if (rs6000_tls_size_string == 0)
3597 return;
3598 else if (strcmp (rs6000_tls_size_string, "16") == 0)
3599 rs6000_tls_size = 16;
3600 else if (strcmp (rs6000_tls_size_string, "32") == 0)
3601 rs6000_tls_size = 32;
3602 else if (strcmp (rs6000_tls_size_string, "64") == 0)
3603 rs6000_tls_size = 64;
3604 else
3605 error ("bad value %qs for -mtls-size switch", rs6000_tls_size_string);
3606 }
3607
3608 void
3609 optimization_options (int level ATTRIBUTE_UNUSED, int size ATTRIBUTE_UNUSED)
3610 {
3611 if (DEFAULT_ABI == ABI_DARWIN)
3612 /* The Darwin libraries never set errno, so we might as well
3613 avoid calling them when that's the only reason we would. */
3614 flag_errno_math = 0;
3615
3616 /* Double growth factor to counter reduced min jump length. */
3617 set_param_value ("max-grow-copy-bb-insns", 16);
3618
3619 /* Enable section anchors by default.
3620 Skip section anchors for Objective C and Objective C++
3621 until front-ends fixed. */
3622 if (!TARGET_MACHO && lang_hooks.name[4] != 'O')
3623 flag_section_anchors = 2;
3624 }
3625
3626 static enum fpu_type_t
3627 rs6000_parse_fpu_option (const char *option)
3628 {
3629 if (!strcmp("none", option)) return FPU_NONE;
3630 if (!strcmp("sp_lite", option)) return FPU_SF_LITE;
3631 if (!strcmp("dp_lite", option)) return FPU_DF_LITE;
3632 if (!strcmp("sp_full", option)) return FPU_SF_FULL;
3633 if (!strcmp("dp_full", option)) return FPU_DF_FULL;
3634 error("unknown value %s for -mfpu", option);
3635 return FPU_NONE;
3636 }
3637
3638
3639 /* Handler for the Mathematical Acceleration Subsystem (mass) interface to a
3640 library with vectorized intrinsics. */
3641
3642 static tree
3643 rs6000_builtin_vectorized_libmass (tree fndecl, tree type_out, tree type_in)
3644 {
3645 char name[32];
3646 const char *suffix = NULL;
3647 tree fntype, new_fndecl, bdecl = NULL_TREE;
3648 int n_args = 1;
3649 const char *bname;
3650 enum machine_mode el_mode, in_mode;
3651 int n, in_n;
3652
3653 /* Libmass is suitable for unsafe math only as it does not correctly support
3654 parts of IEEE with the required precision such as denormals. Only support
3655 it if we have VSX to use the simd d2 or f4 functions.
3656 XXX: Add variable length support. */
3657 if (!flag_unsafe_math_optimizations || !TARGET_VSX)
3658 return NULL_TREE;
3659
3660 el_mode = TYPE_MODE (TREE_TYPE (type_out));
3661 n = TYPE_VECTOR_SUBPARTS (type_out);
3662 in_mode = TYPE_MODE (TREE_TYPE (type_in));
3663 in_n = TYPE_VECTOR_SUBPARTS (type_in);
3664 if (el_mode != in_mode
3665 || n != in_n)
3666 return NULL_TREE;
3667
3668 if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_NORMAL)
3669 {
3670 enum built_in_function fn = DECL_FUNCTION_CODE (fndecl);
3671 switch (fn)
3672 {
3673 case BUILT_IN_ATAN2:
3674 case BUILT_IN_HYPOT:
3675 case BUILT_IN_POW:
3676 n_args = 2;
3677 /* fall through */
3678
3679 case BUILT_IN_ACOS:
3680 case BUILT_IN_ACOSH:
3681 case BUILT_IN_ASIN:
3682 case BUILT_IN_ASINH:
3683 case BUILT_IN_ATAN:
3684 case BUILT_IN_ATANH:
3685 case BUILT_IN_CBRT:
3686 case BUILT_IN_COS:
3687 case BUILT_IN_COSH:
3688 case BUILT_IN_ERF:
3689 case BUILT_IN_ERFC:
3690 case BUILT_IN_EXP2:
3691 case BUILT_IN_EXP:
3692 case BUILT_IN_EXPM1:
3693 case BUILT_IN_LGAMMA:
3694 case BUILT_IN_LOG10:
3695 case BUILT_IN_LOG1P:
3696 case BUILT_IN_LOG2:
3697 case BUILT_IN_LOG:
3698 case BUILT_IN_SIN:
3699 case BUILT_IN_SINH:
3700 case BUILT_IN_SQRT:
3701 case BUILT_IN_TAN:
3702 case BUILT_IN_TANH:
3703 bdecl = implicit_built_in_decls[fn];
3704 suffix = "d2"; /* pow -> powd2 */
3705 if (el_mode != DFmode
3706 || n != 2)
3707 return NULL_TREE;
3708 break;
3709
3710 case BUILT_IN_ATAN2F:
3711 case BUILT_IN_HYPOTF:
3712 case BUILT_IN_POWF:
3713 n_args = 2;
3714 /* fall through */
3715
3716 case BUILT_IN_ACOSF:
3717 case BUILT_IN_ACOSHF:
3718 case BUILT_IN_ASINF:
3719 case BUILT_IN_ASINHF:
3720 case BUILT_IN_ATANF:
3721 case BUILT_IN_ATANHF:
3722 case BUILT_IN_CBRTF:
3723 case BUILT_IN_COSF:
3724 case BUILT_IN_COSHF:
3725 case BUILT_IN_ERFF:
3726 case BUILT_IN_ERFCF:
3727 case BUILT_IN_EXP2F:
3728 case BUILT_IN_EXPF:
3729 case BUILT_IN_EXPM1F:
3730 case BUILT_IN_LGAMMAF:
3731 case BUILT_IN_LOG10F:
3732 case BUILT_IN_LOG1PF:
3733 case BUILT_IN_LOG2F:
3734 case BUILT_IN_LOGF:
3735 case BUILT_IN_SINF:
3736 case BUILT_IN_SINHF:
3737 case BUILT_IN_SQRTF:
3738 case BUILT_IN_TANF:
3739 case BUILT_IN_TANHF:
3740 bdecl = implicit_built_in_decls[fn];
3741 suffix = "4"; /* powf -> powf4 */
3742 if (el_mode != SFmode
3743 || n != 4)
3744 return NULL_TREE;
3745 break;
3746
3747 default:
3748 return NULL_TREE;
3749 }
3750 }
3751 else
3752 return NULL_TREE;
3753
3754 gcc_assert (suffix != NULL);
3755 bname = IDENTIFIER_POINTER (DECL_NAME (bdecl));
3756 strcpy (name, bname + sizeof ("__builtin_") - 1);
3757 strcat (name, suffix);
3758
3759 if (n_args == 1)
3760 fntype = build_function_type_list (type_out, type_in, NULL);
3761 else if (n_args == 2)
3762 fntype = build_function_type_list (type_out, type_in, type_in, NULL);
3763 else
3764 gcc_unreachable ();
3765
3766 /* Build a function declaration for the vectorized function. */
3767 new_fndecl = build_decl (BUILTINS_LOCATION,
3768 FUNCTION_DECL, get_identifier (name), fntype);
3769 TREE_PUBLIC (new_fndecl) = 1;
3770 DECL_EXTERNAL (new_fndecl) = 1;
3771 DECL_IS_NOVOPS (new_fndecl) = 1;
3772 TREE_READONLY (new_fndecl) = 1;
3773
3774 return new_fndecl;
3775 }
3776
3777 /* Returns a function decl for a vectorized version of the builtin function
3778 with builtin function code FN and the result vector type TYPE, or NULL_TREE
3779 if it is not available. */
3780
3781 static tree
3782 rs6000_builtin_vectorized_function (tree fndecl, tree type_out,
3783 tree type_in)
3784 {
3785 enum machine_mode in_mode, out_mode;
3786 int in_n, out_n;
3787
3788 if (TREE_CODE (type_out) != VECTOR_TYPE
3789 || TREE_CODE (type_in) != VECTOR_TYPE
3790 || !TARGET_VECTORIZE_BUILTINS)
3791 return NULL_TREE;
3792
3793 out_mode = TYPE_MODE (TREE_TYPE (type_out));
3794 out_n = TYPE_VECTOR_SUBPARTS (type_out);
3795 in_mode = TYPE_MODE (TREE_TYPE (type_in));
3796 in_n = TYPE_VECTOR_SUBPARTS (type_in);
3797
3798 if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_NORMAL)
3799 {
3800 enum built_in_function fn = DECL_FUNCTION_CODE (fndecl);
3801 switch (fn)
3802 {
3803 case BUILT_IN_COPYSIGN:
3804 if (VECTOR_UNIT_VSX_P (V2DFmode)
3805 && out_mode == DFmode && out_n == 2
3806 && in_mode == DFmode && in_n == 2)
3807 return rs6000_builtin_decls[VSX_BUILTIN_CPSGNDP];
3808 break;
3809 case BUILT_IN_COPYSIGNF:
3810 if (out_mode != SFmode || out_n != 4
3811 || in_mode != SFmode || in_n != 4)
3812 break;
3813 if (VECTOR_UNIT_VSX_P (V4SFmode))
3814 return rs6000_builtin_decls[VSX_BUILTIN_CPSGNSP];
3815 if (VECTOR_UNIT_ALTIVEC_P (V4SFmode))
3816 return rs6000_builtin_decls[ALTIVEC_BUILTIN_COPYSIGN_V4SF];
3817 break;
3818 case BUILT_IN_SQRT:
3819 if (VECTOR_UNIT_VSX_P (V2DFmode)
3820 && out_mode == DFmode && out_n == 2
3821 && in_mode == DFmode && in_n == 2)
3822 return rs6000_builtin_decls[VSX_BUILTIN_XVSQRTDP];
3823 break;
3824 case BUILT_IN_SQRTF:
3825 if (VECTOR_UNIT_VSX_P (V4SFmode)
3826 && out_mode == SFmode && out_n == 4
3827 && in_mode == SFmode && in_n == 4)
3828 return rs6000_builtin_decls[VSX_BUILTIN_XVSQRTSP];
3829 break;
3830 case BUILT_IN_CEIL:
3831 if (VECTOR_UNIT_VSX_P (V2DFmode)
3832 && out_mode == DFmode && out_n == 2
3833 && in_mode == DFmode && in_n == 2)
3834 return rs6000_builtin_decls[VSX_BUILTIN_XVRDPIP];
3835 break;
3836 case BUILT_IN_CEILF:
3837 if (out_mode != SFmode || out_n != 4
3838 || in_mode != SFmode || in_n != 4)
3839 break;
3840 if (VECTOR_UNIT_VSX_P (V4SFmode))
3841 return rs6000_builtin_decls[VSX_BUILTIN_XVRSPIP];
3842 if (VECTOR_UNIT_ALTIVEC_P (V4SFmode))
3843 return rs6000_builtin_decls[ALTIVEC_BUILTIN_VRFIP];
3844 break;
3845 case BUILT_IN_FLOOR:
3846 if (VECTOR_UNIT_VSX_P (V2DFmode)
3847 && out_mode == DFmode && out_n == 2
3848 && in_mode == DFmode && in_n == 2)
3849 return rs6000_builtin_decls[VSX_BUILTIN_XVRDPIM];
3850 break;
3851 case BUILT_IN_FLOORF:
3852 if (out_mode != SFmode || out_n != 4
3853 || in_mode != SFmode || in_n != 4)
3854 break;
3855 if (VECTOR_UNIT_VSX_P (V4SFmode))
3856 return rs6000_builtin_decls[VSX_BUILTIN_XVRSPIM];
3857 if (VECTOR_UNIT_ALTIVEC_P (V4SFmode))
3858 return rs6000_builtin_decls[ALTIVEC_BUILTIN_VRFIM];
3859 break;
3860 case BUILT_IN_TRUNC:
3861 if (VECTOR_UNIT_VSX_P (V2DFmode)
3862 && out_mode == DFmode && out_n == 2
3863 && in_mode == DFmode && in_n == 2)
3864 return rs6000_builtin_decls[VSX_BUILTIN_XVRDPIZ];
3865 break;
3866 case BUILT_IN_TRUNCF:
3867 if (out_mode != SFmode || out_n != 4
3868 || in_mode != SFmode || in_n != 4)
3869 break;
3870 if (VECTOR_UNIT_VSX_P (V4SFmode))
3871 return rs6000_builtin_decls[VSX_BUILTIN_XVRSPIZ];
3872 if (VECTOR_UNIT_ALTIVEC_P (V4SFmode))
3873 return rs6000_builtin_decls[ALTIVEC_BUILTIN_VRFIZ];
3874 break;
3875 case BUILT_IN_NEARBYINT:
3876 if (VECTOR_UNIT_VSX_P (V2DFmode)
3877 && flag_unsafe_math_optimizations
3878 && out_mode == DFmode && out_n == 2
3879 && in_mode == DFmode && in_n == 2)
3880 return rs6000_builtin_decls[VSX_BUILTIN_XVRDPI];
3881 break;
3882 case BUILT_IN_NEARBYINTF:
3883 if (VECTOR_UNIT_VSX_P (V4SFmode)
3884 && flag_unsafe_math_optimizations
3885 && out_mode == SFmode && out_n == 4
3886 && in_mode == SFmode && in_n == 4)
3887 return rs6000_builtin_decls[VSX_BUILTIN_XVRSPI];
3888 break;
3889 case BUILT_IN_RINT:
3890 if (VECTOR_UNIT_VSX_P (V2DFmode)
3891 && !flag_trapping_math
3892 && out_mode == DFmode && out_n == 2
3893 && in_mode == DFmode && in_n == 2)
3894 return rs6000_builtin_decls[VSX_BUILTIN_XVRDPIC];
3895 break;
3896 case BUILT_IN_RINTF:
3897 if (VECTOR_UNIT_VSX_P (V4SFmode)
3898 && !flag_trapping_math
3899 && out_mode == SFmode && out_n == 4
3900 && in_mode == SFmode && in_n == 4)
3901 return rs6000_builtin_decls[VSX_BUILTIN_XVRSPIC];
3902 break;
3903 default:
3904 break;
3905 }
3906 }
3907
3908 else if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
3909 {
3910 enum rs6000_builtins fn
3911 = (enum rs6000_builtins)DECL_FUNCTION_CODE (fndecl);
3912 switch (fn)
3913 {
3914 case RS6000_BUILTIN_RSQRTF:
3915 if (VECTOR_UNIT_ALTIVEC_OR_VSX_P (V4SFmode)
3916 && out_mode == SFmode && out_n == 4
3917 && in_mode == SFmode && in_n == 4)
3918 return rs6000_builtin_decls[ALTIVEC_BUILTIN_VRSQRTFP];
3919 break;
3920 case RS6000_BUILTIN_RSQRT:
3921 if (VECTOR_UNIT_VSX_P (V2DFmode)
3922 && out_mode == DFmode && out_n == 2
3923 && in_mode == DFmode && in_n == 2)
3924 return rs6000_builtin_decls[VSX_BUILTIN_VEC_RSQRT_V2DF];
3925 break;
3926 case RS6000_BUILTIN_RECIPF:
3927 if (VECTOR_UNIT_ALTIVEC_OR_VSX_P (V4SFmode)
3928 && out_mode == SFmode && out_n == 4
3929 && in_mode == SFmode && in_n == 4)
3930 return rs6000_builtin_decls[ALTIVEC_BUILTIN_VRECIPFP];
3931 break;
3932 case RS6000_BUILTIN_RECIP:
3933 if (VECTOR_UNIT_VSX_P (V2DFmode)
3934 && out_mode == DFmode && out_n == 2
3935 && in_mode == DFmode && in_n == 2)
3936 return rs6000_builtin_decls[VSX_BUILTIN_RECIP_V2DF];
3937 break;
3938 default:
3939 break;
3940 }
3941 }
3942
3943 /* Generate calls to libmass if appropriate. */
3944 if (rs6000_veclib_handler)
3945 return rs6000_veclib_handler (fndecl, type_out, type_in);
3946
3947 return NULL_TREE;
3948 }
3949
3950
3951 /* Implement TARGET_HANDLE_OPTION. */
3952
3953 static bool
3954 rs6000_handle_option (size_t code, const char *arg, int value)
3955 {
3956 enum fpu_type_t fpu_type = FPU_NONE;
3957 int isel;
3958
3959 switch (code)
3960 {
3961 case OPT_G:
3962 g_switch_value = value;
3963 g_switch_set = true;
3964 break;
3965
3966 case OPT_mno_power:
3967 target_flags &= ~(MASK_POWER | MASK_POWER2
3968 | MASK_MULTIPLE | MASK_STRING);
3969 target_flags_explicit |= (MASK_POWER | MASK_POWER2
3970 | MASK_MULTIPLE | MASK_STRING);
3971 break;
3972 case OPT_mno_powerpc:
3973 target_flags &= ~(MASK_POWERPC | MASK_PPC_GPOPT
3974 | MASK_PPC_GFXOPT | MASK_POWERPC64);
3975 target_flags_explicit |= (MASK_POWERPC | MASK_PPC_GPOPT
3976 | MASK_PPC_GFXOPT | MASK_POWERPC64);
3977 break;
3978 case OPT_mfull_toc:
3979 target_flags &= ~MASK_MINIMAL_TOC;
3980 TARGET_NO_FP_IN_TOC = 0;
3981 TARGET_NO_SUM_IN_TOC = 0;
3982 target_flags_explicit |= MASK_MINIMAL_TOC;
3983 #ifdef TARGET_USES_SYSV4_OPT
3984 /* Note, V.4 no longer uses a normal TOC, so make -mfull-toc, be
3985 just the same as -mminimal-toc. */
3986 target_flags |= MASK_MINIMAL_TOC;
3987 target_flags_explicit |= MASK_MINIMAL_TOC;
3988 #endif
3989 break;
3990
3991 #ifdef TARGET_USES_SYSV4_OPT
3992 case OPT_mtoc:
3993 /* Make -mtoc behave like -mminimal-toc. */
3994 target_flags |= MASK_MINIMAL_TOC;
3995 target_flags_explicit |= MASK_MINIMAL_TOC;
3996 break;
3997 #endif
3998
3999 #if defined (HAVE_LD_LARGE_TOC) && defined (TARGET_USES_LINUX64_OPT)
4000 case OPT_mcmodel_:
4001 if (strcmp (arg, "small") == 0)
4002 cmodel = CMODEL_SMALL;
4003 else if (strcmp (arg, "large") == 0)
4004 cmodel = CMODEL_LARGE;
4005 else
4006 {
4007 error ("invalid option for -mcmodel: '%s'", arg);
4008 return false;
4009 }
4010 rs6000_explicit_options.cmodel = true;
4011 #endif
4012
4013 #ifdef TARGET_USES_AIX64_OPT
4014 case OPT_maix64:
4015 #else
4016 case OPT_m64:
4017 #endif
4018 target_flags |= MASK_POWERPC64 | MASK_POWERPC;
4019 target_flags |= ~target_flags_explicit & MASK_PPC_GFXOPT;
4020 target_flags_explicit |= MASK_POWERPC64 | MASK_POWERPC;
4021 break;
4022
4023 #ifdef TARGET_USES_AIX64_OPT
4024 case OPT_maix32:
4025 #else
4026 case OPT_m32:
4027 #endif
4028 target_flags &= ~MASK_POWERPC64;
4029 target_flags_explicit |= MASK_POWERPC64;
4030 break;
4031
4032 case OPT_minsert_sched_nops_:
4033 rs6000_sched_insert_nops_str = arg;
4034 break;
4035
4036 case OPT_mminimal_toc:
4037 if (value == 1)
4038 {
4039 TARGET_NO_FP_IN_TOC = 0;
4040 TARGET_NO_SUM_IN_TOC = 0;
4041 }
4042 break;
4043
4044 case OPT_mpower:
4045 if (value == 1)
4046 {
4047 target_flags |= (MASK_MULTIPLE | MASK_STRING);
4048 target_flags_explicit |= (MASK_MULTIPLE | MASK_STRING);
4049 }
4050 break;
4051
4052 case OPT_mpower2:
4053 if (value == 1)
4054 {
4055 target_flags |= (MASK_POWER | MASK_MULTIPLE | MASK_STRING);
4056 target_flags_explicit |= (MASK_POWER | MASK_MULTIPLE | MASK_STRING);
4057 }
4058 break;
4059
4060 case OPT_mpowerpc_gpopt:
4061 case OPT_mpowerpc_gfxopt:
4062 if (value == 1)
4063 {
4064 target_flags |= MASK_POWERPC;
4065 target_flags_explicit |= MASK_POWERPC;
4066 }
4067 break;
4068
4069 case OPT_maix_struct_return:
4070 case OPT_msvr4_struct_return:
4071 rs6000_explicit_options.aix_struct_ret = true;
4072 break;
4073
4074 case OPT_mvrsave:
4075 rs6000_explicit_options.vrsave = true;
4076 TARGET_ALTIVEC_VRSAVE = value;
4077 break;
4078
4079 case OPT_mvrsave_:
4080 rs6000_explicit_options.vrsave = true;
4081 rs6000_parse_yes_no_option ("vrsave", arg, &(TARGET_ALTIVEC_VRSAVE));
4082 break;
4083
4084 case OPT_misel_:
4085 target_flags_explicit |= MASK_ISEL;
4086 isel = 0;
4087 rs6000_parse_yes_no_option ("isel", arg, &isel);
4088 if (isel)
4089 target_flags |= MASK_ISEL;
4090 else
4091 target_flags &= ~MASK_ISEL;
4092 break;
4093
4094 case OPT_mspe:
4095 rs6000_explicit_options.spe = true;
4096 rs6000_spe = value;
4097 break;
4098
4099 case OPT_mspe_:
4100 rs6000_explicit_options.spe = true;
4101 rs6000_parse_yes_no_option ("spe", arg, &(rs6000_spe));
4102 break;
4103
4104 case OPT_mdebug_:
4105 rs6000_debug_name = arg;
4106 break;
4107
4108 #ifdef TARGET_USES_SYSV4_OPT
4109 case OPT_mcall_:
4110 rs6000_abi_name = arg;
4111 break;
4112
4113 case OPT_msdata_:
4114 rs6000_sdata_name = arg;
4115 break;
4116
4117 case OPT_mtls_size_:
4118 rs6000_tls_size_string = arg;
4119 break;
4120
4121 case OPT_mrelocatable:
4122 if (value == 1)
4123 {
4124 target_flags |= MASK_MINIMAL_TOC;
4125 target_flags_explicit |= MASK_MINIMAL_TOC;
4126 TARGET_NO_FP_IN_TOC = 1;
4127 }
4128 break;
4129
4130 case OPT_mrelocatable_lib:
4131 if (value == 1)
4132 {
4133 target_flags |= MASK_RELOCATABLE | MASK_MINIMAL_TOC;
4134 target_flags_explicit |= MASK_RELOCATABLE | MASK_MINIMAL_TOC;
4135 TARGET_NO_FP_IN_TOC = 1;
4136 }
4137 else
4138 {
4139 target_flags &= ~MASK_RELOCATABLE;
4140 target_flags_explicit |= MASK_RELOCATABLE;
4141 }
4142 break;
4143 #endif
4144
4145 case OPT_mabi_:
4146 if (!strcmp (arg, "altivec"))
4147 {
4148 rs6000_explicit_options.altivec_abi = true;
4149 rs6000_altivec_abi = 1;
4150
4151 /* Enabling the AltiVec ABI turns off the SPE ABI. */
4152 rs6000_spe_abi = 0;
4153 }
4154 else if (! strcmp (arg, "no-altivec"))
4155 {
4156 rs6000_explicit_options.altivec_abi = true;
4157 rs6000_altivec_abi = 0;
4158 }
4159 else if (! strcmp (arg, "spe"))
4160 {
4161 rs6000_explicit_options.spe_abi = true;
4162 rs6000_spe_abi = 1;
4163 rs6000_altivec_abi = 0;
4164 if (!TARGET_SPE_ABI)
4165 error ("not configured for ABI: '%s'", arg);
4166 }
4167 else if (! strcmp (arg, "no-spe"))
4168 {
4169 rs6000_explicit_options.spe_abi = true;
4170 rs6000_spe_abi = 0;
4171 }
4172
4173 /* These are here for testing during development only, do not
4174 document in the manual please. */
4175 else if (! strcmp (arg, "d64"))
4176 {
4177 rs6000_darwin64_abi = 1;
4178 warning (0, "Using darwin64 ABI");
4179 }
4180 else if (! strcmp (arg, "d32"))
4181 {
4182 rs6000_darwin64_abi = 0;
4183 warning (0, "Using old darwin ABI");
4184 }
4185
4186 else if (! strcmp (arg, "ibmlongdouble"))
4187 {
4188 rs6000_explicit_options.ieee = true;
4189 rs6000_ieeequad = 0;
4190 warning (0, "Using IBM extended precision long double");
4191 }
4192 else if (! strcmp (arg, "ieeelongdouble"))
4193 {
4194 rs6000_explicit_options.ieee = true;
4195 rs6000_ieeequad = 1;
4196 warning (0, "Using IEEE extended precision long double");
4197 }
4198
4199 else
4200 {
4201 error ("unknown ABI specified: '%s'", arg);
4202 return false;
4203 }
4204 break;
4205
4206 case OPT_mcpu_:
4207 rs6000_select[1].string = arg;
4208 break;
4209
4210 case OPT_mtune_:
4211 rs6000_select[2].string = arg;
4212 break;
4213
4214 case OPT_mtraceback_:
4215 rs6000_traceback_name = arg;
4216 break;
4217
4218 case OPT_mfloat_gprs_:
4219 rs6000_explicit_options.float_gprs = true;
4220 if (! strcmp (arg, "yes") || ! strcmp (arg, "single"))
4221 rs6000_float_gprs = 1;
4222 else if (! strcmp (arg, "double"))
4223 rs6000_float_gprs = 2;
4224 else if (! strcmp (arg, "no"))
4225 rs6000_float_gprs = 0;
4226 else
4227 {
4228 error ("invalid option for -mfloat-gprs: '%s'", arg);
4229 return false;
4230 }
4231 break;
4232
4233 case OPT_mlong_double_:
4234 rs6000_explicit_options.long_double = true;
4235 rs6000_long_double_type_size = RS6000_DEFAULT_LONG_DOUBLE_SIZE;
4236 if (value != 64 && value != 128)
4237 {
4238 error ("Unknown switch -mlong-double-%s", arg);
4239 rs6000_long_double_type_size = RS6000_DEFAULT_LONG_DOUBLE_SIZE;
4240 return false;
4241 }
4242 else
4243 rs6000_long_double_type_size = value;
4244 break;
4245
4246 case OPT_msched_costly_dep_:
4247 rs6000_sched_costly_dep_str = arg;
4248 break;
4249
4250 case OPT_malign_:
4251 rs6000_explicit_options.alignment = true;
4252 if (! strcmp (arg, "power"))
4253 {
4254 /* On 64-bit Darwin, power alignment is ABI-incompatible with
4255 some C library functions, so warn about it. The flag may be
4256 useful for performance studies from time to time though, so
4257 don't disable it entirely. */
4258 if (DEFAULT_ABI == ABI_DARWIN && TARGET_64BIT)
4259 warning (0, "-malign-power is not supported for 64-bit Darwin;"
4260 " it is incompatible with the installed C and C++ libraries");
4261 rs6000_alignment_flags = MASK_ALIGN_POWER;
4262 }
4263 else if (! strcmp (arg, "natural"))
4264 rs6000_alignment_flags = MASK_ALIGN_NATURAL;
4265 else
4266 {
4267 error ("unknown -malign-XXXXX option specified: '%s'", arg);
4268 return false;
4269 }
4270 break;
4271
4272 case OPT_msingle_float:
4273 if (!TARGET_SINGLE_FPU)
4274 warning (0, "-msingle-float option equivalent to -mhard-float");
4275 /* -msingle-float implies -mno-double-float and TARGET_HARD_FLOAT. */
4276 rs6000_double_float = 0;
4277 target_flags &= ~MASK_SOFT_FLOAT;
4278 target_flags_explicit |= MASK_SOFT_FLOAT;
4279 break;
4280
4281 case OPT_mdouble_float:
4282 /* -mdouble-float implies -msingle-float and TARGET_HARD_FLOAT. */
4283 rs6000_single_float = 1;
4284 target_flags &= ~MASK_SOFT_FLOAT;
4285 target_flags_explicit |= MASK_SOFT_FLOAT;
4286 break;
4287
4288 case OPT_msimple_fpu:
4289 if (!TARGET_SINGLE_FPU)
4290 warning (0, "-msimple-fpu option ignored");
4291 break;
4292
4293 case OPT_mhard_float:
4294 /* -mhard_float implies -msingle-float and -mdouble-float. */
4295 rs6000_single_float = rs6000_double_float = 1;
4296 break;
4297
4298 case OPT_msoft_float:
4299 /* -msoft_float implies -mnosingle-float and -mnodouble-float. */
4300 rs6000_single_float = rs6000_double_float = 0;
4301 break;
4302
4303 case OPT_mfpu_:
4304 fpu_type = rs6000_parse_fpu_option(arg);
4305 if (fpu_type != FPU_NONE)
4306 /* If -mfpu is not none, then turn off SOFT_FLOAT, turn on HARD_FLOAT. */
4307 {
4308 target_flags &= ~MASK_SOFT_FLOAT;
4309 target_flags_explicit |= MASK_SOFT_FLOAT;
4310 rs6000_xilinx_fpu = 1;
4311 if (fpu_type == FPU_SF_LITE || fpu_type == FPU_SF_FULL)
4312 rs6000_single_float = 1;
4313 if (fpu_type == FPU_DF_LITE || fpu_type == FPU_DF_FULL)
4314 rs6000_single_float = rs6000_double_float = 1;
4315 if (fpu_type == FPU_SF_LITE || fpu_type == FPU_DF_LITE)
4316 rs6000_simple_fpu = 1;
4317 }
4318 else
4319 {
4320 /* -mfpu=none is equivalent to -msoft-float */
4321 target_flags |= MASK_SOFT_FLOAT;
4322 target_flags_explicit |= MASK_SOFT_FLOAT;
4323 rs6000_single_float = rs6000_double_float = 0;
4324 }
4325
4326 case OPT_mrecip:
4327 rs6000_recip_name = (value) ? "default" : "none";
4328 break;
4329
4330 case OPT_mrecip_:
4331 rs6000_recip_name = arg;
4332 break;
4333 }
4334 return true;
4335 }
4336 \f
4337 /* Do anything needed at the start of the asm file. */
4338
4339 static void
4340 rs6000_file_start (void)
4341 {
4342 size_t i;
4343 char buffer[80];
4344 const char *start = buffer;
4345 struct rs6000_cpu_select *ptr;
4346 const char *default_cpu = TARGET_CPU_DEFAULT;
4347 FILE *file = asm_out_file;
4348
4349 default_file_start ();
4350
4351 #ifdef TARGET_BI_ARCH
4352 if ((TARGET_DEFAULT ^ target_flags) & MASK_64BIT)
4353 default_cpu = 0;
4354 #endif
4355
4356 if (flag_verbose_asm)
4357 {
4358 sprintf (buffer, "\n%s rs6000/powerpc options:", ASM_COMMENT_START);
4359 rs6000_select[0].string = default_cpu;
4360
4361 for (i = 0; i < ARRAY_SIZE (rs6000_select); i++)
4362 {
4363 ptr = &rs6000_select[i];
4364 if (ptr->string != (char *)0 && ptr->string[0] != '\0')
4365 {
4366 fprintf (file, "%s %s%s", start, ptr->name, ptr->string);
4367 start = "";
4368 }
4369 }
4370
4371 if (PPC405_ERRATUM77)
4372 {
4373 fprintf (file, "%s PPC405CR_ERRATUM77", start);
4374 start = "";
4375 }
4376
4377 #ifdef USING_ELFOS_H
4378 switch (rs6000_sdata)
4379 {
4380 case SDATA_NONE: fprintf (file, "%s -msdata=none", start); start = ""; break;
4381 case SDATA_DATA: fprintf (file, "%s -msdata=data", start); start = ""; break;
4382 case SDATA_SYSV: fprintf (file, "%s -msdata=sysv", start); start = ""; break;
4383 case SDATA_EABI: fprintf (file, "%s -msdata=eabi", start); start = ""; break;
4384 }
4385
4386 if (rs6000_sdata && g_switch_value)
4387 {
4388 fprintf (file, "%s -G " HOST_WIDE_INT_PRINT_UNSIGNED, start,
4389 g_switch_value);
4390 start = "";
4391 }
4392 #endif
4393
4394 if (*start == '\0')
4395 putc ('\n', file);
4396 }
4397
4398 #ifdef HAVE_AS_GNU_ATTRIBUTE
4399 if (TARGET_32BIT && DEFAULT_ABI == ABI_V4)
4400 {
4401 fprintf (file, "\t.gnu_attribute 4, %d\n",
4402 ((TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT) ? 1
4403 : (TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT) ? 3
4404 : 2));
4405 fprintf (file, "\t.gnu_attribute 8, %d\n",
4406 (TARGET_ALTIVEC_ABI ? 2
4407 : TARGET_SPE_ABI ? 3
4408 : 1));
4409 fprintf (file, "\t.gnu_attribute 12, %d\n",
4410 aix_struct_return ? 2 : 1);
4411
4412 }
4413 #endif
4414
4415 if (DEFAULT_ABI == ABI_AIX || (TARGET_ELF && flag_pic == 2))
4416 {
4417 switch_to_section (toc_section);
4418 switch_to_section (text_section);
4419 }
4420 }
4421
4422 \f
4423 /* Return nonzero if this function is known to have a null epilogue. */
4424
4425 int
4426 direct_return (void)
4427 {
4428 if (reload_completed)
4429 {
4430 rs6000_stack_t *info = rs6000_stack_info ();
4431
4432 if (info->first_gp_reg_save == 32
4433 && info->first_fp_reg_save == 64
4434 && info->first_altivec_reg_save == LAST_ALTIVEC_REGNO + 1
4435 && ! info->lr_save_p
4436 && ! info->cr_save_p
4437 && info->vrsave_mask == 0
4438 && ! info->push_p)
4439 return 1;
4440 }
4441
4442 return 0;
4443 }
4444
4445 /* Return the number of instructions it takes to form a constant in an
4446 integer register. */
4447
4448 int
4449 num_insns_constant_wide (HOST_WIDE_INT value)
4450 {
4451 /* signed constant loadable with {cal|addi} */
4452 if ((unsigned HOST_WIDE_INT) (value + 0x8000) < 0x10000)
4453 return 1;
4454
4455 /* constant loadable with {cau|addis} */
4456 else if ((value & 0xffff) == 0
4457 && (value >> 31 == -1 || value >> 31 == 0))
4458 return 1;
4459
4460 #if HOST_BITS_PER_WIDE_INT == 64
4461 else if (TARGET_POWERPC64)
4462 {
4463 HOST_WIDE_INT low = ((value & 0xffffffff) ^ 0x80000000) - 0x80000000;
4464 HOST_WIDE_INT high = value >> 31;
4465
4466 if (high == 0 || high == -1)
4467 return 2;
4468
4469 high >>= 1;
4470
4471 if (low == 0)
4472 return num_insns_constant_wide (high) + 1;
4473 else if (high == 0)
4474 return num_insns_constant_wide (low) + 1;
4475 else
4476 return (num_insns_constant_wide (high)
4477 + num_insns_constant_wide (low) + 1);
4478 }
4479 #endif
4480
4481 else
4482 return 2;
4483 }
4484
4485 int
4486 num_insns_constant (rtx op, enum machine_mode mode)
4487 {
4488 HOST_WIDE_INT low, high;
4489
4490 switch (GET_CODE (op))
4491 {
4492 case CONST_INT:
4493 #if HOST_BITS_PER_WIDE_INT == 64
4494 if ((INTVAL (op) >> 31) != 0 && (INTVAL (op) >> 31) != -1
4495 && mask64_operand (op, mode))
4496 return 2;
4497 else
4498 #endif
4499 return num_insns_constant_wide (INTVAL (op));
4500
4501 case CONST_DOUBLE:
4502 if (mode == SFmode || mode == SDmode)
4503 {
4504 long l;
4505 REAL_VALUE_TYPE rv;
4506
4507 REAL_VALUE_FROM_CONST_DOUBLE (rv, op);
4508 if (DECIMAL_FLOAT_MODE_P (mode))
4509 REAL_VALUE_TO_TARGET_DECIMAL32 (rv, l);
4510 else
4511 REAL_VALUE_TO_TARGET_SINGLE (rv, l);
4512 return num_insns_constant_wide ((HOST_WIDE_INT) l);
4513 }
4514
4515 if (mode == VOIDmode || mode == DImode)
4516 {
4517 high = CONST_DOUBLE_HIGH (op);
4518 low = CONST_DOUBLE_LOW (op);
4519 }
4520 else
4521 {
4522 long l[2];
4523 REAL_VALUE_TYPE rv;
4524
4525 REAL_VALUE_FROM_CONST_DOUBLE (rv, op);
4526 if (DECIMAL_FLOAT_MODE_P (mode))
4527 REAL_VALUE_TO_TARGET_DECIMAL64 (rv, l);
4528 else
4529 REAL_VALUE_TO_TARGET_DOUBLE (rv, l);
4530 high = l[WORDS_BIG_ENDIAN == 0];
4531 low = l[WORDS_BIG_ENDIAN != 0];
4532 }
4533
4534 if (TARGET_32BIT)
4535 return (num_insns_constant_wide (low)
4536 + num_insns_constant_wide (high));
4537 else
4538 {
4539 if ((high == 0 && low >= 0)
4540 || (high == -1 && low < 0))
4541 return num_insns_constant_wide (low);
4542
4543 else if (mask64_operand (op, mode))
4544 return 2;
4545
4546 else if (low == 0)
4547 return num_insns_constant_wide (high) + 1;
4548
4549 else
4550 return (num_insns_constant_wide (high)
4551 + num_insns_constant_wide (low) + 1);
4552 }
4553
4554 default:
4555 gcc_unreachable ();
4556 }
4557 }
4558
4559 /* Interpret element ELT of the CONST_VECTOR OP as an integer value.
4560 If the mode of OP is MODE_VECTOR_INT, this simply returns the
4561 corresponding element of the vector, but for V4SFmode and V2SFmode,
4562 the corresponding "float" is interpreted as an SImode integer. */
4563
4564 HOST_WIDE_INT
4565 const_vector_elt_as_int (rtx op, unsigned int elt)
4566 {
4567 rtx tmp = CONST_VECTOR_ELT (op, elt);
4568 if (GET_MODE (op) == V4SFmode
4569 || GET_MODE (op) == V2SFmode)
4570 tmp = gen_lowpart (SImode, tmp);
4571 return INTVAL (tmp);
4572 }
4573
4574 /* Return true if OP can be synthesized with a particular vspltisb, vspltish
4575 or vspltisw instruction. OP is a CONST_VECTOR. Which instruction is used
4576 depends on STEP and COPIES, one of which will be 1. If COPIES > 1,
4577 all items are set to the same value and contain COPIES replicas of the
4578 vsplt's operand; if STEP > 1, one in STEP elements is set to the vsplt's
4579 operand and the others are set to the value of the operand's msb. */
4580
4581 static bool
4582 vspltis_constant (rtx op, unsigned step, unsigned copies)
4583 {
4584 enum machine_mode mode = GET_MODE (op);
4585 enum machine_mode inner = GET_MODE_INNER (mode);
4586
4587 unsigned i;
4588 unsigned nunits = GET_MODE_NUNITS (mode);
4589 unsigned bitsize = GET_MODE_BITSIZE (inner);
4590 unsigned mask = GET_MODE_MASK (inner);
4591
4592 HOST_WIDE_INT val = const_vector_elt_as_int (op, nunits - 1);
4593 HOST_WIDE_INT splat_val = val;
4594 HOST_WIDE_INT msb_val = val > 0 ? 0 : -1;
4595
4596 /* Construct the value to be splatted, if possible. If not, return 0. */
4597 for (i = 2; i <= copies; i *= 2)
4598 {
4599 HOST_WIDE_INT small_val;
4600 bitsize /= 2;
4601 small_val = splat_val >> bitsize;
4602 mask >>= bitsize;
4603 if (splat_val != ((small_val << bitsize) | (small_val & mask)))
4604 return false;
4605 splat_val = small_val;
4606 }
4607
4608 /* Check if SPLAT_VAL can really be the operand of a vspltis[bhw]. */
4609 if (EASY_VECTOR_15 (splat_val))
4610 ;
4611
4612 /* Also check if we can splat, and then add the result to itself. Do so if
4613 the value is positive, of if the splat instruction is using OP's mode;
4614 for splat_val < 0, the splat and the add should use the same mode. */
4615 else if (EASY_VECTOR_15_ADD_SELF (splat_val)
4616 && (splat_val >= 0 || (step == 1 && copies == 1)))
4617 ;
4618
4619 /* Also check if are loading up the most significant bit which can be done by
4620 loading up -1 and shifting the value left by -1. */
4621 else if (EASY_VECTOR_MSB (splat_val, inner))
4622 ;
4623
4624 else
4625 return false;
4626
4627 /* Check if VAL is present in every STEP-th element, and the
4628 other elements are filled with its most significant bit. */
4629 for (i = 0; i < nunits - 1; ++i)
4630 {
4631 HOST_WIDE_INT desired_val;
4632 if (((i + 1) & (step - 1)) == 0)
4633 desired_val = val;
4634 else
4635 desired_val = msb_val;
4636
4637 if (desired_val != const_vector_elt_as_int (op, i))
4638 return false;
4639 }
4640
4641 return true;
4642 }
4643
4644
4645 /* Return true if OP is of the given MODE and can be synthesized
4646 with a vspltisb, vspltish or vspltisw. */
4647
4648 bool
4649 easy_altivec_constant (rtx op, enum machine_mode mode)
4650 {
4651 unsigned step, copies;
4652
4653 if (mode == VOIDmode)
4654 mode = GET_MODE (op);
4655 else if (mode != GET_MODE (op))
4656 return false;
4657
4658 /* Start with a vspltisw. */
4659 step = GET_MODE_NUNITS (mode) / 4;
4660 copies = 1;
4661
4662 if (vspltis_constant (op, step, copies))
4663 return true;
4664
4665 /* Then try with a vspltish. */
4666 if (step == 1)
4667 copies <<= 1;
4668 else
4669 step >>= 1;
4670
4671 if (vspltis_constant (op, step, copies))
4672 return true;
4673
4674 /* And finally a vspltisb. */
4675 if (step == 1)
4676 copies <<= 1;
4677 else
4678 step >>= 1;
4679
4680 if (vspltis_constant (op, step, copies))
4681 return true;
4682
4683 return false;
4684 }
4685
4686 /* Generate a VEC_DUPLICATE representing a vspltis[bhw] instruction whose
4687 result is OP. Abort if it is not possible. */
4688
4689 rtx
4690 gen_easy_altivec_constant (rtx op)
4691 {
4692 enum machine_mode mode = GET_MODE (op);
4693 int nunits = GET_MODE_NUNITS (mode);
4694 rtx last = CONST_VECTOR_ELT (op, nunits - 1);
4695 unsigned step = nunits / 4;
4696 unsigned copies = 1;
4697
4698 /* Start with a vspltisw. */
4699 if (vspltis_constant (op, step, copies))
4700 return gen_rtx_VEC_DUPLICATE (V4SImode, gen_lowpart (SImode, last));
4701
4702 /* Then try with a vspltish. */
4703 if (step == 1)
4704 copies <<= 1;
4705 else
4706 step >>= 1;
4707
4708 if (vspltis_constant (op, step, copies))
4709 return gen_rtx_VEC_DUPLICATE (V8HImode, gen_lowpart (HImode, last));
4710
4711 /* And finally a vspltisb. */
4712 if (step == 1)
4713 copies <<= 1;
4714 else
4715 step >>= 1;
4716
4717 if (vspltis_constant (op, step, copies))
4718 return gen_rtx_VEC_DUPLICATE (V16QImode, gen_lowpart (QImode, last));
4719
4720 gcc_unreachable ();
4721 }
4722
4723 const char *
4724 output_vec_const_move (rtx *operands)
4725 {
4726 int cst, cst2;
4727 enum machine_mode mode;
4728 rtx dest, vec;
4729
4730 dest = operands[0];
4731 vec = operands[1];
4732 mode = GET_MODE (dest);
4733
4734 if (TARGET_VSX && zero_constant (vec, mode))
4735 return "xxlxor %x0,%x0,%x0";
4736
4737 if (TARGET_ALTIVEC)
4738 {
4739 rtx splat_vec;
4740 if (zero_constant (vec, mode))
4741 return "vxor %0,%0,%0";
4742
4743 splat_vec = gen_easy_altivec_constant (vec);
4744 gcc_assert (GET_CODE (splat_vec) == VEC_DUPLICATE);
4745 operands[1] = XEXP (splat_vec, 0);
4746 if (!EASY_VECTOR_15 (INTVAL (operands[1])))
4747 return "#";
4748
4749 switch (GET_MODE (splat_vec))
4750 {
4751 case V4SImode:
4752 return "vspltisw %0,%1";
4753
4754 case V8HImode:
4755 return "vspltish %0,%1";
4756
4757 case V16QImode:
4758 return "vspltisb %0,%1";
4759
4760 default:
4761 gcc_unreachable ();
4762 }
4763 }
4764
4765 gcc_assert (TARGET_SPE);
4766
4767 /* Vector constant 0 is handled as a splitter of V2SI, and in the
4768 pattern of V1DI, V4HI, and V2SF.
4769
4770 FIXME: We should probably return # and add post reload
4771 splitters for these, but this way is so easy ;-). */
4772 cst = INTVAL (CONST_VECTOR_ELT (vec, 0));
4773 cst2 = INTVAL (CONST_VECTOR_ELT (vec, 1));
4774 operands[1] = CONST_VECTOR_ELT (vec, 0);
4775 operands[2] = CONST_VECTOR_ELT (vec, 1);
4776 if (cst == cst2)
4777 return "li %0,%1\n\tevmergelo %0,%0,%0";
4778 else
4779 return "li %0,%1\n\tevmergelo %0,%0,%0\n\tli %0,%2";
4780 }
4781
4782 /* Initialize TARGET of vector PAIRED to VALS. */
4783
4784 void
4785 paired_expand_vector_init (rtx target, rtx vals)
4786 {
4787 enum machine_mode mode = GET_MODE (target);
4788 int n_elts = GET_MODE_NUNITS (mode);
4789 int n_var = 0;
4790 rtx x, new_rtx, tmp, constant_op, op1, op2;
4791 int i;
4792
4793 for (i = 0; i < n_elts; ++i)
4794 {
4795 x = XVECEXP (vals, 0, i);
4796 if (!CONSTANT_P (x))
4797 ++n_var;
4798 }
4799 if (n_var == 0)
4800 {
4801 /* Load from constant pool. */
4802 emit_move_insn (target, gen_rtx_CONST_VECTOR (mode, XVEC (vals, 0)));
4803 return;
4804 }
4805
4806 if (n_var == 2)
4807 {
4808 /* The vector is initialized only with non-constants. */
4809 new_rtx = gen_rtx_VEC_CONCAT (V2SFmode, XVECEXP (vals, 0, 0),
4810 XVECEXP (vals, 0, 1));
4811
4812 emit_move_insn (target, new_rtx);
4813 return;
4814 }
4815
4816 /* One field is non-constant and the other one is a constant. Load the
4817 constant from the constant pool and use ps_merge instruction to
4818 construct the whole vector. */
4819 op1 = XVECEXP (vals, 0, 0);
4820 op2 = XVECEXP (vals, 0, 1);
4821
4822 constant_op = (CONSTANT_P (op1)) ? op1 : op2;
4823
4824 tmp = gen_reg_rtx (GET_MODE (constant_op));
4825 emit_move_insn (tmp, constant_op);
4826
4827 if (CONSTANT_P (op1))
4828 new_rtx = gen_rtx_VEC_CONCAT (V2SFmode, tmp, op2);
4829 else
4830 new_rtx = gen_rtx_VEC_CONCAT (V2SFmode, op1, tmp);
4831
4832 emit_move_insn (target, new_rtx);
4833 }
4834
4835 void
4836 paired_expand_vector_move (rtx operands[])
4837 {
4838 rtx op0 = operands[0], op1 = operands[1];
4839
4840 emit_move_insn (op0, op1);
4841 }
4842
4843 /* Emit vector compare for code RCODE. DEST is destination, OP1 and
4844 OP2 are two VEC_COND_EXPR operands, CC_OP0 and CC_OP1 are the two
4845 operands for the relation operation COND. This is a recursive
4846 function. */
4847
4848 static void
4849 paired_emit_vector_compare (enum rtx_code rcode,
4850 rtx dest, rtx op0, rtx op1,
4851 rtx cc_op0, rtx cc_op1)
4852 {
4853 rtx tmp = gen_reg_rtx (V2SFmode);
4854 rtx tmp1, max, min;
4855
4856 gcc_assert (TARGET_PAIRED_FLOAT);
4857 gcc_assert (GET_MODE (op0) == GET_MODE (op1));
4858
4859 switch (rcode)
4860 {
4861 case LT:
4862 case LTU:
4863 paired_emit_vector_compare (GE, dest, op1, op0, cc_op0, cc_op1);
4864 return;
4865 case GE:
4866 case GEU:
4867 emit_insn (gen_subv2sf3 (tmp, cc_op0, cc_op1));
4868 emit_insn (gen_selv2sf4 (dest, tmp, op0, op1, CONST0_RTX (SFmode)));
4869 return;
4870 case LE:
4871 case LEU:
4872 paired_emit_vector_compare (GE, dest, op0, op1, cc_op1, cc_op0);
4873 return;
4874 case GT:
4875 paired_emit_vector_compare (LE, dest, op1, op0, cc_op0, cc_op1);
4876 return;
4877 case EQ:
4878 tmp1 = gen_reg_rtx (V2SFmode);
4879 max = gen_reg_rtx (V2SFmode);
4880 min = gen_reg_rtx (V2SFmode);
4881 gen_reg_rtx (V2SFmode);
4882
4883 emit_insn (gen_subv2sf3 (tmp, cc_op0, cc_op1));
4884 emit_insn (gen_selv2sf4
4885 (max, tmp, cc_op0, cc_op1, CONST0_RTX (SFmode)));
4886 emit_insn (gen_subv2sf3 (tmp, cc_op1, cc_op0));
4887 emit_insn (gen_selv2sf4
4888 (min, tmp, cc_op0, cc_op1, CONST0_RTX (SFmode)));
4889 emit_insn (gen_subv2sf3 (tmp1, min, max));
4890 emit_insn (gen_selv2sf4 (dest, tmp1, op0, op1, CONST0_RTX (SFmode)));
4891 return;
4892 case NE:
4893 paired_emit_vector_compare (EQ, dest, op1, op0, cc_op0, cc_op1);
4894 return;
4895 case UNLE:
4896 paired_emit_vector_compare (LE, dest, op1, op0, cc_op0, cc_op1);
4897 return;
4898 case UNLT:
4899 paired_emit_vector_compare (LT, dest, op1, op0, cc_op0, cc_op1);
4900 return;
4901 case UNGE:
4902 paired_emit_vector_compare (GE, dest, op1, op0, cc_op0, cc_op1);
4903 return;
4904 case UNGT:
4905 paired_emit_vector_compare (GT, dest, op1, op0, cc_op0, cc_op1);
4906 return;
4907 default:
4908 gcc_unreachable ();
4909 }
4910
4911 return;
4912 }
4913
4914 /* Emit vector conditional expression.
4915 DEST is destination. OP1 and OP2 are two VEC_COND_EXPR operands.
4916 CC_OP0 and CC_OP1 are the two operands for the relation operation COND. */
4917
4918 int
4919 paired_emit_vector_cond_expr (rtx dest, rtx op1, rtx op2,
4920 rtx cond, rtx cc_op0, rtx cc_op1)
4921 {
4922 enum rtx_code rcode = GET_CODE (cond);
4923
4924 if (!TARGET_PAIRED_FLOAT)
4925 return 0;
4926
4927 paired_emit_vector_compare (rcode, dest, op1, op2, cc_op0, cc_op1);
4928
4929 return 1;
4930 }
4931
4932 /* Initialize vector TARGET to VALS. */
4933
4934 void
4935 rs6000_expand_vector_init (rtx target, rtx vals)
4936 {
4937 enum machine_mode mode = GET_MODE (target);
4938 enum machine_mode inner_mode = GET_MODE_INNER (mode);
4939 int n_elts = GET_MODE_NUNITS (mode);
4940 int n_var = 0, one_var = -1;
4941 bool all_same = true, all_const_zero = true;
4942 rtx x, mem;
4943 int i;
4944
4945 for (i = 0; i < n_elts; ++i)
4946 {
4947 x = XVECEXP (vals, 0, i);
4948 if (!CONSTANT_P (x))
4949 ++n_var, one_var = i;
4950 else if (x != CONST0_RTX (inner_mode))
4951 all_const_zero = false;
4952
4953 if (i > 0 && !rtx_equal_p (x, XVECEXP (vals, 0, 0)))
4954 all_same = false;
4955 }
4956
4957 if (n_var == 0)
4958 {
4959 rtx const_vec = gen_rtx_CONST_VECTOR (mode, XVEC (vals, 0));
4960 bool int_vector_p = (GET_MODE_CLASS (mode) == MODE_VECTOR_INT);
4961 if ((int_vector_p || TARGET_VSX) && all_const_zero)
4962 {
4963 /* Zero register. */
4964 emit_insn (gen_rtx_SET (VOIDmode, target,
4965 gen_rtx_XOR (mode, target, target)));
4966 return;
4967 }
4968 else if (int_vector_p && easy_vector_constant (const_vec, mode))
4969 {
4970 /* Splat immediate. */
4971 emit_insn (gen_rtx_SET (VOIDmode, target, const_vec));
4972 return;
4973 }
4974 else
4975 {
4976 /* Load from constant pool. */
4977 emit_move_insn (target, const_vec);
4978 return;
4979 }
4980 }
4981
4982 /* Double word values on VSX can use xxpermdi or lxvdsx. */
4983 if (VECTOR_MEM_VSX_P (mode) && (mode == V2DFmode || mode == V2DImode))
4984 {
4985 if (all_same)
4986 {
4987 rtx element = XVECEXP (vals, 0, 0);
4988 if (mode == V2DFmode)
4989 emit_insn (gen_vsx_splat_v2df (target, element));
4990 else
4991 emit_insn (gen_vsx_splat_v2di (target, element));
4992 }
4993 else
4994 {
4995 rtx op0 = copy_to_reg (XVECEXP (vals, 0, 0));
4996 rtx op1 = copy_to_reg (XVECEXP (vals, 0, 1));
4997 if (mode == V2DFmode)
4998 emit_insn (gen_vsx_concat_v2df (target, op0, op1));
4999 else
5000 emit_insn (gen_vsx_concat_v2di (target, op0, op1));
5001 }
5002 return;
5003 }
5004
5005 /* With single precision floating point on VSX, know that internally single
5006 precision is actually represented as a double, and either make 2 V2DF
5007 vectors, and convert these vectors to single precision, or do one
5008 conversion, and splat the result to the other elements. */
5009 if (mode == V4SFmode && VECTOR_MEM_VSX_P (mode))
5010 {
5011 if (all_same)
5012 {
5013 rtx freg = gen_reg_rtx (V4SFmode);
5014 rtx sreg = copy_to_reg (XVECEXP (vals, 0, 0));
5015
5016 emit_insn (gen_vsx_xscvdpsp_scalar (freg, sreg));
5017 emit_insn (gen_vsx_xxspltw_v4sf (target, freg, const0_rtx));
5018 }
5019 else
5020 {
5021 rtx dbl_even = gen_reg_rtx (V2DFmode);
5022 rtx dbl_odd = gen_reg_rtx (V2DFmode);
5023 rtx flt_even = gen_reg_rtx (V4SFmode);
5024 rtx flt_odd = gen_reg_rtx (V4SFmode);
5025
5026 emit_insn (gen_vsx_concat_v2sf (dbl_even,
5027 copy_to_reg (XVECEXP (vals, 0, 0)),
5028 copy_to_reg (XVECEXP (vals, 0, 1))));
5029 emit_insn (gen_vsx_concat_v2sf (dbl_odd,
5030 copy_to_reg (XVECEXP (vals, 0, 2)),
5031 copy_to_reg (XVECEXP (vals, 0, 3))));
5032 emit_insn (gen_vsx_xvcvdpsp (flt_even, dbl_even));
5033 emit_insn (gen_vsx_xvcvdpsp (flt_odd, dbl_odd));
5034 emit_insn (gen_vec_extract_evenv4sf (target, flt_even, flt_odd));
5035 }
5036 return;
5037 }
5038
5039 /* Store value to stack temp. Load vector element. Splat. However, splat
5040 of 64-bit items is not supported on Altivec. */
5041 if (all_same && GET_MODE_SIZE (mode) <= 4)
5042 {
5043 mem = assign_stack_temp (mode, GET_MODE_SIZE (inner_mode), 0);
5044 emit_move_insn (adjust_address_nv (mem, inner_mode, 0),
5045 XVECEXP (vals, 0, 0));
5046 x = gen_rtx_UNSPEC (VOIDmode,
5047 gen_rtvec (1, const0_rtx), UNSPEC_LVE);
5048 emit_insn (gen_rtx_PARALLEL (VOIDmode,
5049 gen_rtvec (2,
5050 gen_rtx_SET (VOIDmode,
5051 target, mem),
5052 x)));
5053 x = gen_rtx_VEC_SELECT (inner_mode, target,
5054 gen_rtx_PARALLEL (VOIDmode,
5055 gen_rtvec (1, const0_rtx)));
5056 emit_insn (gen_rtx_SET (VOIDmode, target,
5057 gen_rtx_VEC_DUPLICATE (mode, x)));
5058 return;
5059 }
5060
5061 /* One field is non-constant. Load constant then overwrite
5062 varying field. */
5063 if (n_var == 1)
5064 {
5065 rtx copy = copy_rtx (vals);
5066
5067 /* Load constant part of vector, substitute neighboring value for
5068 varying element. */
5069 XVECEXP (copy, 0, one_var) = XVECEXP (vals, 0, (one_var + 1) % n_elts);
5070 rs6000_expand_vector_init (target, copy);
5071
5072 /* Insert variable. */
5073 rs6000_expand_vector_set (target, XVECEXP (vals, 0, one_var), one_var);
5074 return;
5075 }
5076
5077 /* Construct the vector in memory one field at a time
5078 and load the whole vector. */
5079 mem = assign_stack_temp (mode, GET_MODE_SIZE (mode), 0);
5080 for (i = 0; i < n_elts; i++)
5081 emit_move_insn (adjust_address_nv (mem, inner_mode,
5082 i * GET_MODE_SIZE (inner_mode)),
5083 XVECEXP (vals, 0, i));
5084 emit_move_insn (target, mem);
5085 }
5086
5087 /* Set field ELT of TARGET to VAL. */
5088
5089 void
5090 rs6000_expand_vector_set (rtx target, rtx val, int elt)
5091 {
5092 enum machine_mode mode = GET_MODE (target);
5093 enum machine_mode inner_mode = GET_MODE_INNER (mode);
5094 rtx reg = gen_reg_rtx (mode);
5095 rtx mask, mem, x;
5096 int width = GET_MODE_SIZE (inner_mode);
5097 int i;
5098
5099 if (VECTOR_MEM_VSX_P (mode) && (mode == V2DFmode || mode == V2DImode))
5100 {
5101 rtx (*set_func) (rtx, rtx, rtx, rtx)
5102 = ((mode == V2DFmode) ? gen_vsx_set_v2df : gen_vsx_set_v2di);
5103 emit_insn (set_func (target, target, val, GEN_INT (elt)));
5104 return;
5105 }
5106
5107 /* Load single variable value. */
5108 mem = assign_stack_temp (mode, GET_MODE_SIZE (inner_mode), 0);
5109 emit_move_insn (adjust_address_nv (mem, inner_mode, 0), val);
5110 x = gen_rtx_UNSPEC (VOIDmode,
5111 gen_rtvec (1, const0_rtx), UNSPEC_LVE);
5112 emit_insn (gen_rtx_PARALLEL (VOIDmode,
5113 gen_rtvec (2,
5114 gen_rtx_SET (VOIDmode,
5115 reg, mem),
5116 x)));
5117
5118 /* Linear sequence. */
5119 mask = gen_rtx_PARALLEL (V16QImode, rtvec_alloc (16));
5120 for (i = 0; i < 16; ++i)
5121 XVECEXP (mask, 0, i) = GEN_INT (i);
5122
5123 /* Set permute mask to insert element into target. */
5124 for (i = 0; i < width; ++i)
5125 XVECEXP (mask, 0, elt*width + i)
5126 = GEN_INT (i + 0x10);
5127 x = gen_rtx_CONST_VECTOR (V16QImode, XVEC (mask, 0));
5128 x = gen_rtx_UNSPEC (mode,
5129 gen_rtvec (3, target, reg,
5130 force_reg (V16QImode, x)),
5131 UNSPEC_VPERM);
5132 emit_insn (gen_rtx_SET (VOIDmode, target, x));
5133 }
5134
5135 /* Extract field ELT from VEC into TARGET. */
5136
5137 void
5138 rs6000_expand_vector_extract (rtx target, rtx vec, int elt)
5139 {
5140 enum machine_mode mode = GET_MODE (vec);
5141 enum machine_mode inner_mode = GET_MODE_INNER (mode);
5142 rtx mem, x;
5143
5144 if (VECTOR_MEM_VSX_P (mode) && (mode == V2DFmode || mode == V2DImode))
5145 {
5146 rtx (*extract_func) (rtx, rtx, rtx)
5147 = ((mode == V2DFmode) ? gen_vsx_extract_v2df : gen_vsx_extract_v2di);
5148 emit_insn (extract_func (target, vec, GEN_INT (elt)));
5149 return;
5150 }
5151
5152 /* Allocate mode-sized buffer. */
5153 mem = assign_stack_temp (mode, GET_MODE_SIZE (mode), 0);
5154
5155 /* Add offset to field within buffer matching vector element. */
5156 mem = adjust_address_nv (mem, mode, elt * GET_MODE_SIZE (inner_mode));
5157
5158 /* Store single field into mode-sized buffer. */
5159 x = gen_rtx_UNSPEC (VOIDmode,
5160 gen_rtvec (1, const0_rtx), UNSPEC_STVE);
5161 emit_insn (gen_rtx_PARALLEL (VOIDmode,
5162 gen_rtvec (2,
5163 gen_rtx_SET (VOIDmode,
5164 mem, vec),
5165 x)));
5166 emit_move_insn (target, adjust_address_nv (mem, inner_mode, 0));
5167 }
5168
5169 /* Generates shifts and masks for a pair of rldicl or rldicr insns to
5170 implement ANDing by the mask IN. */
5171 void
5172 build_mask64_2_operands (rtx in, rtx *out)
5173 {
5174 #if HOST_BITS_PER_WIDE_INT >= 64
5175 unsigned HOST_WIDE_INT c, lsb, m1, m2;
5176 int shift;
5177
5178 gcc_assert (GET_CODE (in) == CONST_INT);
5179
5180 c = INTVAL (in);
5181 if (c & 1)
5182 {
5183 /* Assume c initially something like 0x00fff000000fffff. The idea
5184 is to rotate the word so that the middle ^^^^^^ group of zeros
5185 is at the MS end and can be cleared with an rldicl mask. We then
5186 rotate back and clear off the MS ^^ group of zeros with a
5187 second rldicl. */
5188 c = ~c; /* c == 0xff000ffffff00000 */
5189 lsb = c & -c; /* lsb == 0x0000000000100000 */
5190 m1 = -lsb; /* m1 == 0xfffffffffff00000 */
5191 c = ~c; /* c == 0x00fff000000fffff */
5192 c &= -lsb; /* c == 0x00fff00000000000 */
5193 lsb = c & -c; /* lsb == 0x0000100000000000 */
5194 c = ~c; /* c == 0xff000fffffffffff */
5195 c &= -lsb; /* c == 0xff00000000000000 */
5196 shift = 0;
5197 while ((lsb >>= 1) != 0)
5198 shift++; /* shift == 44 on exit from loop */
5199 m1 <<= 64 - shift; /* m1 == 0xffffff0000000000 */
5200 m1 = ~m1; /* m1 == 0x000000ffffffffff */
5201 m2 = ~c; /* m2 == 0x00ffffffffffffff */
5202 }
5203 else
5204 {
5205 /* Assume c initially something like 0xff000f0000000000. The idea
5206 is to rotate the word so that the ^^^ middle group of zeros
5207 is at the LS end and can be cleared with an rldicr mask. We then
5208 rotate back and clear off the LS group of ^^^^^^^^^^ zeros with
5209 a second rldicr. */
5210 lsb = c & -c; /* lsb == 0x0000010000000000 */
5211 m2 = -lsb; /* m2 == 0xffffff0000000000 */
5212 c = ~c; /* c == 0x00fff0ffffffffff */
5213 c &= -lsb; /* c == 0x00fff00000000000 */
5214 lsb = c & -c; /* lsb == 0x0000100000000000 */
5215 c = ~c; /* c == 0xff000fffffffffff */
5216 c &= -lsb; /* c == 0xff00000000000000 */
5217 shift = 0;
5218 while ((lsb >>= 1) != 0)
5219 shift++; /* shift == 44 on exit from loop */
5220 m1 = ~c; /* m1 == 0x00ffffffffffffff */
5221 m1 >>= shift; /* m1 == 0x0000000000000fff */
5222 m1 = ~m1; /* m1 == 0xfffffffffffff000 */
5223 }
5224
5225 /* Note that when we only have two 0->1 and 1->0 transitions, one of the
5226 masks will be all 1's. We are guaranteed more than one transition. */
5227 out[0] = GEN_INT (64 - shift);
5228 out[1] = GEN_INT (m1);
5229 out[2] = GEN_INT (shift);
5230 out[3] = GEN_INT (m2);
5231 #else
5232 (void)in;
5233 (void)out;
5234 gcc_unreachable ();
5235 #endif
5236 }
5237
5238 /* Return TRUE if OP is an invalid SUBREG operation on the e500. */
5239
5240 bool
5241 invalid_e500_subreg (rtx op, enum machine_mode mode)
5242 {
5243 if (TARGET_E500_DOUBLE)
5244 {
5245 /* Reject (subreg:SI (reg:DF)); likewise with subreg:DI or
5246 subreg:TI and reg:TF. Decimal float modes are like integer
5247 modes (only low part of each register used) for this
5248 purpose. */
5249 if (GET_CODE (op) == SUBREG
5250 && (mode == SImode || mode == DImode || mode == TImode
5251 || mode == DDmode || mode == TDmode)
5252 && REG_P (SUBREG_REG (op))
5253 && (GET_MODE (SUBREG_REG (op)) == DFmode
5254 || GET_MODE (SUBREG_REG (op)) == TFmode))
5255 return true;
5256
5257 /* Reject (subreg:DF (reg:DI)); likewise with subreg:TF and
5258 reg:TI. */
5259 if (GET_CODE (op) == SUBREG
5260 && (mode == DFmode || mode == TFmode)
5261 && REG_P (SUBREG_REG (op))
5262 && (GET_MODE (SUBREG_REG (op)) == DImode
5263 || GET_MODE (SUBREG_REG (op)) == TImode
5264 || GET_MODE (SUBREG_REG (op)) == DDmode
5265 || GET_MODE (SUBREG_REG (op)) == TDmode))
5266 return true;
5267 }
5268
5269 if (TARGET_SPE
5270 && GET_CODE (op) == SUBREG
5271 && mode == SImode
5272 && REG_P (SUBREG_REG (op))
5273 && SPE_VECTOR_MODE (GET_MODE (SUBREG_REG (op))))
5274 return true;
5275
5276 return false;
5277 }
5278
5279 /* AIX increases natural record alignment to doubleword if the first
5280 field is an FP double while the FP fields remain word aligned. */
5281
5282 unsigned int
5283 rs6000_special_round_type_align (tree type, unsigned int computed,
5284 unsigned int specified)
5285 {
5286 unsigned int align = MAX (computed, specified);
5287 tree field = TYPE_FIELDS (type);
5288
5289 /* Skip all non field decls */
5290 while (field != NULL && TREE_CODE (field) != FIELD_DECL)
5291 field = DECL_CHAIN (field);
5292
5293 if (field != NULL && field != type)
5294 {
5295 type = TREE_TYPE (field);
5296 while (TREE_CODE (type) == ARRAY_TYPE)
5297 type = TREE_TYPE (type);
5298
5299 if (type != error_mark_node && TYPE_MODE (type) == DFmode)
5300 align = MAX (align, 64);
5301 }
5302
5303 return align;
5304 }
5305
5306 /* Darwin increases record alignment to the natural alignment of
5307 the first field. */
5308
5309 unsigned int
5310 darwin_rs6000_special_round_type_align (tree type, unsigned int computed,
5311 unsigned int specified)
5312 {
5313 unsigned int align = MAX (computed, specified);
5314
5315 if (TYPE_PACKED (type))
5316 return align;
5317
5318 /* Find the first field, looking down into aggregates. */
5319 do {
5320 tree field = TYPE_FIELDS (type);
5321 /* Skip all non field decls */
5322 while (field != NULL && TREE_CODE (field) != FIELD_DECL)
5323 field = DECL_CHAIN (field);
5324 if (! field)
5325 break;
5326 /* A packed field does not contribute any extra alignment. */
5327 if (DECL_PACKED (field))
5328 return align;
5329 type = TREE_TYPE (field);
5330 while (TREE_CODE (type) == ARRAY_TYPE)
5331 type = TREE_TYPE (type);
5332 } while (AGGREGATE_TYPE_P (type));
5333
5334 if (! AGGREGATE_TYPE_P (type) && type != error_mark_node)
5335 align = MAX (align, TYPE_ALIGN (type));
5336
5337 return align;
5338 }
5339
5340 /* Return 1 for an operand in small memory on V.4/eabi. */
5341
5342 int
5343 small_data_operand (rtx op ATTRIBUTE_UNUSED,
5344 enum machine_mode mode ATTRIBUTE_UNUSED)
5345 {
5346 #if TARGET_ELF
5347 rtx sym_ref;
5348
5349 if (rs6000_sdata == SDATA_NONE || rs6000_sdata == SDATA_DATA)
5350 return 0;
5351
5352 if (DEFAULT_ABI != ABI_V4)
5353 return 0;
5354
5355 /* Vector and float memory instructions have a limited offset on the
5356 SPE, so using a vector or float variable directly as an operand is
5357 not useful. */
5358 if (TARGET_SPE
5359 && (SPE_VECTOR_MODE (mode) || FLOAT_MODE_P (mode)))
5360 return 0;
5361
5362 if (GET_CODE (op) == SYMBOL_REF)
5363 sym_ref = op;
5364
5365 else if (GET_CODE (op) != CONST
5366 || GET_CODE (XEXP (op, 0)) != PLUS
5367 || GET_CODE (XEXP (XEXP (op, 0), 0)) != SYMBOL_REF
5368 || GET_CODE (XEXP (XEXP (op, 0), 1)) != CONST_INT)
5369 return 0;
5370
5371 else
5372 {
5373 rtx sum = XEXP (op, 0);
5374 HOST_WIDE_INT summand;
5375
5376 /* We have to be careful here, because it is the referenced address
5377 that must be 32k from _SDA_BASE_, not just the symbol. */
5378 summand = INTVAL (XEXP (sum, 1));
5379 if (summand < 0 || (unsigned HOST_WIDE_INT) summand > g_switch_value)
5380 return 0;
5381
5382 sym_ref = XEXP (sum, 0);
5383 }
5384
5385 return SYMBOL_REF_SMALL_P (sym_ref);
5386 #else
5387 return 0;
5388 #endif
5389 }
5390
5391 /* Return true if either operand is a general purpose register. */
5392
5393 bool
5394 gpr_or_gpr_p (rtx op0, rtx op1)
5395 {
5396 return ((REG_P (op0) && INT_REGNO_P (REGNO (op0)))
5397 || (REG_P (op1) && INT_REGNO_P (REGNO (op1))));
5398 }
5399
5400 \f
5401 /* Subroutines of rs6000_legitimize_address and rs6000_legitimate_address_p. */
5402
5403 static bool
5404 reg_offset_addressing_ok_p (enum machine_mode mode)
5405 {
5406 switch (mode)
5407 {
5408 case V16QImode:
5409 case V8HImode:
5410 case V4SFmode:
5411 case V4SImode:
5412 case V2DFmode:
5413 case V2DImode:
5414 /* AltiVec/VSX vector modes. Only reg+reg addressing is valid. */
5415 if (VECTOR_MEM_ALTIVEC_OR_VSX_P (mode))
5416 return false;
5417 break;
5418
5419 case V4HImode:
5420 case V2SImode:
5421 case V1DImode:
5422 case V2SFmode:
5423 /* Paired vector modes. Only reg+reg addressing is valid. */
5424 if (TARGET_PAIRED_FLOAT)
5425 return false;
5426 break;
5427
5428 default:
5429 break;
5430 }
5431
5432 return true;
5433 }
5434
5435 static bool
5436 virtual_stack_registers_memory_p (rtx op)
5437 {
5438 int regnum;
5439
5440 if (GET_CODE (op) == REG)
5441 regnum = REGNO (op);
5442
5443 else if (GET_CODE (op) == PLUS
5444 && GET_CODE (XEXP (op, 0)) == REG
5445 && GET_CODE (XEXP (op, 1)) == CONST_INT)
5446 regnum = REGNO (XEXP (op, 0));
5447
5448 else
5449 return false;
5450
5451 return (regnum >= FIRST_VIRTUAL_REGISTER
5452 && regnum <= LAST_VIRTUAL_REGISTER);
5453 }
5454
5455 static bool
5456 constant_pool_expr_p (rtx op)
5457 {
5458 rtx base, offset;
5459
5460 split_const (op, &base, &offset);
5461 return (GET_CODE (base) == SYMBOL_REF
5462 && CONSTANT_POOL_ADDRESS_P (base)
5463 && ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (get_pool_constant (base), Pmode));
5464 }
5465
5466 static rtx tocrel_base, tocrel_offset;
5467
5468 bool
5469 toc_relative_expr_p (rtx op)
5470 {
5471 if (GET_CODE (op) != CONST)
5472 return false;
5473
5474 split_const (op, &tocrel_base, &tocrel_offset);
5475 return (GET_CODE (tocrel_base) == UNSPEC
5476 && XINT (tocrel_base, 1) == UNSPEC_TOCREL);
5477 }
5478
5479 bool
5480 legitimate_constant_pool_address_p (const_rtx x, bool strict)
5481 {
5482 return (TARGET_TOC
5483 && (GET_CODE (x) == PLUS || GET_CODE (x) == LO_SUM)
5484 && GET_CODE (XEXP (x, 0)) == REG
5485 && (REGNO (XEXP (x, 0)) == TOC_REGISTER
5486 || ((TARGET_MINIMAL_TOC
5487 || TARGET_CMODEL != CMODEL_SMALL)
5488 && INT_REG_OK_FOR_BASE_P (XEXP (x, 0), strict)))
5489 && toc_relative_expr_p (XEXP (x, 1)));
5490 }
5491
5492 static bool
5493 legitimate_small_data_p (enum machine_mode mode, rtx x)
5494 {
5495 return (DEFAULT_ABI == ABI_V4
5496 && !flag_pic && !TARGET_TOC
5497 && (GET_CODE (x) == SYMBOL_REF || GET_CODE (x) == CONST)
5498 && small_data_operand (x, mode));
5499 }
5500
5501 /* SPE offset addressing is limited to 5-bits worth of double words. */
5502 #define SPE_CONST_OFFSET_OK(x) (((x) & ~0xf8) == 0)
5503
5504 bool
5505 rs6000_legitimate_offset_address_p (enum machine_mode mode, rtx x, int strict)
5506 {
5507 unsigned HOST_WIDE_INT offset, extra;
5508
5509 if (GET_CODE (x) != PLUS)
5510 return false;
5511 if (GET_CODE (XEXP (x, 0)) != REG)
5512 return false;
5513 if (!INT_REG_OK_FOR_BASE_P (XEXP (x, 0), strict))
5514 return false;
5515 if (!reg_offset_addressing_ok_p (mode))
5516 return virtual_stack_registers_memory_p (x);
5517 if (legitimate_constant_pool_address_p (x, strict))
5518 return true;
5519 if (GET_CODE (XEXP (x, 1)) != CONST_INT)
5520 return false;
5521
5522 offset = INTVAL (XEXP (x, 1));
5523 extra = 0;
5524 switch (mode)
5525 {
5526 case V4HImode:
5527 case V2SImode:
5528 case V1DImode:
5529 case V2SFmode:
5530 /* SPE vector modes. */
5531 return SPE_CONST_OFFSET_OK (offset);
5532
5533 case DFmode:
5534 if (TARGET_E500_DOUBLE)
5535 return SPE_CONST_OFFSET_OK (offset);
5536
5537 /* If we are using VSX scalar loads, restrict ourselves to reg+reg
5538 addressing. */
5539 if (VECTOR_MEM_VSX_P (DFmode))
5540 return false;
5541
5542 case DDmode:
5543 case DImode:
5544 /* On e500v2, we may have:
5545
5546 (subreg:DF (mem:DI (plus (reg) (const_int))) 0).
5547
5548 Which gets addressed with evldd instructions. */
5549 if (TARGET_E500_DOUBLE)
5550 return SPE_CONST_OFFSET_OK (offset);
5551
5552 if (mode == DFmode || mode == DDmode || !TARGET_POWERPC64)
5553 extra = 4;
5554 else if (offset & 3)
5555 return false;
5556 break;
5557
5558 case TFmode:
5559 if (TARGET_E500_DOUBLE)
5560 return (SPE_CONST_OFFSET_OK (offset)
5561 && SPE_CONST_OFFSET_OK (offset + 8));
5562
5563 case TDmode:
5564 case TImode:
5565 if (mode == TFmode || mode == TDmode || !TARGET_POWERPC64)
5566 extra = 12;
5567 else if (offset & 3)
5568 return false;
5569 else
5570 extra = 8;
5571 break;
5572
5573 default:
5574 break;
5575 }
5576
5577 offset += 0x8000;
5578 return (offset < 0x10000) && (offset + extra < 0x10000);
5579 }
5580
5581 bool
5582 legitimate_indexed_address_p (rtx x, int strict)
5583 {
5584 rtx op0, op1;
5585
5586 if (GET_CODE (x) != PLUS)
5587 return false;
5588
5589 op0 = XEXP (x, 0);
5590 op1 = XEXP (x, 1);
5591
5592 /* Recognize the rtl generated by reload which we know will later be
5593 replaced with proper base and index regs. */
5594 if (!strict
5595 && reload_in_progress
5596 && (REG_P (op0) || GET_CODE (op0) == PLUS)
5597 && REG_P (op1))
5598 return true;
5599
5600 return (REG_P (op0) && REG_P (op1)
5601 && ((INT_REG_OK_FOR_BASE_P (op0, strict)
5602 && INT_REG_OK_FOR_INDEX_P (op1, strict))
5603 || (INT_REG_OK_FOR_BASE_P (op1, strict)
5604 && INT_REG_OK_FOR_INDEX_P (op0, strict))));
5605 }
5606
5607 bool
5608 avoiding_indexed_address_p (enum machine_mode mode)
5609 {
5610 /* Avoid indexed addressing for modes that have non-indexed
5611 load/store instruction forms. */
5612 return (TARGET_AVOID_XFORM && VECTOR_MEM_NONE_P (mode));
5613 }
5614
5615 inline bool
5616 legitimate_indirect_address_p (rtx x, int strict)
5617 {
5618 return GET_CODE (x) == REG && INT_REG_OK_FOR_BASE_P (x, strict);
5619 }
5620
5621 bool
5622 macho_lo_sum_memory_operand (rtx x, enum machine_mode mode)
5623 {
5624 if (!TARGET_MACHO || !flag_pic
5625 || mode != SImode || GET_CODE (x) != MEM)
5626 return false;
5627 x = XEXP (x, 0);
5628
5629 if (GET_CODE (x) != LO_SUM)
5630 return false;
5631 if (GET_CODE (XEXP (x, 0)) != REG)
5632 return false;
5633 if (!INT_REG_OK_FOR_BASE_P (XEXP (x, 0), 0))
5634 return false;
5635 x = XEXP (x, 1);
5636
5637 return CONSTANT_P (x);
5638 }
5639
5640 static bool
5641 legitimate_lo_sum_address_p (enum machine_mode mode, rtx x, int strict)
5642 {
5643 if (GET_CODE (x) != LO_SUM)
5644 return false;
5645 if (GET_CODE (XEXP (x, 0)) != REG)
5646 return false;
5647 if (!INT_REG_OK_FOR_BASE_P (XEXP (x, 0), strict))
5648 return false;
5649 /* Restrict addressing for DI because of our SUBREG hackery. */
5650 if (TARGET_E500_DOUBLE && (mode == DFmode || mode == TFmode
5651 || mode == DDmode || mode == TDmode
5652 || mode == DImode))
5653 return false;
5654 x = XEXP (x, 1);
5655
5656 if (TARGET_ELF || TARGET_MACHO)
5657 {
5658 if (DEFAULT_ABI != ABI_AIX && DEFAULT_ABI != ABI_DARWIN && flag_pic)
5659 return false;
5660 if (TARGET_TOC)
5661 return false;
5662 if (GET_MODE_NUNITS (mode) != 1)
5663 return false;
5664 if (GET_MODE_BITSIZE (mode) > 64
5665 || (GET_MODE_BITSIZE (mode) > 32 && !TARGET_POWERPC64
5666 && !(TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
5667 && (mode == DFmode || mode == DDmode))))
5668 return false;
5669
5670 return CONSTANT_P (x);
5671 }
5672
5673 return false;
5674 }
5675
5676
5677 /* Try machine-dependent ways of modifying an illegitimate address
5678 to be legitimate. If we find one, return the new, valid address.
5679 This is used from only one place: `memory_address' in explow.c.
5680
5681 OLDX is the address as it was before break_out_memory_refs was
5682 called. In some cases it is useful to look at this to decide what
5683 needs to be done.
5684
5685 It is always safe for this function to do nothing. It exists to
5686 recognize opportunities to optimize the output.
5687
5688 On RS/6000, first check for the sum of a register with a constant
5689 integer that is out of range. If so, generate code to add the
5690 constant with the low-order 16 bits masked to the register and force
5691 this result into another register (this can be done with `cau').
5692 Then generate an address of REG+(CONST&0xffff), allowing for the
5693 possibility of bit 16 being a one.
5694
5695 Then check for the sum of a register and something not constant, try to
5696 load the other things into a register and return the sum. */
5697
5698 static rtx
5699 rs6000_legitimize_address (rtx x, rtx oldx ATTRIBUTE_UNUSED,
5700 enum machine_mode mode)
5701 {
5702 unsigned int extra = 0;
5703
5704 if (!reg_offset_addressing_ok_p (mode))
5705 {
5706 if (virtual_stack_registers_memory_p (x))
5707 return x;
5708
5709 /* In theory we should not be seeing addresses of the form reg+0,
5710 but just in case it is generated, optimize it away. */
5711 if (GET_CODE (x) == PLUS && XEXP (x, 1) == const0_rtx)
5712 return force_reg (Pmode, XEXP (x, 0));
5713
5714 /* Make sure both operands are registers. */
5715 else if (GET_CODE (x) == PLUS)
5716 return gen_rtx_PLUS (Pmode,
5717 force_reg (Pmode, XEXP (x, 0)),
5718 force_reg (Pmode, XEXP (x, 1)));
5719 else
5720 return force_reg (Pmode, x);
5721 }
5722 if (GET_CODE (x) == SYMBOL_REF)
5723 {
5724 enum tls_model model = SYMBOL_REF_TLS_MODEL (x);
5725 if (model != 0)
5726 return rs6000_legitimize_tls_address (x, model);
5727 }
5728
5729 switch (mode)
5730 {
5731 case DFmode:
5732 case DDmode:
5733 extra = 4;
5734 break;
5735 case DImode:
5736 if (!TARGET_POWERPC64)
5737 extra = 4;
5738 break;
5739 case TFmode:
5740 case TDmode:
5741 extra = 12;
5742 break;
5743 case TImode:
5744 extra = TARGET_POWERPC64 ? 8 : 12;
5745 break;
5746 default:
5747 break;
5748 }
5749
5750 if (GET_CODE (x) == PLUS
5751 && GET_CODE (XEXP (x, 0)) == REG
5752 && GET_CODE (XEXP (x, 1)) == CONST_INT
5753 && ((unsigned HOST_WIDE_INT) (INTVAL (XEXP (x, 1)) + 0x8000)
5754 >= 0x10000 - extra)
5755 && !((TARGET_POWERPC64
5756 && (mode == DImode || mode == TImode)
5757 && (INTVAL (XEXP (x, 1)) & 3) != 0)
5758 || SPE_VECTOR_MODE (mode)
5759 || (TARGET_E500_DOUBLE && (mode == DFmode || mode == TFmode
5760 || mode == DImode || mode == DDmode
5761 || mode == TDmode))))
5762 {
5763 HOST_WIDE_INT high_int, low_int;
5764 rtx sum;
5765 low_int = ((INTVAL (XEXP (x, 1)) & 0xffff) ^ 0x8000) - 0x8000;
5766 if (low_int >= 0x8000 - extra)
5767 low_int = 0;
5768 high_int = INTVAL (XEXP (x, 1)) - low_int;
5769 sum = force_operand (gen_rtx_PLUS (Pmode, XEXP (x, 0),
5770 GEN_INT (high_int)), 0);
5771 return plus_constant (sum, low_int);
5772 }
5773 else if (GET_CODE (x) == PLUS
5774 && GET_CODE (XEXP (x, 0)) == REG
5775 && GET_CODE (XEXP (x, 1)) != CONST_INT
5776 && GET_MODE_NUNITS (mode) == 1
5777 && ((TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT)
5778 || TARGET_POWERPC64
5779 || ((mode != DImode && mode != DFmode && mode != DDmode)
5780 || (TARGET_E500_DOUBLE && mode != DDmode)))
5781 && (TARGET_POWERPC64 || mode != DImode)
5782 && !avoiding_indexed_address_p (mode)
5783 && mode != TImode
5784 && mode != TFmode
5785 && mode != TDmode)
5786 {
5787 return gen_rtx_PLUS (Pmode, XEXP (x, 0),
5788 force_reg (Pmode, force_operand (XEXP (x, 1), 0)));
5789 }
5790 else if (SPE_VECTOR_MODE (mode)
5791 || (TARGET_E500_DOUBLE && (mode == DFmode || mode == TFmode
5792 || mode == DDmode || mode == TDmode
5793 || mode == DImode)))
5794 {
5795 if (mode == DImode)
5796 return x;
5797 /* We accept [reg + reg] and [reg + OFFSET]. */
5798
5799 if (GET_CODE (x) == PLUS)
5800 {
5801 rtx op1 = XEXP (x, 0);
5802 rtx op2 = XEXP (x, 1);
5803 rtx y;
5804
5805 op1 = force_reg (Pmode, op1);
5806
5807 if (GET_CODE (op2) != REG
5808 && (GET_CODE (op2) != CONST_INT
5809 || !SPE_CONST_OFFSET_OK (INTVAL (op2))
5810 || (GET_MODE_SIZE (mode) > 8
5811 && !SPE_CONST_OFFSET_OK (INTVAL (op2) + 8))))
5812 op2 = force_reg (Pmode, op2);
5813
5814 /* We can't always do [reg + reg] for these, because [reg +
5815 reg + offset] is not a legitimate addressing mode. */
5816 y = gen_rtx_PLUS (Pmode, op1, op2);
5817
5818 if ((GET_MODE_SIZE (mode) > 8 || mode == DDmode) && REG_P (op2))
5819 return force_reg (Pmode, y);
5820 else
5821 return y;
5822 }
5823
5824 return force_reg (Pmode, x);
5825 }
5826 else if (TARGET_ELF
5827 && TARGET_32BIT
5828 && TARGET_NO_TOC
5829 && ! flag_pic
5830 && GET_CODE (x) != CONST_INT
5831 && GET_CODE (x) != CONST_DOUBLE
5832 && CONSTANT_P (x)
5833 && GET_MODE_NUNITS (mode) == 1
5834 && (GET_MODE_BITSIZE (mode) <= 32
5835 || ((TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT)
5836 && (mode == DFmode || mode == DDmode))))
5837 {
5838 rtx reg = gen_reg_rtx (Pmode);
5839 emit_insn (gen_elf_high (reg, x));
5840 return gen_rtx_LO_SUM (Pmode, reg, x);
5841 }
5842 else if (TARGET_MACHO && TARGET_32BIT && TARGET_NO_TOC
5843 && ! flag_pic
5844 #if TARGET_MACHO
5845 && ! MACHO_DYNAMIC_NO_PIC_P
5846 #endif
5847 && GET_CODE (x) != CONST_INT
5848 && GET_CODE (x) != CONST_DOUBLE
5849 && CONSTANT_P (x)
5850 && GET_MODE_NUNITS (mode) == 1
5851 && ((TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT)
5852 || (mode != DFmode && mode != DDmode))
5853 && mode != DImode
5854 && mode != TImode)
5855 {
5856 rtx reg = gen_reg_rtx (Pmode);
5857 emit_insn (gen_macho_high (reg, x));
5858 return gen_rtx_LO_SUM (Pmode, reg, x);
5859 }
5860 else if (TARGET_TOC
5861 && GET_CODE (x) == SYMBOL_REF
5862 && constant_pool_expr_p (x)
5863 && ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (get_pool_constant (x), Pmode))
5864 {
5865 rtx reg = TARGET_CMODEL != CMODEL_SMALL ? gen_reg_rtx (Pmode) : NULL_RTX;
5866 return create_TOC_reference (x, reg);
5867 }
5868 else
5869 return x;
5870 }
5871
5872 /* Debug version of rs6000_legitimize_address. */
5873 static rtx
5874 rs6000_debug_legitimize_address (rtx x, rtx oldx, enum machine_mode mode)
5875 {
5876 rtx ret;
5877 rtx insns;
5878
5879 start_sequence ();
5880 ret = rs6000_legitimize_address (x, oldx, mode);
5881 insns = get_insns ();
5882 end_sequence ();
5883
5884 if (ret != x)
5885 {
5886 fprintf (stderr,
5887 "\nrs6000_legitimize_address: mode %s, old code %s, "
5888 "new code %s, modified\n",
5889 GET_MODE_NAME (mode), GET_RTX_NAME (GET_CODE (x)),
5890 GET_RTX_NAME (GET_CODE (ret)));
5891
5892 fprintf (stderr, "Original address:\n");
5893 debug_rtx (x);
5894
5895 fprintf (stderr, "oldx:\n");
5896 debug_rtx (oldx);
5897
5898 fprintf (stderr, "New address:\n");
5899 debug_rtx (ret);
5900
5901 if (insns)
5902 {
5903 fprintf (stderr, "Insns added:\n");
5904 debug_rtx_list (insns, 20);
5905 }
5906 }
5907 else
5908 {
5909 fprintf (stderr,
5910 "\nrs6000_legitimize_address: mode %s, code %s, no change:\n",
5911 GET_MODE_NAME (mode), GET_RTX_NAME (GET_CODE (x)));
5912
5913 debug_rtx (x);
5914 }
5915
5916 if (insns)
5917 emit_insn (insns);
5918
5919 return ret;
5920 }
5921
5922 /* This is called from dwarf2out.c via TARGET_ASM_OUTPUT_DWARF_DTPREL.
5923 We need to emit DTP-relative relocations. */
5924
5925 static void
5926 rs6000_output_dwarf_dtprel (FILE *file, int size, rtx x)
5927 {
5928 switch (size)
5929 {
5930 case 4:
5931 fputs ("\t.long\t", file);
5932 break;
5933 case 8:
5934 fputs (DOUBLE_INT_ASM_OP, file);
5935 break;
5936 default:
5937 gcc_unreachable ();
5938 }
5939 output_addr_const (file, x);
5940 fputs ("@dtprel+0x8000", file);
5941 }
5942
5943 /* In the name of slightly smaller debug output, and to cater to
5944 general assembler lossage, recognize various UNSPEC sequences
5945 and turn them back into a direct symbol reference. */
5946
5947 static rtx
5948 rs6000_delegitimize_address (rtx orig_x)
5949 {
5950 rtx x, y;
5951
5952 orig_x = delegitimize_mem_from_attrs (orig_x);
5953 x = orig_x;
5954 if (MEM_P (x))
5955 x = XEXP (x, 0);
5956
5957 if ((GET_CODE (x) == PLUS
5958 || GET_CODE (x) == LO_SUM)
5959 && GET_CODE (XEXP (x, 0)) == REG
5960 && (REGNO (XEXP (x, 0)) == TOC_REGISTER
5961 || TARGET_MINIMAL_TOC
5962 || TARGET_CMODEL != CMODEL_SMALL)
5963 && GET_CODE (XEXP (x, 1)) == CONST)
5964 {
5965 y = XEXP (XEXP (x, 1), 0);
5966 if (GET_CODE (y) == UNSPEC
5967 && XINT (y, 1) == UNSPEC_TOCREL)
5968 {
5969 y = XVECEXP (y, 0, 0);
5970 if (!MEM_P (orig_x))
5971 return y;
5972 else
5973 return replace_equiv_address_nv (orig_x, y);
5974 }
5975 }
5976
5977 if (TARGET_MACHO
5978 && GET_CODE (orig_x) == LO_SUM
5979 && GET_CODE (XEXP (x, 1)) == CONST)
5980 {
5981 y = XEXP (XEXP (x, 1), 0);
5982 if (GET_CODE (y) == UNSPEC
5983 && XINT (y, 1) == UNSPEC_MACHOPIC_OFFSET)
5984 return XVECEXP (y, 0, 0);
5985 }
5986
5987 return orig_x;
5988 }
5989
5990 /* Construct the SYMBOL_REF for the tls_get_addr function. */
5991
5992 static GTY(()) rtx rs6000_tls_symbol;
5993 static rtx
5994 rs6000_tls_get_addr (void)
5995 {
5996 if (!rs6000_tls_symbol)
5997 rs6000_tls_symbol = init_one_libfunc ("__tls_get_addr");
5998
5999 return rs6000_tls_symbol;
6000 }
6001
6002 /* Construct the SYMBOL_REF for TLS GOT references. */
6003
6004 static GTY(()) rtx rs6000_got_symbol;
6005 static rtx
6006 rs6000_got_sym (void)
6007 {
6008 if (!rs6000_got_symbol)
6009 {
6010 rs6000_got_symbol = gen_rtx_SYMBOL_REF (Pmode, "_GLOBAL_OFFSET_TABLE_");
6011 SYMBOL_REF_FLAGS (rs6000_got_symbol) |= SYMBOL_FLAG_LOCAL;
6012 SYMBOL_REF_FLAGS (rs6000_got_symbol) |= SYMBOL_FLAG_EXTERNAL;
6013 }
6014
6015 return rs6000_got_symbol;
6016 }
6017
6018 /* ADDR contains a thread-local SYMBOL_REF. Generate code to compute
6019 this (thread-local) address. */
6020
6021 static rtx
6022 rs6000_legitimize_tls_address (rtx addr, enum tls_model model)
6023 {
6024 rtx dest, insn;
6025
6026 dest = gen_reg_rtx (Pmode);
6027 if (model == TLS_MODEL_LOCAL_EXEC && rs6000_tls_size == 16)
6028 {
6029 rtx tlsreg;
6030
6031 if (TARGET_64BIT)
6032 {
6033 tlsreg = gen_rtx_REG (Pmode, 13);
6034 insn = gen_tls_tprel_64 (dest, tlsreg, addr);
6035 }
6036 else
6037 {
6038 tlsreg = gen_rtx_REG (Pmode, 2);
6039 insn = gen_tls_tprel_32 (dest, tlsreg, addr);
6040 }
6041 emit_insn (insn);
6042 }
6043 else if (model == TLS_MODEL_LOCAL_EXEC && rs6000_tls_size == 32)
6044 {
6045 rtx tlsreg, tmp;
6046
6047 tmp = gen_reg_rtx (Pmode);
6048 if (TARGET_64BIT)
6049 {
6050 tlsreg = gen_rtx_REG (Pmode, 13);
6051 insn = gen_tls_tprel_ha_64 (tmp, tlsreg, addr);
6052 }
6053 else
6054 {
6055 tlsreg = gen_rtx_REG (Pmode, 2);
6056 insn = gen_tls_tprel_ha_32 (tmp, tlsreg, addr);
6057 }
6058 emit_insn (insn);
6059 if (TARGET_64BIT)
6060 insn = gen_tls_tprel_lo_64 (dest, tmp, addr);
6061 else
6062 insn = gen_tls_tprel_lo_32 (dest, tmp, addr);
6063 emit_insn (insn);
6064 }
6065 else
6066 {
6067 rtx r3, got, tga, tmp1, tmp2, call_insn;
6068
6069 /* We currently use relocations like @got@tlsgd for tls, which
6070 means the linker will handle allocation of tls entries, placing
6071 them in the .got section. So use a pointer to the .got section,
6072 not one to secondary TOC sections used by 64-bit -mminimal-toc,
6073 or to secondary GOT sections used by 32-bit -fPIC. */
6074 if (TARGET_64BIT)
6075 got = gen_rtx_REG (Pmode, 2);
6076 else
6077 {
6078 if (flag_pic == 1)
6079 got = gen_rtx_REG (Pmode, RS6000_PIC_OFFSET_TABLE_REGNUM);
6080 else
6081 {
6082 rtx gsym = rs6000_got_sym ();
6083 got = gen_reg_rtx (Pmode);
6084 if (flag_pic == 0)
6085 rs6000_emit_move (got, gsym, Pmode);
6086 else
6087 {
6088 rtx mem, lab, last;
6089
6090 tmp1 = gen_reg_rtx (Pmode);
6091 tmp2 = gen_reg_rtx (Pmode);
6092 mem = gen_const_mem (Pmode, tmp1);
6093 lab = gen_label_rtx ();
6094 emit_insn (gen_load_toc_v4_PIC_1b (gsym, lab));
6095 emit_move_insn (tmp1, gen_rtx_REG (Pmode, LR_REGNO));
6096 emit_move_insn (tmp2, mem);
6097 last = emit_insn (gen_addsi3 (got, tmp1, tmp2));
6098 set_unique_reg_note (last, REG_EQUAL, gsym);
6099 }
6100 }
6101 }
6102
6103 if (model == TLS_MODEL_GLOBAL_DYNAMIC)
6104 {
6105 r3 = gen_rtx_REG (Pmode, 3);
6106 tga = rs6000_tls_get_addr ();
6107 emit_library_call_value (tga, dest, LCT_CONST, Pmode, 1, r3, Pmode);
6108
6109 if (DEFAULT_ABI == ABI_AIX && TARGET_64BIT)
6110 insn = gen_tls_gd_aix64 (r3, got, addr, tga, const0_rtx);
6111 else if (DEFAULT_ABI == ABI_AIX && !TARGET_64BIT)
6112 insn = gen_tls_gd_aix32 (r3, got, addr, tga, const0_rtx);
6113 else if (DEFAULT_ABI == ABI_V4)
6114 insn = gen_tls_gd_sysvsi (r3, got, addr, tga, const0_rtx);
6115 else
6116 gcc_unreachable ();
6117 call_insn = last_call_insn ();
6118 PATTERN (call_insn) = insn;
6119 if (DEFAULT_ABI == ABI_V4 && TARGET_SECURE_PLT && flag_pic)
6120 use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn),
6121 pic_offset_table_rtx);
6122 }
6123 else if (model == TLS_MODEL_LOCAL_DYNAMIC)
6124 {
6125 r3 = gen_rtx_REG (Pmode, 3);
6126 tga = rs6000_tls_get_addr ();
6127 tmp1 = gen_reg_rtx (Pmode);
6128 emit_library_call_value (tga, tmp1, LCT_CONST, Pmode, 1, r3, Pmode);
6129
6130 if (DEFAULT_ABI == ABI_AIX && TARGET_64BIT)
6131 insn = gen_tls_ld_aix64 (r3, got, tga, const0_rtx);
6132 else if (DEFAULT_ABI == ABI_AIX && !TARGET_64BIT)
6133 insn = gen_tls_ld_aix32 (r3, got, tga, const0_rtx);
6134 else if (DEFAULT_ABI == ABI_V4)
6135 insn = gen_tls_ld_sysvsi (r3, got, tga, const0_rtx);
6136 else
6137 gcc_unreachable ();
6138 call_insn = last_call_insn ();
6139 PATTERN (call_insn) = insn;
6140 if (DEFAULT_ABI == ABI_V4 && TARGET_SECURE_PLT && flag_pic)
6141 use_reg (&CALL_INSN_FUNCTION_USAGE (call_insn),
6142 pic_offset_table_rtx);
6143
6144 if (rs6000_tls_size == 16)
6145 {
6146 if (TARGET_64BIT)
6147 insn = gen_tls_dtprel_64 (dest, tmp1, addr);
6148 else
6149 insn = gen_tls_dtprel_32 (dest, tmp1, addr);
6150 }
6151 else if (rs6000_tls_size == 32)
6152 {
6153 tmp2 = gen_reg_rtx (Pmode);
6154 if (TARGET_64BIT)
6155 insn = gen_tls_dtprel_ha_64 (tmp2, tmp1, addr);
6156 else
6157 insn = gen_tls_dtprel_ha_32 (tmp2, tmp1, addr);
6158 emit_insn (insn);
6159 if (TARGET_64BIT)
6160 insn = gen_tls_dtprel_lo_64 (dest, tmp2, addr);
6161 else
6162 insn = gen_tls_dtprel_lo_32 (dest, tmp2, addr);
6163 }
6164 else
6165 {
6166 tmp2 = gen_reg_rtx (Pmode);
6167 if (TARGET_64BIT)
6168 insn = gen_tls_got_dtprel_64 (tmp2, got, addr);
6169 else
6170 insn = gen_tls_got_dtprel_32 (tmp2, got, addr);
6171 emit_insn (insn);
6172 insn = gen_rtx_SET (Pmode, dest,
6173 gen_rtx_PLUS (Pmode, tmp2, tmp1));
6174 }
6175 emit_insn (insn);
6176 }
6177 else
6178 {
6179 /* IE, or 64-bit offset LE. */
6180 tmp2 = gen_reg_rtx (Pmode);
6181 if (TARGET_64BIT)
6182 insn = gen_tls_got_tprel_64 (tmp2, got, addr);
6183 else
6184 insn = gen_tls_got_tprel_32 (tmp2, got, addr);
6185 emit_insn (insn);
6186 if (TARGET_64BIT)
6187 insn = gen_tls_tls_64 (dest, tmp2, addr);
6188 else
6189 insn = gen_tls_tls_32 (dest, tmp2, addr);
6190 emit_insn (insn);
6191 }
6192 }
6193
6194 return dest;
6195 }
6196
6197 /* Return 1 if X contains a thread-local symbol. */
6198
6199 bool
6200 rs6000_tls_referenced_p (rtx x)
6201 {
6202 if (! TARGET_HAVE_TLS)
6203 return false;
6204
6205 return for_each_rtx (&x, &rs6000_tls_symbol_ref_1, 0);
6206 }
6207
6208 /* Return 1 if *X is a thread-local symbol. This is the same as
6209 rs6000_tls_symbol_ref except for the type of the unused argument. */
6210
6211 static int
6212 rs6000_tls_symbol_ref_1 (rtx *x, void *data ATTRIBUTE_UNUSED)
6213 {
6214 return RS6000_SYMBOL_REF_TLS_P (*x);
6215 }
6216
6217 /* Our implementation of LEGITIMIZE_RELOAD_ADDRESS. Returns a value to
6218 replace the input X, or the original X if no replacement is called for.
6219 The output parameter *WIN is 1 if the calling macro should goto WIN,
6220 0 if it should not.
6221
6222 For RS/6000, we wish to handle large displacements off a base
6223 register by splitting the addend across an addiu/addis and the mem insn.
6224 This cuts number of extra insns needed from 3 to 1.
6225
6226 On Darwin, we use this to generate code for floating point constants.
6227 A movsf_low is generated so we wind up with 2 instructions rather than 3.
6228 The Darwin code is inside #if TARGET_MACHO because only then are the
6229 machopic_* functions defined. */
6230 static rtx
6231 rs6000_legitimize_reload_address (rtx x, enum machine_mode mode,
6232 int opnum, int type,
6233 int ind_levels ATTRIBUTE_UNUSED, int *win)
6234 {
6235 bool reg_offset_p = reg_offset_addressing_ok_p (mode);
6236
6237 /* We must recognize output that we have already generated ourselves. */
6238 if (GET_CODE (x) == PLUS
6239 && GET_CODE (XEXP (x, 0)) == PLUS
6240 && GET_CODE (XEXP (XEXP (x, 0), 0)) == REG
6241 && GET_CODE (XEXP (XEXP (x, 0), 1)) == CONST_INT
6242 && GET_CODE (XEXP (x, 1)) == CONST_INT)
6243 {
6244 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
6245 BASE_REG_CLASS, GET_MODE (x), VOIDmode, 0, 0,
6246 opnum, (enum reload_type)type);
6247 *win = 1;
6248 return x;
6249 }
6250
6251 /* Likewise for (lo_sum (high ...) ...) output we have generated. */
6252 if (GET_CODE (x) == LO_SUM
6253 && GET_CODE (XEXP (x, 0)) == HIGH)
6254 {
6255 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
6256 BASE_REG_CLASS, Pmode, VOIDmode, 0, 0,
6257 opnum, (enum reload_type)type);
6258 *win = 1;
6259 return x;
6260 }
6261
6262 #if TARGET_MACHO
6263 if (DEFAULT_ABI == ABI_DARWIN && flag_pic
6264 && GET_CODE (x) == LO_SUM
6265 && GET_CODE (XEXP (x, 0)) == PLUS
6266 && XEXP (XEXP (x, 0), 0) == pic_offset_table_rtx
6267 && GET_CODE (XEXP (XEXP (x, 0), 1)) == HIGH
6268 && XEXP (XEXP (XEXP (x, 0), 1), 0) == XEXP (x, 1)
6269 && machopic_operand_p (XEXP (x, 1)))
6270 {
6271 /* Result of previous invocation of this function on Darwin
6272 floating point constant. */
6273 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
6274 BASE_REG_CLASS, Pmode, VOIDmode, 0, 0,
6275 opnum, (enum reload_type)type);
6276 *win = 1;
6277 return x;
6278 }
6279 #endif
6280
6281 if (TARGET_CMODEL != CMODEL_SMALL
6282 && GET_CODE (x) == LO_SUM
6283 && GET_CODE (XEXP (x, 0)) == PLUS
6284 && GET_CODE (XEXP (XEXP (x, 0), 0)) == REG
6285 && REGNO (XEXP (XEXP (x, 0), 0)) == TOC_REGISTER
6286 && GET_CODE (XEXP (XEXP (x, 0), 1)) == HIGH
6287 && GET_CODE (XEXP (x, 1)) == CONST
6288 && GET_CODE (XEXP (XEXP (x, 1), 0)) == UNSPEC
6289 && XINT (XEXP (XEXP (x, 1), 0), 1) == UNSPEC_TOCREL
6290 && rtx_equal_p (XEXP (XEXP (XEXP (x, 0), 1), 0), XEXP (x, 1)))
6291 {
6292 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
6293 BASE_REG_CLASS, Pmode, VOIDmode, 0, 0,
6294 opnum, (enum reload_type) type);
6295 *win = 1;
6296 return x;
6297 }
6298
6299 /* Force ld/std non-word aligned offset into base register by wrapping
6300 in offset 0. */
6301 if (GET_CODE (x) == PLUS
6302 && GET_CODE (XEXP (x, 0)) == REG
6303 && REGNO (XEXP (x, 0)) < 32
6304 && INT_REG_OK_FOR_BASE_P (XEXP (x, 0), 1)
6305 && GET_CODE (XEXP (x, 1)) == CONST_INT
6306 && reg_offset_p
6307 && (INTVAL (XEXP (x, 1)) & 3) != 0
6308 && VECTOR_MEM_NONE_P (mode)
6309 && GET_MODE_SIZE (mode) >= UNITS_PER_WORD
6310 && TARGET_POWERPC64)
6311 {
6312 x = gen_rtx_PLUS (GET_MODE (x), x, GEN_INT (0));
6313 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
6314 BASE_REG_CLASS, GET_MODE (x), VOIDmode, 0, 0,
6315 opnum, (enum reload_type) type);
6316 *win = 1;
6317 return x;
6318 }
6319
6320 if (GET_CODE (x) == PLUS
6321 && GET_CODE (XEXP (x, 0)) == REG
6322 && REGNO (XEXP (x, 0)) < FIRST_PSEUDO_REGISTER
6323 && INT_REG_OK_FOR_BASE_P (XEXP (x, 0), 1)
6324 && GET_CODE (XEXP (x, 1)) == CONST_INT
6325 && reg_offset_p
6326 && !SPE_VECTOR_MODE (mode)
6327 && !(TARGET_E500_DOUBLE && (mode == DFmode || mode == TFmode
6328 || mode == DDmode || mode == TDmode
6329 || mode == DImode))
6330 && VECTOR_MEM_NONE_P (mode))
6331 {
6332 HOST_WIDE_INT val = INTVAL (XEXP (x, 1));
6333 HOST_WIDE_INT low = ((val & 0xffff) ^ 0x8000) - 0x8000;
6334 HOST_WIDE_INT high
6335 = (((val - low) & 0xffffffff) ^ 0x80000000) - 0x80000000;
6336
6337 /* Check for 32-bit overflow. */
6338 if (high + low != val)
6339 {
6340 *win = 0;
6341 return x;
6342 }
6343
6344 /* Reload the high part into a base reg; leave the low part
6345 in the mem directly. */
6346
6347 x = gen_rtx_PLUS (GET_MODE (x),
6348 gen_rtx_PLUS (GET_MODE (x), XEXP (x, 0),
6349 GEN_INT (high)),
6350 GEN_INT (low));
6351
6352 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
6353 BASE_REG_CLASS, GET_MODE (x), VOIDmode, 0, 0,
6354 opnum, (enum reload_type)type);
6355 *win = 1;
6356 return x;
6357 }
6358
6359 if (GET_CODE (x) == SYMBOL_REF
6360 && reg_offset_p
6361 && VECTOR_MEM_NONE_P (mode)
6362 && !SPE_VECTOR_MODE (mode)
6363 #if TARGET_MACHO
6364 && DEFAULT_ABI == ABI_DARWIN
6365 && (flag_pic || MACHO_DYNAMIC_NO_PIC_P)
6366 #else
6367 && DEFAULT_ABI == ABI_V4
6368 && !flag_pic
6369 #endif
6370 /* Don't do this for TFmode or TDmode, since the result isn't offsettable.
6371 The same goes for DImode without 64-bit gprs and DFmode and DDmode
6372 without fprs. */
6373 && mode != TFmode
6374 && mode != TDmode
6375 && (mode != DImode || TARGET_POWERPC64)
6376 && ((mode != DFmode && mode != DDmode) || TARGET_POWERPC64
6377 || (TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT)))
6378 {
6379 #if TARGET_MACHO
6380 if (flag_pic)
6381 {
6382 rtx offset = machopic_gen_offset (x);
6383 x = gen_rtx_LO_SUM (GET_MODE (x),
6384 gen_rtx_PLUS (Pmode, pic_offset_table_rtx,
6385 gen_rtx_HIGH (Pmode, offset)), offset);
6386 }
6387 else
6388 #endif
6389 x = gen_rtx_LO_SUM (GET_MODE (x),
6390 gen_rtx_HIGH (Pmode, x), x);
6391
6392 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
6393 BASE_REG_CLASS, Pmode, VOIDmode, 0, 0,
6394 opnum, (enum reload_type)type);
6395 *win = 1;
6396 return x;
6397 }
6398
6399 /* Reload an offset address wrapped by an AND that represents the
6400 masking of the lower bits. Strip the outer AND and let reload
6401 convert the offset address into an indirect address. For VSX,
6402 force reload to create the address with an AND in a separate
6403 register, because we can't guarantee an altivec register will
6404 be used. */
6405 if (VECTOR_MEM_ALTIVEC_P (mode)
6406 && GET_CODE (x) == AND
6407 && GET_CODE (XEXP (x, 0)) == PLUS
6408 && GET_CODE (XEXP (XEXP (x, 0), 0)) == REG
6409 && GET_CODE (XEXP (XEXP (x, 0), 1)) == CONST_INT
6410 && GET_CODE (XEXP (x, 1)) == CONST_INT
6411 && INTVAL (XEXP (x, 1)) == -16)
6412 {
6413 x = XEXP (x, 0);
6414 *win = 1;
6415 return x;
6416 }
6417
6418 if (TARGET_TOC
6419 && reg_offset_p
6420 && GET_CODE (x) == SYMBOL_REF
6421 && constant_pool_expr_p (x)
6422 && ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (get_pool_constant (x), mode))
6423 {
6424 x = create_TOC_reference (x, NULL_RTX);
6425 if (TARGET_CMODEL != CMODEL_SMALL)
6426 push_reload (XEXP (x, 0), NULL_RTX, &XEXP (x, 0), NULL,
6427 BASE_REG_CLASS, Pmode, VOIDmode, 0, 0,
6428 opnum, (enum reload_type) type);
6429 *win = 1;
6430 return x;
6431 }
6432 *win = 0;
6433 return x;
6434 }
6435
6436 /* Debug version of rs6000_legitimize_reload_address. */
6437 static rtx
6438 rs6000_debug_legitimize_reload_address (rtx x, enum machine_mode mode,
6439 int opnum, int type,
6440 int ind_levels, int *win)
6441 {
6442 rtx ret = rs6000_legitimize_reload_address (x, mode, opnum, type,
6443 ind_levels, win);
6444 fprintf (stderr,
6445 "\nrs6000_legitimize_reload_address: mode = %s, opnum = %d, "
6446 "type = %d, ind_levels = %d, win = %d, original addr:\n",
6447 GET_MODE_NAME (mode), opnum, type, ind_levels, *win);
6448 debug_rtx (x);
6449
6450 if (x == ret)
6451 fprintf (stderr, "Same address returned\n");
6452 else if (!ret)
6453 fprintf (stderr, "NULL returned\n");
6454 else
6455 {
6456 fprintf (stderr, "New address:\n");
6457 debug_rtx (ret);
6458 }
6459
6460 return ret;
6461 }
6462
6463 /* TARGET_LEGITIMATE_ADDRESS_P recognizes an RTL expression
6464 that is a valid memory address for an instruction.
6465 The MODE argument is the machine mode for the MEM expression
6466 that wants to use this address.
6467
6468 On the RS/6000, there are four valid address: a SYMBOL_REF that
6469 refers to a constant pool entry of an address (or the sum of it
6470 plus a constant), a short (16-bit signed) constant plus a register,
6471 the sum of two registers, or a register indirect, possibly with an
6472 auto-increment. For DFmode, DDmode and DImode with a constant plus
6473 register, we must ensure that both words are addressable or PowerPC64
6474 with offset word aligned.
6475
6476 For modes spanning multiple registers (DFmode and DDmode in 32-bit GPRs,
6477 32-bit DImode, TImode, TFmode, TDmode), indexed addressing cannot be used
6478 because adjacent memory cells are accessed by adding word-sized offsets
6479 during assembly output. */
6480 bool
6481 rs6000_legitimate_address_p (enum machine_mode mode, rtx x, bool reg_ok_strict)
6482 {
6483 bool reg_offset_p = reg_offset_addressing_ok_p (mode);
6484
6485 /* If this is an unaligned stvx/ldvx type address, discard the outer AND. */
6486 if (VECTOR_MEM_ALTIVEC_P (mode)
6487 && GET_CODE (x) == AND
6488 && GET_CODE (XEXP (x, 1)) == CONST_INT
6489 && INTVAL (XEXP (x, 1)) == -16)
6490 x = XEXP (x, 0);
6491
6492 if (RS6000_SYMBOL_REF_TLS_P (x))
6493 return 0;
6494 if (legitimate_indirect_address_p (x, reg_ok_strict))
6495 return 1;
6496 if ((GET_CODE (x) == PRE_INC || GET_CODE (x) == PRE_DEC)
6497 && !VECTOR_MEM_ALTIVEC_OR_VSX_P (mode)
6498 && !SPE_VECTOR_MODE (mode)
6499 && mode != TFmode
6500 && mode != TDmode
6501 /* Restrict addressing for DI because of our SUBREG hackery. */
6502 && !(TARGET_E500_DOUBLE
6503 && (mode == DFmode || mode == DDmode || mode == DImode))
6504 && TARGET_UPDATE
6505 && legitimate_indirect_address_p (XEXP (x, 0), reg_ok_strict))
6506 return 1;
6507 if (virtual_stack_registers_memory_p (x))
6508 return 1;
6509 if (reg_offset_p && legitimate_small_data_p (mode, x))
6510 return 1;
6511 if (reg_offset_p && legitimate_constant_pool_address_p (x, reg_ok_strict))
6512 return 1;
6513 /* If not REG_OK_STRICT (before reload) let pass any stack offset. */
6514 if (! reg_ok_strict
6515 && reg_offset_p
6516 && GET_CODE (x) == PLUS
6517 && GET_CODE (XEXP (x, 0)) == REG
6518 && (XEXP (x, 0) == virtual_stack_vars_rtx
6519 || XEXP (x, 0) == arg_pointer_rtx)
6520 && GET_CODE (XEXP (x, 1)) == CONST_INT)
6521 return 1;
6522 if (rs6000_legitimate_offset_address_p (mode, x, reg_ok_strict))
6523 return 1;
6524 if (mode != TImode
6525 && mode != TFmode
6526 && mode != TDmode
6527 && ((TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT)
6528 || TARGET_POWERPC64
6529 || (mode != DFmode && mode != DDmode)
6530 || (TARGET_E500_DOUBLE && mode != DDmode))
6531 && (TARGET_POWERPC64 || mode != DImode)
6532 && !avoiding_indexed_address_p (mode)
6533 && legitimate_indexed_address_p (x, reg_ok_strict))
6534 return 1;
6535 if (GET_CODE (x) == PRE_MODIFY
6536 && mode != TImode
6537 && mode != TFmode
6538 && mode != TDmode
6539 && ((TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT)
6540 || TARGET_POWERPC64
6541 || ((mode != DFmode && mode != DDmode) || TARGET_E500_DOUBLE))
6542 && (TARGET_POWERPC64 || mode != DImode)
6543 && !VECTOR_MEM_ALTIVEC_OR_VSX_P (mode)
6544 && !SPE_VECTOR_MODE (mode)
6545 /* Restrict addressing for DI because of our SUBREG hackery. */
6546 && !(TARGET_E500_DOUBLE
6547 && (mode == DFmode || mode == DDmode || mode == DImode))
6548 && TARGET_UPDATE
6549 && legitimate_indirect_address_p (XEXP (x, 0), reg_ok_strict)
6550 && (rs6000_legitimate_offset_address_p (mode, XEXP (x, 1), reg_ok_strict)
6551 || (!avoiding_indexed_address_p (mode)
6552 && legitimate_indexed_address_p (XEXP (x, 1), reg_ok_strict)))
6553 && rtx_equal_p (XEXP (XEXP (x, 1), 0), XEXP (x, 0)))
6554 return 1;
6555 if (reg_offset_p && legitimate_lo_sum_address_p (mode, x, reg_ok_strict))
6556 return 1;
6557 return 0;
6558 }
6559
6560 /* Debug version of rs6000_legitimate_address_p. */
6561 static bool
6562 rs6000_debug_legitimate_address_p (enum machine_mode mode, rtx x,
6563 bool reg_ok_strict)
6564 {
6565 bool ret = rs6000_legitimate_address_p (mode, x, reg_ok_strict);
6566 fprintf (stderr,
6567 "\nrs6000_legitimate_address_p: return = %s, mode = %s, "
6568 "strict = %d, code = %s\n",
6569 ret ? "true" : "false",
6570 GET_MODE_NAME (mode),
6571 reg_ok_strict,
6572 GET_RTX_NAME (GET_CODE (x)));
6573 debug_rtx (x);
6574
6575 return ret;
6576 }
6577
6578 /* Implement TARGET_MODE_DEPENDENT_ADDRESS_P. */
6579
6580 static bool
6581 rs6000_mode_dependent_address_p (const_rtx addr)
6582 {
6583 return rs6000_mode_dependent_address_ptr (addr);
6584 }
6585
6586 /* Go to LABEL if ADDR (a legitimate address expression)
6587 has an effect that depends on the machine mode it is used for.
6588
6589 On the RS/6000 this is true of all integral offsets (since AltiVec
6590 and VSX modes don't allow them) or is a pre-increment or decrement.
6591
6592 ??? Except that due to conceptual problems in offsettable_address_p
6593 we can't really report the problems of integral offsets. So leave
6594 this assuming that the adjustable offset must be valid for the
6595 sub-words of a TFmode operand, which is what we had before. */
6596
6597 static bool
6598 rs6000_mode_dependent_address (const_rtx addr)
6599 {
6600 switch (GET_CODE (addr))
6601 {
6602 case PLUS:
6603 /* Any offset from virtual_stack_vars_rtx and arg_pointer_rtx
6604 is considered a legitimate address before reload, so there
6605 are no offset restrictions in that case. Note that this
6606 condition is safe in strict mode because any address involving
6607 virtual_stack_vars_rtx or arg_pointer_rtx would already have
6608 been rejected as illegitimate. */
6609 if (XEXP (addr, 0) != virtual_stack_vars_rtx
6610 && XEXP (addr, 0) != arg_pointer_rtx
6611 && GET_CODE (XEXP (addr, 1)) == CONST_INT)
6612 {
6613 unsigned HOST_WIDE_INT val = INTVAL (XEXP (addr, 1));
6614 return val + 12 + 0x8000 >= 0x10000;
6615 }
6616 break;
6617
6618 case LO_SUM:
6619 /* Anything in the constant pool is sufficiently aligned that
6620 all bytes have the same high part address. */
6621 return !legitimate_constant_pool_address_p (addr, false);
6622
6623 /* Auto-increment cases are now treated generically in recog.c. */
6624 case PRE_MODIFY:
6625 return TARGET_UPDATE;
6626
6627 /* AND is only allowed in Altivec loads. */
6628 case AND:
6629 return true;
6630
6631 default:
6632 break;
6633 }
6634
6635 return false;
6636 }
6637
6638 /* Debug version of rs6000_mode_dependent_address. */
6639 static bool
6640 rs6000_debug_mode_dependent_address (const_rtx addr)
6641 {
6642 bool ret = rs6000_mode_dependent_address (addr);
6643
6644 fprintf (stderr, "\nrs6000_mode_dependent_address: ret = %s\n",
6645 ret ? "true" : "false");
6646 debug_rtx (addr);
6647
6648 return ret;
6649 }
6650
6651 /* Implement FIND_BASE_TERM. */
6652
6653 rtx
6654 rs6000_find_base_term (rtx op)
6655 {
6656 rtx base, offset;
6657
6658 split_const (op, &base, &offset);
6659 if (GET_CODE (base) == UNSPEC)
6660 switch (XINT (base, 1))
6661 {
6662 case UNSPEC_TOCREL:
6663 case UNSPEC_MACHOPIC_OFFSET:
6664 /* OP represents SYM [+ OFFSET] - ANCHOR. SYM is the base term
6665 for aliasing purposes. */
6666 return XVECEXP (base, 0, 0);
6667 }
6668
6669 return op;
6670 }
6671
6672 /* More elaborate version of recog's offsettable_memref_p predicate
6673 that works around the ??? note of rs6000_mode_dependent_address.
6674 In particular it accepts
6675
6676 (mem:DI (plus:SI (reg/f:SI 31 31) (const_int 32760 [0x7ff8])))
6677
6678 in 32-bit mode, that the recog predicate rejects. */
6679
6680 bool
6681 rs6000_offsettable_memref_p (rtx op)
6682 {
6683 if (!MEM_P (op))
6684 return false;
6685
6686 /* First mimic offsettable_memref_p. */
6687 if (offsettable_address_p (1, GET_MODE (op), XEXP (op, 0)))
6688 return true;
6689
6690 /* offsettable_address_p invokes rs6000_mode_dependent_address, but
6691 the latter predicate knows nothing about the mode of the memory
6692 reference and, therefore, assumes that it is the largest supported
6693 mode (TFmode). As a consequence, legitimate offsettable memory
6694 references are rejected. rs6000_legitimate_offset_address_p contains
6695 the correct logic for the PLUS case of rs6000_mode_dependent_address. */
6696 return rs6000_legitimate_offset_address_p (GET_MODE (op), XEXP (op, 0), 1);
6697 }
6698
6699 /* Change register usage conditional on target flags. */
6700 void
6701 rs6000_conditional_register_usage (void)
6702 {
6703 int i;
6704
6705 /* Set MQ register fixed (already call_used) if not POWER
6706 architecture (RIOS1, RIOS2, RSC, and PPC601) so that it will not
6707 be allocated. */
6708 if (! TARGET_POWER)
6709 fixed_regs[64] = 1;
6710
6711 /* 64-bit AIX and Linux reserve GPR13 for thread-private data. */
6712 if (TARGET_64BIT)
6713 fixed_regs[13] = call_used_regs[13]
6714 = call_really_used_regs[13] = 1;
6715
6716 /* Conditionally disable FPRs. */
6717 if (TARGET_SOFT_FLOAT || !TARGET_FPRS)
6718 for (i = 32; i < 64; i++)
6719 fixed_regs[i] = call_used_regs[i]
6720 = call_really_used_regs[i] = 1;
6721
6722 /* The TOC register is not killed across calls in a way that is
6723 visible to the compiler. */
6724 if (DEFAULT_ABI == ABI_AIX)
6725 call_really_used_regs[2] = 0;
6726
6727 if (DEFAULT_ABI == ABI_V4
6728 && PIC_OFFSET_TABLE_REGNUM != INVALID_REGNUM
6729 && flag_pic == 2)
6730 fixed_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] = 1;
6731
6732 if (DEFAULT_ABI == ABI_V4
6733 && PIC_OFFSET_TABLE_REGNUM != INVALID_REGNUM
6734 && flag_pic == 1)
6735 fixed_regs[RS6000_PIC_OFFSET_TABLE_REGNUM]
6736 = call_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM]
6737 = call_really_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] = 1;
6738
6739 if (DEFAULT_ABI == ABI_DARWIN
6740 && PIC_OFFSET_TABLE_REGNUM != INVALID_REGNUM)
6741 fixed_regs[RS6000_PIC_OFFSET_TABLE_REGNUM]
6742 = call_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM]
6743 = call_really_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] = 1;
6744
6745 if (TARGET_TOC && TARGET_MINIMAL_TOC)
6746 fixed_regs[RS6000_PIC_OFFSET_TABLE_REGNUM]
6747 = call_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] = 1;
6748
6749 if (TARGET_SPE)
6750 {
6751 global_regs[SPEFSCR_REGNO] = 1;
6752 /* We used to use r14 as FIXED_SCRATCH to address SPE 64-bit
6753 registers in prologues and epilogues. We no longer use r14
6754 for FIXED_SCRATCH, but we're keeping r14 out of the allocation
6755 pool for link-compatibility with older versions of GCC. Once
6756 "old" code has died out, we can return r14 to the allocation
6757 pool. */
6758 fixed_regs[14]
6759 = call_used_regs[14]
6760 = call_really_used_regs[14] = 1;
6761 }
6762
6763 if (!TARGET_ALTIVEC && !TARGET_VSX)
6764 {
6765 for (i = FIRST_ALTIVEC_REGNO; i <= LAST_ALTIVEC_REGNO; ++i)
6766 fixed_regs[i] = call_used_regs[i] = call_really_used_regs[i] = 1;
6767 call_really_used_regs[VRSAVE_REGNO] = 1;
6768 }
6769
6770 if (TARGET_ALTIVEC || TARGET_VSX)
6771 global_regs[VSCR_REGNO] = 1;
6772
6773 if (TARGET_ALTIVEC_ABI)
6774 {
6775 for (i = FIRST_ALTIVEC_REGNO; i < FIRST_ALTIVEC_REGNO + 20; ++i)
6776 call_used_regs[i] = call_really_used_regs[i] = 1;
6777
6778 /* AIX reserves VR20:31 in non-extended ABI mode. */
6779 if (TARGET_XCOFF)
6780 for (i = FIRST_ALTIVEC_REGNO + 20; i < FIRST_ALTIVEC_REGNO + 32; ++i)
6781 fixed_regs[i] = call_used_regs[i] = call_really_used_regs[i] = 1;
6782 }
6783 }
6784 \f
6785 /* Try to output insns to set TARGET equal to the constant C if it can
6786 be done in less than N insns. Do all computations in MODE.
6787 Returns the place where the output has been placed if it can be
6788 done and the insns have been emitted. If it would take more than N
6789 insns, zero is returned and no insns and emitted. */
6790
6791 rtx
6792 rs6000_emit_set_const (rtx dest, enum machine_mode mode,
6793 rtx source, int n ATTRIBUTE_UNUSED)
6794 {
6795 rtx result, insn, set;
6796 HOST_WIDE_INT c0, c1;
6797
6798 switch (mode)
6799 {
6800 case QImode:
6801 case HImode:
6802 if (dest == NULL)
6803 dest = gen_reg_rtx (mode);
6804 emit_insn (gen_rtx_SET (VOIDmode, dest, source));
6805 return dest;
6806
6807 case SImode:
6808 result = !can_create_pseudo_p () ? dest : gen_reg_rtx (SImode);
6809
6810 emit_insn (gen_rtx_SET (VOIDmode, copy_rtx (result),
6811 GEN_INT (INTVAL (source)
6812 & (~ (HOST_WIDE_INT) 0xffff))));
6813 emit_insn (gen_rtx_SET (VOIDmode, dest,
6814 gen_rtx_IOR (SImode, copy_rtx (result),
6815 GEN_INT (INTVAL (source) & 0xffff))));
6816 result = dest;
6817 break;
6818
6819 case DImode:
6820 switch (GET_CODE (source))
6821 {
6822 case CONST_INT:
6823 c0 = INTVAL (source);
6824 c1 = -(c0 < 0);
6825 break;
6826
6827 case CONST_DOUBLE:
6828 #if HOST_BITS_PER_WIDE_INT >= 64
6829 c0 = CONST_DOUBLE_LOW (source);
6830 c1 = -(c0 < 0);
6831 #else
6832 c0 = CONST_DOUBLE_LOW (source);
6833 c1 = CONST_DOUBLE_HIGH (source);
6834 #endif
6835 break;
6836
6837 default:
6838 gcc_unreachable ();
6839 }
6840
6841 result = rs6000_emit_set_long_const (dest, c0, c1);
6842 break;
6843
6844 default:
6845 gcc_unreachable ();
6846 }
6847
6848 insn = get_last_insn ();
6849 set = single_set (insn);
6850 if (! CONSTANT_P (SET_SRC (set)))
6851 set_unique_reg_note (insn, REG_EQUAL, source);
6852
6853 return result;
6854 }
6855
6856 /* Having failed to find a 3 insn sequence in rs6000_emit_set_const,
6857 fall back to a straight forward decomposition. We do this to avoid
6858 exponential run times encountered when looking for longer sequences
6859 with rs6000_emit_set_const. */
6860 static rtx
6861 rs6000_emit_set_long_const (rtx dest, HOST_WIDE_INT c1, HOST_WIDE_INT c2)
6862 {
6863 if (!TARGET_POWERPC64)
6864 {
6865 rtx operand1, operand2;
6866
6867 operand1 = operand_subword_force (dest, WORDS_BIG_ENDIAN == 0,
6868 DImode);
6869 operand2 = operand_subword_force (copy_rtx (dest), WORDS_BIG_ENDIAN != 0,
6870 DImode);
6871 emit_move_insn (operand1, GEN_INT (c1));
6872 emit_move_insn (operand2, GEN_INT (c2));
6873 }
6874 else
6875 {
6876 HOST_WIDE_INT ud1, ud2, ud3, ud4;
6877
6878 ud1 = c1 & 0xffff;
6879 ud2 = (c1 & 0xffff0000) >> 16;
6880 #if HOST_BITS_PER_WIDE_INT >= 64
6881 c2 = c1 >> 32;
6882 #endif
6883 ud3 = c2 & 0xffff;
6884 ud4 = (c2 & 0xffff0000) >> 16;
6885
6886 if ((ud4 == 0xffff && ud3 == 0xffff && ud2 == 0xffff && (ud1 & 0x8000))
6887 || (ud4 == 0 && ud3 == 0 && ud2 == 0 && ! (ud1 & 0x8000)))
6888 {
6889 if (ud1 & 0x8000)
6890 emit_move_insn (dest, GEN_INT (((ud1 ^ 0x8000) - 0x8000)));
6891 else
6892 emit_move_insn (dest, GEN_INT (ud1));
6893 }
6894
6895 else if ((ud4 == 0xffff && ud3 == 0xffff && (ud2 & 0x8000))
6896 || (ud4 == 0 && ud3 == 0 && ! (ud2 & 0x8000)))
6897 {
6898 if (ud2 & 0x8000)
6899 emit_move_insn (dest, GEN_INT (((ud2 << 16) ^ 0x80000000)
6900 - 0x80000000));
6901 else
6902 emit_move_insn (dest, GEN_INT (ud2 << 16));
6903 if (ud1 != 0)
6904 emit_move_insn (copy_rtx (dest),
6905 gen_rtx_IOR (DImode, copy_rtx (dest),
6906 GEN_INT (ud1)));
6907 }
6908 else if (ud3 == 0 && ud4 == 0)
6909 {
6910 gcc_assert (ud2 & 0x8000);
6911 emit_move_insn (dest, GEN_INT (((ud2 << 16) ^ 0x80000000)
6912 - 0x80000000));
6913 if (ud1 != 0)
6914 emit_move_insn (copy_rtx (dest),
6915 gen_rtx_IOR (DImode, copy_rtx (dest),
6916 GEN_INT (ud1)));
6917 emit_move_insn (copy_rtx (dest),
6918 gen_rtx_ZERO_EXTEND (DImode,
6919 gen_lowpart (SImode,
6920 copy_rtx (dest))));
6921 }
6922 else if ((ud4 == 0xffff && (ud3 & 0x8000))
6923 || (ud4 == 0 && ! (ud3 & 0x8000)))
6924 {
6925 if (ud3 & 0x8000)
6926 emit_move_insn (dest, GEN_INT (((ud3 << 16) ^ 0x80000000)
6927 - 0x80000000));
6928 else
6929 emit_move_insn (dest, GEN_INT (ud3 << 16));
6930
6931 if (ud2 != 0)
6932 emit_move_insn (copy_rtx (dest),
6933 gen_rtx_IOR (DImode, copy_rtx (dest),
6934 GEN_INT (ud2)));
6935 emit_move_insn (copy_rtx (dest),
6936 gen_rtx_ASHIFT (DImode, copy_rtx (dest),
6937 GEN_INT (16)));
6938 if (ud1 != 0)
6939 emit_move_insn (copy_rtx (dest),
6940 gen_rtx_IOR (DImode, copy_rtx (dest),
6941 GEN_INT (ud1)));
6942 }
6943 else
6944 {
6945 if (ud4 & 0x8000)
6946 emit_move_insn (dest, GEN_INT (((ud4 << 16) ^ 0x80000000)
6947 - 0x80000000));
6948 else
6949 emit_move_insn (dest, GEN_INT (ud4 << 16));
6950
6951 if (ud3 != 0)
6952 emit_move_insn (copy_rtx (dest),
6953 gen_rtx_IOR (DImode, copy_rtx (dest),
6954 GEN_INT (ud3)));
6955
6956 emit_move_insn (copy_rtx (dest),
6957 gen_rtx_ASHIFT (DImode, copy_rtx (dest),
6958 GEN_INT (32)));
6959 if (ud2 != 0)
6960 emit_move_insn (copy_rtx (dest),
6961 gen_rtx_IOR (DImode, copy_rtx (dest),
6962 GEN_INT (ud2 << 16)));
6963 if (ud1 != 0)
6964 emit_move_insn (copy_rtx (dest),
6965 gen_rtx_IOR (DImode, copy_rtx (dest), GEN_INT (ud1)));
6966 }
6967 }
6968 return dest;
6969 }
6970
6971 /* Helper for the following. Get rid of [r+r] memory refs
6972 in cases where it won't work (TImode, TFmode, TDmode). */
6973
6974 static void
6975 rs6000_eliminate_indexed_memrefs (rtx operands[2])
6976 {
6977 if (reload_in_progress)
6978 return;
6979
6980 if (GET_CODE (operands[0]) == MEM
6981 && GET_CODE (XEXP (operands[0], 0)) != REG
6982 && ! legitimate_constant_pool_address_p (XEXP (operands[0], 0), false))
6983 operands[0]
6984 = replace_equiv_address (operands[0],
6985 copy_addr_to_reg (XEXP (operands[0], 0)));
6986
6987 if (GET_CODE (operands[1]) == MEM
6988 && GET_CODE (XEXP (operands[1], 0)) != REG
6989 && ! legitimate_constant_pool_address_p (XEXP (operands[1], 0), false))
6990 operands[1]
6991 = replace_equiv_address (operands[1],
6992 copy_addr_to_reg (XEXP (operands[1], 0)));
6993 }
6994
6995 /* Emit a move from SOURCE to DEST in mode MODE. */
6996 void
6997 rs6000_emit_move (rtx dest, rtx source, enum machine_mode mode)
6998 {
6999 rtx operands[2];
7000 operands[0] = dest;
7001 operands[1] = source;
7002
7003 if (TARGET_DEBUG_ADDR)
7004 {
7005 fprintf (stderr,
7006 "\nrs6000_emit_move: mode = %s, reload_in_progress = %d, "
7007 "reload_completed = %d, can_create_pseudos = %d.\ndest:\n",
7008 GET_MODE_NAME (mode),
7009 reload_in_progress,
7010 reload_completed,
7011 can_create_pseudo_p ());
7012 debug_rtx (dest);
7013 fprintf (stderr, "source:\n");
7014 debug_rtx (source);
7015 }
7016
7017 /* Sanity checks. Check that we get CONST_DOUBLE only when we should. */
7018 if (GET_CODE (operands[1]) == CONST_DOUBLE
7019 && ! FLOAT_MODE_P (mode)
7020 && GET_MODE_BITSIZE (mode) <= HOST_BITS_PER_WIDE_INT)
7021 {
7022 /* FIXME. This should never happen. */
7023 /* Since it seems that it does, do the safe thing and convert
7024 to a CONST_INT. */
7025 operands[1] = gen_int_mode (CONST_DOUBLE_LOW (operands[1]), mode);
7026 }
7027 gcc_assert (GET_CODE (operands[1]) != CONST_DOUBLE
7028 || FLOAT_MODE_P (mode)
7029 || ((CONST_DOUBLE_HIGH (operands[1]) != 0
7030 || CONST_DOUBLE_LOW (operands[1]) < 0)
7031 && (CONST_DOUBLE_HIGH (operands[1]) != -1
7032 || CONST_DOUBLE_LOW (operands[1]) >= 0)));
7033
7034 /* Check if GCC is setting up a block move that will end up using FP
7035 registers as temporaries. We must make sure this is acceptable. */
7036 if (GET_CODE (operands[0]) == MEM
7037 && GET_CODE (operands[1]) == MEM
7038 && mode == DImode
7039 && (SLOW_UNALIGNED_ACCESS (DImode, MEM_ALIGN (operands[0]))
7040 || SLOW_UNALIGNED_ACCESS (DImode, MEM_ALIGN (operands[1])))
7041 && ! (SLOW_UNALIGNED_ACCESS (SImode, (MEM_ALIGN (operands[0]) > 32
7042 ? 32 : MEM_ALIGN (operands[0])))
7043 || SLOW_UNALIGNED_ACCESS (SImode, (MEM_ALIGN (operands[1]) > 32
7044 ? 32
7045 : MEM_ALIGN (operands[1]))))
7046 && ! MEM_VOLATILE_P (operands [0])
7047 && ! MEM_VOLATILE_P (operands [1]))
7048 {
7049 emit_move_insn (adjust_address (operands[0], SImode, 0),
7050 adjust_address (operands[1], SImode, 0));
7051 emit_move_insn (adjust_address (copy_rtx (operands[0]), SImode, 4),
7052 adjust_address (copy_rtx (operands[1]), SImode, 4));
7053 return;
7054 }
7055
7056 if (can_create_pseudo_p () && GET_CODE (operands[0]) == MEM
7057 && !gpc_reg_operand (operands[1], mode))
7058 operands[1] = force_reg (mode, operands[1]);
7059
7060 if (mode == SFmode && ! TARGET_POWERPC
7061 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
7062 && GET_CODE (operands[0]) == MEM)
7063 {
7064 int regnum;
7065
7066 if (reload_in_progress || reload_completed)
7067 regnum = true_regnum (operands[1]);
7068 else if (GET_CODE (operands[1]) == REG)
7069 regnum = REGNO (operands[1]);
7070 else
7071 regnum = -1;
7072
7073 /* If operands[1] is a register, on POWER it may have
7074 double-precision data in it, so truncate it to single
7075 precision. */
7076 if (FP_REGNO_P (regnum) || regnum >= FIRST_PSEUDO_REGISTER)
7077 {
7078 rtx newreg;
7079 newreg = (!can_create_pseudo_p () ? copy_rtx (operands[1])
7080 : gen_reg_rtx (mode));
7081 emit_insn (gen_aux_truncdfsf2 (newreg, operands[1]));
7082 operands[1] = newreg;
7083 }
7084 }
7085
7086 /* Recognize the case where operand[1] is a reference to thread-local
7087 data and load its address to a register. */
7088 if (rs6000_tls_referenced_p (operands[1]))
7089 {
7090 enum tls_model model;
7091 rtx tmp = operands[1];
7092 rtx addend = NULL;
7093
7094 if (GET_CODE (tmp) == CONST && GET_CODE (XEXP (tmp, 0)) == PLUS)
7095 {
7096 addend = XEXP (XEXP (tmp, 0), 1);
7097 tmp = XEXP (XEXP (tmp, 0), 0);
7098 }
7099
7100 gcc_assert (GET_CODE (tmp) == SYMBOL_REF);
7101 model = SYMBOL_REF_TLS_MODEL (tmp);
7102 gcc_assert (model != 0);
7103
7104 tmp = rs6000_legitimize_tls_address (tmp, model);
7105 if (addend)
7106 {
7107 tmp = gen_rtx_PLUS (mode, tmp, addend);
7108 tmp = force_operand (tmp, operands[0]);
7109 }
7110 operands[1] = tmp;
7111 }
7112
7113 /* Handle the case where reload calls us with an invalid address. */
7114 if (reload_in_progress && mode == Pmode
7115 && (! general_operand (operands[1], mode)
7116 || ! nonimmediate_operand (operands[0], mode)))
7117 goto emit_set;
7118
7119 /* 128-bit constant floating-point values on Darwin should really be
7120 loaded as two parts. */
7121 if (!TARGET_IEEEQUAD && TARGET_LONG_DOUBLE_128
7122 && mode == TFmode && GET_CODE (operands[1]) == CONST_DOUBLE)
7123 {
7124 /* DImode is used, not DFmode, because simplify_gen_subreg doesn't
7125 know how to get a DFmode SUBREG of a TFmode. */
7126 enum machine_mode imode = (TARGET_E500_DOUBLE ? DFmode : DImode);
7127 rs6000_emit_move (simplify_gen_subreg (imode, operands[0], mode, 0),
7128 simplify_gen_subreg (imode, operands[1], mode, 0),
7129 imode);
7130 rs6000_emit_move (simplify_gen_subreg (imode, operands[0], mode,
7131 GET_MODE_SIZE (imode)),
7132 simplify_gen_subreg (imode, operands[1], mode,
7133 GET_MODE_SIZE (imode)),
7134 imode);
7135 return;
7136 }
7137
7138 if (reload_in_progress && cfun->machine->sdmode_stack_slot != NULL_RTX)
7139 cfun->machine->sdmode_stack_slot =
7140 eliminate_regs (cfun->machine->sdmode_stack_slot, VOIDmode, NULL_RTX);
7141
7142 if (reload_in_progress
7143 && mode == SDmode
7144 && MEM_P (operands[0])
7145 && rtx_equal_p (operands[0], cfun->machine->sdmode_stack_slot)
7146 && REG_P (operands[1]))
7147 {
7148 if (FP_REGNO_P (REGNO (operands[1])))
7149 {
7150 rtx mem = adjust_address_nv (operands[0], DDmode, 0);
7151 mem = eliminate_regs (mem, VOIDmode, NULL_RTX);
7152 emit_insn (gen_movsd_store (mem, operands[1]));
7153 }
7154 else if (INT_REGNO_P (REGNO (operands[1])))
7155 {
7156 rtx mem = adjust_address_nv (operands[0], mode, 4);
7157 mem = eliminate_regs (mem, VOIDmode, NULL_RTX);
7158 emit_insn (gen_movsd_hardfloat (mem, operands[1]));
7159 }
7160 else
7161 gcc_unreachable();
7162 return;
7163 }
7164 if (reload_in_progress
7165 && mode == SDmode
7166 && REG_P (operands[0])
7167 && MEM_P (operands[1])
7168 && rtx_equal_p (operands[1], cfun->machine->sdmode_stack_slot))
7169 {
7170 if (FP_REGNO_P (REGNO (operands[0])))
7171 {
7172 rtx mem = adjust_address_nv (operands[1], DDmode, 0);
7173 mem = eliminate_regs (mem, VOIDmode, NULL_RTX);
7174 emit_insn (gen_movsd_load (operands[0], mem));
7175 }
7176 else if (INT_REGNO_P (REGNO (operands[0])))
7177 {
7178 rtx mem = adjust_address_nv (operands[1], mode, 4);
7179 mem = eliminate_regs (mem, VOIDmode, NULL_RTX);
7180 emit_insn (gen_movsd_hardfloat (operands[0], mem));
7181 }
7182 else
7183 gcc_unreachable();
7184 return;
7185 }
7186
7187 /* FIXME: In the long term, this switch statement should go away
7188 and be replaced by a sequence of tests based on things like
7189 mode == Pmode. */
7190 switch (mode)
7191 {
7192 case HImode:
7193 case QImode:
7194 if (CONSTANT_P (operands[1])
7195 && GET_CODE (operands[1]) != CONST_INT)
7196 operands[1] = force_const_mem (mode, operands[1]);
7197 break;
7198
7199 case TFmode:
7200 case TDmode:
7201 rs6000_eliminate_indexed_memrefs (operands);
7202 /* fall through */
7203
7204 case DFmode:
7205 case DDmode:
7206 case SFmode:
7207 case SDmode:
7208 if (CONSTANT_P (operands[1])
7209 && ! easy_fp_constant (operands[1], mode))
7210 operands[1] = force_const_mem (mode, operands[1]);
7211 break;
7212
7213 case V16QImode:
7214 case V8HImode:
7215 case V4SFmode:
7216 case V4SImode:
7217 case V4HImode:
7218 case V2SFmode:
7219 case V2SImode:
7220 case V1DImode:
7221 case V2DFmode:
7222 case V2DImode:
7223 if (CONSTANT_P (operands[1])
7224 && !easy_vector_constant (operands[1], mode))
7225 operands[1] = force_const_mem (mode, operands[1]);
7226 break;
7227
7228 case SImode:
7229 case DImode:
7230 /* Use default pattern for address of ELF small data */
7231 if (TARGET_ELF
7232 && mode == Pmode
7233 && DEFAULT_ABI == ABI_V4
7234 && (GET_CODE (operands[1]) == SYMBOL_REF
7235 || GET_CODE (operands[1]) == CONST)
7236 && small_data_operand (operands[1], mode))
7237 {
7238 emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
7239 return;
7240 }
7241
7242 if (DEFAULT_ABI == ABI_V4
7243 && mode == Pmode && mode == SImode
7244 && flag_pic == 1 && got_operand (operands[1], mode))
7245 {
7246 emit_insn (gen_movsi_got (operands[0], operands[1]));
7247 return;
7248 }
7249
7250 if ((TARGET_ELF || DEFAULT_ABI == ABI_DARWIN)
7251 && TARGET_NO_TOC
7252 && ! flag_pic
7253 && mode == Pmode
7254 && CONSTANT_P (operands[1])
7255 && GET_CODE (operands[1]) != HIGH
7256 && GET_CODE (operands[1]) != CONST_INT)
7257 {
7258 rtx target = (!can_create_pseudo_p ()
7259 ? operands[0]
7260 : gen_reg_rtx (mode));
7261
7262 /* If this is a function address on -mcall-aixdesc,
7263 convert it to the address of the descriptor. */
7264 if (DEFAULT_ABI == ABI_AIX
7265 && GET_CODE (operands[1]) == SYMBOL_REF
7266 && XSTR (operands[1], 0)[0] == '.')
7267 {
7268 const char *name = XSTR (operands[1], 0);
7269 rtx new_ref;
7270 while (*name == '.')
7271 name++;
7272 new_ref = gen_rtx_SYMBOL_REF (Pmode, name);
7273 CONSTANT_POOL_ADDRESS_P (new_ref)
7274 = CONSTANT_POOL_ADDRESS_P (operands[1]);
7275 SYMBOL_REF_FLAGS (new_ref) = SYMBOL_REF_FLAGS (operands[1]);
7276 SYMBOL_REF_USED (new_ref) = SYMBOL_REF_USED (operands[1]);
7277 SYMBOL_REF_DATA (new_ref) = SYMBOL_REF_DATA (operands[1]);
7278 operands[1] = new_ref;
7279 }
7280
7281 if (DEFAULT_ABI == ABI_DARWIN)
7282 {
7283 #if TARGET_MACHO
7284 if (MACHO_DYNAMIC_NO_PIC_P)
7285 {
7286 /* Take care of any required data indirection. */
7287 operands[1] = rs6000_machopic_legitimize_pic_address (
7288 operands[1], mode, operands[0]);
7289 if (operands[0] != operands[1])
7290 emit_insn (gen_rtx_SET (VOIDmode,
7291 operands[0], operands[1]));
7292 return;
7293 }
7294 #endif
7295 emit_insn (gen_macho_high (target, operands[1]));
7296 emit_insn (gen_macho_low (operands[0], target, operands[1]));
7297 return;
7298 }
7299
7300 emit_insn (gen_elf_high (target, operands[1]));
7301 emit_insn (gen_elf_low (operands[0], target, operands[1]));
7302 return;
7303 }
7304
7305 /* If this is a SYMBOL_REF that refers to a constant pool entry,
7306 and we have put it in the TOC, we just need to make a TOC-relative
7307 reference to it. */
7308 if (TARGET_TOC
7309 && GET_CODE (operands[1]) == SYMBOL_REF
7310 && constant_pool_expr_p (operands[1])
7311 && ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (get_pool_constant (operands[1]),
7312 get_pool_mode (operands[1])))
7313 {
7314 rtx reg = NULL_RTX;
7315 if (TARGET_CMODEL != CMODEL_SMALL)
7316 {
7317 if (can_create_pseudo_p ())
7318 reg = gen_reg_rtx (Pmode);
7319 else
7320 reg = operands[0];
7321 }
7322 operands[1] = create_TOC_reference (operands[1], reg);
7323 }
7324 else if (mode == Pmode
7325 && CONSTANT_P (operands[1])
7326 && ((GET_CODE (operands[1]) != CONST_INT
7327 && ! easy_fp_constant (operands[1], mode))
7328 || (GET_CODE (operands[1]) == CONST_INT
7329 && (num_insns_constant (operands[1], mode)
7330 > (TARGET_CMODEL != CMODEL_SMALL ? 3 : 2)))
7331 || (GET_CODE (operands[0]) == REG
7332 && FP_REGNO_P (REGNO (operands[0]))))
7333 && GET_CODE (operands[1]) != HIGH
7334 && ! legitimate_constant_pool_address_p (operands[1], false)
7335 && ! toc_relative_expr_p (operands[1])
7336 && (TARGET_CMODEL == CMODEL_SMALL
7337 || can_create_pseudo_p ()
7338 || (REG_P (operands[0])
7339 && INT_REG_OK_FOR_BASE_P (operands[0], true))))
7340 {
7341
7342 #if TARGET_MACHO
7343 /* Darwin uses a special PIC legitimizer. */
7344 if (DEFAULT_ABI == ABI_DARWIN && MACHOPIC_INDIRECT)
7345 {
7346 operands[1] =
7347 rs6000_machopic_legitimize_pic_address (operands[1], mode,
7348 operands[0]);
7349 if (operands[0] != operands[1])
7350 emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
7351 return;
7352 }
7353 #endif
7354
7355 /* If we are to limit the number of things we put in the TOC and
7356 this is a symbol plus a constant we can add in one insn,
7357 just put the symbol in the TOC and add the constant. Don't do
7358 this if reload is in progress. */
7359 if (GET_CODE (operands[1]) == CONST
7360 && TARGET_NO_SUM_IN_TOC && ! reload_in_progress
7361 && GET_CODE (XEXP (operands[1], 0)) == PLUS
7362 && add_operand (XEXP (XEXP (operands[1], 0), 1), mode)
7363 && (GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == LABEL_REF
7364 || GET_CODE (XEXP (XEXP (operands[1], 0), 0)) == SYMBOL_REF)
7365 && ! side_effects_p (operands[0]))
7366 {
7367 rtx sym =
7368 force_const_mem (mode, XEXP (XEXP (operands[1], 0), 0));
7369 rtx other = XEXP (XEXP (operands[1], 0), 1);
7370
7371 sym = force_reg (mode, sym);
7372 emit_insn (gen_add3_insn (operands[0], sym, other));
7373 return;
7374 }
7375
7376 operands[1] = force_const_mem (mode, operands[1]);
7377
7378 if (TARGET_TOC
7379 && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF
7380 && constant_pool_expr_p (XEXP (operands[1], 0))
7381 && ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (
7382 get_pool_constant (XEXP (operands[1], 0)),
7383 get_pool_mode (XEXP (operands[1], 0))))
7384 {
7385 rtx tocref;
7386 rtx reg = NULL_RTX;
7387 if (TARGET_CMODEL != CMODEL_SMALL)
7388 {
7389 if (can_create_pseudo_p ())
7390 reg = gen_reg_rtx (Pmode);
7391 else
7392 reg = operands[0];
7393 }
7394 tocref = create_TOC_reference (XEXP (operands[1], 0), reg);
7395 operands[1] = gen_const_mem (mode, tocref);
7396 set_mem_alias_set (operands[1], get_TOC_alias_set ());
7397 }
7398 }
7399 break;
7400
7401 case TImode:
7402 rs6000_eliminate_indexed_memrefs (operands);
7403
7404 if (TARGET_POWER)
7405 {
7406 emit_insn (gen_rtx_PARALLEL (VOIDmode,
7407 gen_rtvec (2,
7408 gen_rtx_SET (VOIDmode,
7409 operands[0], operands[1]),
7410 gen_rtx_CLOBBER (VOIDmode,
7411 gen_rtx_SCRATCH (SImode)))));
7412 return;
7413 }
7414 break;
7415
7416 default:
7417 fatal_insn ("bad move", gen_rtx_SET (VOIDmode, dest, source));
7418 }
7419
7420 /* Above, we may have called force_const_mem which may have returned
7421 an invalid address. If we can, fix this up; otherwise, reload will
7422 have to deal with it. */
7423 if (GET_CODE (operands[1]) == MEM && ! reload_in_progress)
7424 operands[1] = validize_mem (operands[1]);
7425
7426 emit_set:
7427 emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[1]));
7428 }
7429 \f
7430 /* Nonzero if we can use a floating-point register to pass this arg. */
7431 #define USE_FP_FOR_ARG_P(CUM,MODE,TYPE) \
7432 (SCALAR_FLOAT_MODE_P (MODE) \
7433 && (CUM)->fregno <= FP_ARG_MAX_REG \
7434 && TARGET_HARD_FLOAT && TARGET_FPRS)
7435
7436 /* Nonzero if we can use an AltiVec register to pass this arg. */
7437 #define USE_ALTIVEC_FOR_ARG_P(CUM,MODE,TYPE,NAMED) \
7438 ((ALTIVEC_VECTOR_MODE (MODE) || VSX_VECTOR_MODE (MODE)) \
7439 && (CUM)->vregno <= ALTIVEC_ARG_MAX_REG \
7440 && TARGET_ALTIVEC_ABI \
7441 && (NAMED))
7442
7443 /* Return a nonzero value to say to return the function value in
7444 memory, just as large structures are always returned. TYPE will be
7445 the data type of the value, and FNTYPE will be the type of the
7446 function doing the returning, or @code{NULL} for libcalls.
7447
7448 The AIX ABI for the RS/6000 specifies that all structures are
7449 returned in memory. The Darwin ABI does the same.
7450
7451 For the Darwin 64 Bit ABI, a function result can be returned in
7452 registers or in memory, depending on the size of the return data
7453 type. If it is returned in registers, the value occupies the same
7454 registers as it would if it were the first and only function
7455 argument. Otherwise, the function places its result in memory at
7456 the location pointed to by GPR3.
7457
7458 The SVR4 ABI specifies that structures <= 8 bytes are returned in r3/r4,
7459 but a draft put them in memory, and GCC used to implement the draft
7460 instead of the final standard. Therefore, aix_struct_return
7461 controls this instead of DEFAULT_ABI; V.4 targets needing backward
7462 compatibility can change DRAFT_V4_STRUCT_RET to override the
7463 default, and -m switches get the final word. See
7464 rs6000_override_options for more details.
7465
7466 The PPC32 SVR4 ABI uses IEEE double extended for long double, if 128-bit
7467 long double support is enabled. These values are returned in memory.
7468
7469 int_size_in_bytes returns -1 for variable size objects, which go in
7470 memory always. The cast to unsigned makes -1 > 8. */
7471
7472 static bool
7473 rs6000_return_in_memory (const_tree type, const_tree fntype ATTRIBUTE_UNUSED)
7474 {
7475 /* For the Darwin64 ABI, test if we can fit the return value in regs. */
7476 if (TARGET_MACHO
7477 && rs6000_darwin64_abi
7478 && TREE_CODE (type) == RECORD_TYPE
7479 && int_size_in_bytes (type) > 0)
7480 {
7481 CUMULATIVE_ARGS valcum;
7482 rtx valret;
7483
7484 valcum.words = 0;
7485 valcum.fregno = FP_ARG_MIN_REG;
7486 valcum.vregno = ALTIVEC_ARG_MIN_REG;
7487 /* Do a trial code generation as if this were going to be passed
7488 as an argument; if any part goes in memory, we return NULL. */
7489 valret = rs6000_darwin64_record_arg (&valcum, type, true, true);
7490 if (valret)
7491 return false;
7492 /* Otherwise fall through to more conventional ABI rules. */
7493 }
7494
7495 if (AGGREGATE_TYPE_P (type)
7496 && (aix_struct_return
7497 || (unsigned HOST_WIDE_INT) int_size_in_bytes (type) > 8))
7498 return true;
7499
7500 /* Allow -maltivec -mabi=no-altivec without warning. Altivec vector
7501 modes only exist for GCC vector types if -maltivec. */
7502 if (TARGET_32BIT && !TARGET_ALTIVEC_ABI
7503 && ALTIVEC_VECTOR_MODE (TYPE_MODE (type)))
7504 return false;
7505
7506 /* Return synthetic vectors in memory. */
7507 if (TREE_CODE (type) == VECTOR_TYPE
7508 && int_size_in_bytes (type) > (TARGET_ALTIVEC_ABI ? 16 : 8))
7509 {
7510 static bool warned_for_return_big_vectors = false;
7511 if (!warned_for_return_big_vectors)
7512 {
7513 warning (0, "GCC vector returned by reference: "
7514 "non-standard ABI extension with no compatibility guarantee");
7515 warned_for_return_big_vectors = true;
7516 }
7517 return true;
7518 }
7519
7520 if (DEFAULT_ABI == ABI_V4 && TARGET_IEEEQUAD && TYPE_MODE (type) == TFmode)
7521 return true;
7522
7523 return false;
7524 }
7525
7526 /* Initialize a variable CUM of type CUMULATIVE_ARGS
7527 for a call to a function whose data type is FNTYPE.
7528 For a library call, FNTYPE is 0.
7529
7530 For incoming args we set the number of arguments in the prototype large
7531 so we never return a PARALLEL. */
7532
7533 void
7534 init_cumulative_args (CUMULATIVE_ARGS *cum, tree fntype,
7535 rtx libname ATTRIBUTE_UNUSED, int incoming,
7536 int libcall, int n_named_args)
7537 {
7538 static CUMULATIVE_ARGS zero_cumulative;
7539
7540 *cum = zero_cumulative;
7541 cum->words = 0;
7542 cum->fregno = FP_ARG_MIN_REG;
7543 cum->vregno = ALTIVEC_ARG_MIN_REG;
7544 cum->prototype = (fntype && TYPE_ARG_TYPES (fntype));
7545 cum->call_cookie = ((DEFAULT_ABI == ABI_V4 && libcall)
7546 ? CALL_LIBCALL : CALL_NORMAL);
7547 cum->sysv_gregno = GP_ARG_MIN_REG;
7548 cum->stdarg = stdarg_p (fntype);
7549
7550 cum->nargs_prototype = 0;
7551 if (incoming || cum->prototype)
7552 cum->nargs_prototype = n_named_args;
7553
7554 /* Check for a longcall attribute. */
7555 if ((!fntype && rs6000_default_long_calls)
7556 || (fntype
7557 && lookup_attribute ("longcall", TYPE_ATTRIBUTES (fntype))
7558 && !lookup_attribute ("shortcall", TYPE_ATTRIBUTES (fntype))))
7559 cum->call_cookie |= CALL_LONG;
7560
7561 if (TARGET_DEBUG_ARG)
7562 {
7563 fprintf (stderr, "\ninit_cumulative_args:");
7564 if (fntype)
7565 {
7566 tree ret_type = TREE_TYPE (fntype);
7567 fprintf (stderr, " ret code = %s,",
7568 tree_code_name[ (int)TREE_CODE (ret_type) ]);
7569 }
7570
7571 if (cum->call_cookie & CALL_LONG)
7572 fprintf (stderr, " longcall,");
7573
7574 fprintf (stderr, " proto = %d, nargs = %d\n",
7575 cum->prototype, cum->nargs_prototype);
7576 }
7577
7578 if (fntype
7579 && !TARGET_ALTIVEC
7580 && TARGET_ALTIVEC_ABI
7581 && ALTIVEC_VECTOR_MODE (TYPE_MODE (TREE_TYPE (fntype))))
7582 {
7583 error ("cannot return value in vector register because"
7584 " altivec instructions are disabled, use -maltivec"
7585 " to enable them");
7586 }
7587 }
7588 \f
7589 /* Return true if TYPE must be passed on the stack and not in registers. */
7590
7591 static bool
7592 rs6000_must_pass_in_stack (enum machine_mode mode, const_tree type)
7593 {
7594 if (DEFAULT_ABI == ABI_AIX || TARGET_64BIT)
7595 return must_pass_in_stack_var_size (mode, type);
7596 else
7597 return must_pass_in_stack_var_size_or_pad (mode, type);
7598 }
7599
7600 /* If defined, a C expression which determines whether, and in which
7601 direction, to pad out an argument with extra space. The value
7602 should be of type `enum direction': either `upward' to pad above
7603 the argument, `downward' to pad below, or `none' to inhibit
7604 padding.
7605
7606 For the AIX ABI structs are always stored left shifted in their
7607 argument slot. */
7608
7609 enum direction
7610 function_arg_padding (enum machine_mode mode, const_tree type)
7611 {
7612 #ifndef AGGREGATE_PADDING_FIXED
7613 #define AGGREGATE_PADDING_FIXED 0
7614 #endif
7615 #ifndef AGGREGATES_PAD_UPWARD_ALWAYS
7616 #define AGGREGATES_PAD_UPWARD_ALWAYS 0
7617 #endif
7618
7619 if (!AGGREGATE_PADDING_FIXED)
7620 {
7621 /* GCC used to pass structures of the same size as integer types as
7622 if they were in fact integers, ignoring FUNCTION_ARG_PADDING.
7623 i.e. Structures of size 1 or 2 (or 4 when TARGET_64BIT) were
7624 passed padded downward, except that -mstrict-align further
7625 muddied the water in that multi-component structures of 2 and 4
7626 bytes in size were passed padded upward.
7627
7628 The following arranges for best compatibility with previous
7629 versions of gcc, but removes the -mstrict-align dependency. */
7630 if (BYTES_BIG_ENDIAN)
7631 {
7632 HOST_WIDE_INT size = 0;
7633
7634 if (mode == BLKmode)
7635 {
7636 if (type && TREE_CODE (TYPE_SIZE (type)) == INTEGER_CST)
7637 size = int_size_in_bytes (type);
7638 }
7639 else
7640 size = GET_MODE_SIZE (mode);
7641
7642 if (size == 1 || size == 2 || size == 4)
7643 return downward;
7644 }
7645 return upward;
7646 }
7647
7648 if (AGGREGATES_PAD_UPWARD_ALWAYS)
7649 {
7650 if (type != 0 && AGGREGATE_TYPE_P (type))
7651 return upward;
7652 }
7653
7654 /* Fall back to the default. */
7655 return DEFAULT_FUNCTION_ARG_PADDING (mode, type);
7656 }
7657
7658 /* If defined, a C expression that gives the alignment boundary, in bits,
7659 of an argument with the specified mode and type. If it is not defined,
7660 PARM_BOUNDARY is used for all arguments.
7661
7662 V.4 wants long longs and doubles to be double word aligned. Just
7663 testing the mode size is a boneheaded way to do this as it means
7664 that other types such as complex int are also double word aligned.
7665 However, we're stuck with this because changing the ABI might break
7666 existing library interfaces.
7667
7668 Doubleword align SPE vectors.
7669 Quadword align Altivec vectors.
7670 Quadword align large synthetic vector types. */
7671
7672 int
7673 function_arg_boundary (enum machine_mode mode, const_tree type)
7674 {
7675 if (DEFAULT_ABI == ABI_V4
7676 && (GET_MODE_SIZE (mode) == 8
7677 || (TARGET_HARD_FLOAT
7678 && TARGET_FPRS
7679 && (mode == TFmode || mode == TDmode))))
7680 return 64;
7681 else if (SPE_VECTOR_MODE (mode)
7682 || (type && TREE_CODE (type) == VECTOR_TYPE
7683 && int_size_in_bytes (type) >= 8
7684 && int_size_in_bytes (type) < 16))
7685 return 64;
7686 else if ((ALTIVEC_VECTOR_MODE (mode) || VSX_VECTOR_MODE (mode))
7687 || (type && TREE_CODE (type) == VECTOR_TYPE
7688 && int_size_in_bytes (type) >= 16))
7689 return 128;
7690 else if (TARGET_MACHO
7691 && rs6000_darwin64_abi
7692 && mode == BLKmode
7693 && type && TYPE_ALIGN (type) > 64)
7694 return 128;
7695 else
7696 return PARM_BOUNDARY;
7697 }
7698
7699 /* For a function parm of MODE and TYPE, return the starting word in
7700 the parameter area. NWORDS of the parameter area are already used. */
7701
7702 static unsigned int
7703 rs6000_parm_start (enum machine_mode mode, const_tree type,
7704 unsigned int nwords)
7705 {
7706 unsigned int align;
7707 unsigned int parm_offset;
7708
7709 align = function_arg_boundary (mode, type) / PARM_BOUNDARY - 1;
7710 parm_offset = DEFAULT_ABI == ABI_V4 ? 2 : 6;
7711 return nwords + (-(parm_offset + nwords) & align);
7712 }
7713
7714 /* Compute the size (in words) of a function argument. */
7715
7716 static unsigned long
7717 rs6000_arg_size (enum machine_mode mode, const_tree type)
7718 {
7719 unsigned long size;
7720
7721 if (mode != BLKmode)
7722 size = GET_MODE_SIZE (mode);
7723 else
7724 size = int_size_in_bytes (type);
7725
7726 if (TARGET_32BIT)
7727 return (size + 3) >> 2;
7728 else
7729 return (size + 7) >> 3;
7730 }
7731 \f
7732 /* Use this to flush pending int fields. */
7733
7734 static void
7735 rs6000_darwin64_record_arg_advance_flush (CUMULATIVE_ARGS *cum,
7736 HOST_WIDE_INT bitpos, int final)
7737 {
7738 unsigned int startbit, endbit;
7739 int intregs, intoffset;
7740 enum machine_mode mode;
7741
7742 /* Handle the situations where a float is taking up the first half
7743 of the GPR, and the other half is empty (typically due to
7744 alignment restrictions). We can detect this by a 8-byte-aligned
7745 int field, or by seeing that this is the final flush for this
7746 argument. Count the word and continue on. */
7747 if (cum->floats_in_gpr == 1
7748 && (cum->intoffset % 64 == 0
7749 || (cum->intoffset == -1 && final)))
7750 {
7751 cum->words++;
7752 cum->floats_in_gpr = 0;
7753 }
7754
7755 if (cum->intoffset == -1)
7756 return;
7757
7758 intoffset = cum->intoffset;
7759 cum->intoffset = -1;
7760 cum->floats_in_gpr = 0;
7761
7762 if (intoffset % BITS_PER_WORD != 0)
7763 {
7764 mode = mode_for_size (BITS_PER_WORD - intoffset % BITS_PER_WORD,
7765 MODE_INT, 0);
7766 if (mode == BLKmode)
7767 {
7768 /* We couldn't find an appropriate mode, which happens,
7769 e.g., in packed structs when there are 3 bytes to load.
7770 Back intoffset back to the beginning of the word in this
7771 case. */
7772 intoffset = intoffset & -BITS_PER_WORD;
7773 }
7774 }
7775
7776 startbit = intoffset & -BITS_PER_WORD;
7777 endbit = (bitpos + BITS_PER_WORD - 1) & -BITS_PER_WORD;
7778 intregs = (endbit - startbit) / BITS_PER_WORD;
7779 cum->words += intregs;
7780 /* words should be unsigned. */
7781 if ((unsigned)cum->words < (endbit/BITS_PER_WORD))
7782 {
7783 int pad = (endbit/BITS_PER_WORD) - cum->words;
7784 cum->words += pad;
7785 }
7786 }
7787
7788 /* The darwin64 ABI calls for us to recurse down through structs,
7789 looking for elements passed in registers. Unfortunately, we have
7790 to track int register count here also because of misalignments
7791 in powerpc alignment mode. */
7792
7793 static void
7794 rs6000_darwin64_record_arg_advance_recurse (CUMULATIVE_ARGS *cum,
7795 const_tree type,
7796 HOST_WIDE_INT startbitpos)
7797 {
7798 tree f;
7799
7800 for (f = TYPE_FIELDS (type); f ; f = DECL_CHAIN (f))
7801 if (TREE_CODE (f) == FIELD_DECL)
7802 {
7803 HOST_WIDE_INT bitpos = startbitpos;
7804 tree ftype = TREE_TYPE (f);
7805 enum machine_mode mode;
7806 if (ftype == error_mark_node)
7807 continue;
7808 mode = TYPE_MODE (ftype);
7809
7810 if (DECL_SIZE (f) != 0
7811 && host_integerp (bit_position (f), 1))
7812 bitpos += int_bit_position (f);
7813
7814 /* ??? FIXME: else assume zero offset. */
7815
7816 if (TREE_CODE (ftype) == RECORD_TYPE)
7817 rs6000_darwin64_record_arg_advance_recurse (cum, ftype, bitpos);
7818 else if (USE_FP_FOR_ARG_P (cum, mode, ftype))
7819 {
7820 rs6000_darwin64_record_arg_advance_flush (cum, bitpos, 0);
7821 cum->fregno += (GET_MODE_SIZE (mode) + 7) >> 3;
7822 /* Single-precision floats present a special problem for
7823 us, because they are smaller than an 8-byte GPR, and so
7824 the structure-packing rules combined with the standard
7825 varargs behavior mean that we want to pack float/float
7826 and float/int combinations into a single register's
7827 space. This is complicated by the arg advance flushing,
7828 which works on arbitrarily large groups of int-type
7829 fields. */
7830 if (mode == SFmode)
7831 {
7832 if (cum->floats_in_gpr == 1)
7833 {
7834 /* Two floats in a word; count the word and reset
7835 the float count. */
7836 cum->words++;
7837 cum->floats_in_gpr = 0;
7838 }
7839 else if (bitpos % 64 == 0)
7840 {
7841 /* A float at the beginning of an 8-byte word;
7842 count it and put off adjusting cum->words until
7843 we see if a arg advance flush is going to do it
7844 for us. */
7845 cum->floats_in_gpr++;
7846 }
7847 else
7848 {
7849 /* The float is at the end of a word, preceded
7850 by integer fields, so the arg advance flush
7851 just above has already set cum->words and
7852 everything is taken care of. */
7853 }
7854 }
7855 else
7856 cum->words += (GET_MODE_SIZE (mode) + 7) >> 3;
7857 }
7858 else if (USE_ALTIVEC_FOR_ARG_P (cum, mode, type, 1))
7859 {
7860 rs6000_darwin64_record_arg_advance_flush (cum, bitpos, 0);
7861 cum->vregno++;
7862 cum->words += 2;
7863 }
7864 else if (cum->intoffset == -1)
7865 cum->intoffset = bitpos;
7866 }
7867 }
7868
7869 /* Check for an item that needs to be considered specially under the darwin 64
7870 bit ABI. These are record types where the mode is BLK or the structure is
7871 8 bytes in size. */
7872 static int
7873 rs6000_darwin64_struct_check_p (enum machine_mode mode, const_tree type)
7874 {
7875 return rs6000_darwin64_abi
7876 && ((mode == BLKmode
7877 && TREE_CODE (type) == RECORD_TYPE
7878 && int_size_in_bytes (type) > 0)
7879 || (type && TREE_CODE (type) == RECORD_TYPE
7880 && int_size_in_bytes (type) == 8)) ? 1 : 0;
7881 }
7882
7883 /* Update the data in CUM to advance over an argument
7884 of mode MODE and data type TYPE.
7885 (TYPE is null for libcalls where that information may not be available.)
7886
7887 Note that for args passed by reference, function_arg will be called
7888 with MODE and TYPE set to that of the pointer to the arg, not the arg
7889 itself. */
7890
7891 static void
7892 rs6000_function_arg_advance_1 (CUMULATIVE_ARGS *cum, enum machine_mode mode,
7893 const_tree type, bool named, int depth)
7894 {
7895
7896 /* Only tick off an argument if we're not recursing. */
7897 if (depth == 0)
7898 cum->nargs_prototype--;
7899
7900 if (TARGET_ALTIVEC_ABI
7901 && (ALTIVEC_VECTOR_MODE (mode)
7902 || VSX_VECTOR_MODE (mode)
7903 || (type && TREE_CODE (type) == VECTOR_TYPE
7904 && int_size_in_bytes (type) == 16)))
7905 {
7906 bool stack = false;
7907
7908 if (USE_ALTIVEC_FOR_ARG_P (cum, mode, type, named))
7909 {
7910 cum->vregno++;
7911 if (!TARGET_ALTIVEC)
7912 error ("cannot pass argument in vector register because"
7913 " altivec instructions are disabled, use -maltivec"
7914 " to enable them");
7915
7916 /* PowerPC64 Linux and AIX allocate GPRs for a vector argument
7917 even if it is going to be passed in a vector register.
7918 Darwin does the same for variable-argument functions. */
7919 if ((DEFAULT_ABI == ABI_AIX && TARGET_64BIT)
7920 || (cum->stdarg && DEFAULT_ABI != ABI_V4))
7921 stack = true;
7922 }
7923 else
7924 stack = true;
7925
7926 if (stack)
7927 {
7928 int align;
7929
7930 /* Vector parameters must be 16-byte aligned. This places
7931 them at 2 mod 4 in terms of words in 32-bit mode, since
7932 the parameter save area starts at offset 24 from the
7933 stack. In 64-bit mode, they just have to start on an
7934 even word, since the parameter save area is 16-byte
7935 aligned. Space for GPRs is reserved even if the argument
7936 will be passed in memory. */
7937 if (TARGET_32BIT)
7938 align = (2 - cum->words) & 3;
7939 else
7940 align = cum->words & 1;
7941 cum->words += align + rs6000_arg_size (mode, type);
7942
7943 if (TARGET_DEBUG_ARG)
7944 {
7945 fprintf (stderr, "function_adv: words = %2d, align=%d, ",
7946 cum->words, align);
7947 fprintf (stderr, "nargs = %4d, proto = %d, mode = %4s\n",
7948 cum->nargs_prototype, cum->prototype,
7949 GET_MODE_NAME (mode));
7950 }
7951 }
7952 }
7953 else if (TARGET_SPE_ABI && TARGET_SPE && SPE_VECTOR_MODE (mode)
7954 && !cum->stdarg
7955 && cum->sysv_gregno <= GP_ARG_MAX_REG)
7956 cum->sysv_gregno++;
7957
7958 else if (TARGET_MACHO && rs6000_darwin64_struct_check_p (mode, type))
7959 {
7960 int size = int_size_in_bytes (type);
7961 /* Variable sized types have size == -1 and are
7962 treated as if consisting entirely of ints.
7963 Pad to 16 byte boundary if needed. */
7964 if (TYPE_ALIGN (type) >= 2 * BITS_PER_WORD
7965 && (cum->words % 2) != 0)
7966 cum->words++;
7967 /* For varargs, we can just go up by the size of the struct. */
7968 if (!named)
7969 cum->words += (size + 7) / 8;
7970 else
7971 {
7972 /* It is tempting to say int register count just goes up by
7973 sizeof(type)/8, but this is wrong in a case such as
7974 { int; double; int; } [powerpc alignment]. We have to
7975 grovel through the fields for these too. */
7976 cum->intoffset = 0;
7977 cum->floats_in_gpr = 0;
7978 rs6000_darwin64_record_arg_advance_recurse (cum, type, 0);
7979 rs6000_darwin64_record_arg_advance_flush (cum,
7980 size * BITS_PER_UNIT, 1);
7981 }
7982 if (TARGET_DEBUG_ARG)
7983 {
7984 fprintf (stderr, "function_adv: words = %2d, align=%d, size=%d",
7985 cum->words, TYPE_ALIGN (type), size);
7986 fprintf (stderr,
7987 "nargs = %4d, proto = %d, mode = %4s (darwin64 abi)\n",
7988 cum->nargs_prototype, cum->prototype,
7989 GET_MODE_NAME (mode));
7990 }
7991 }
7992 else if (DEFAULT_ABI == ABI_V4)
7993 {
7994 if (TARGET_HARD_FLOAT && TARGET_FPRS
7995 && ((TARGET_SINGLE_FLOAT && mode == SFmode)
7996 || (TARGET_DOUBLE_FLOAT && mode == DFmode)
7997 || (mode == TFmode && !TARGET_IEEEQUAD)
7998 || mode == SDmode || mode == DDmode || mode == TDmode))
7999 {
8000 /* _Decimal128 must use an even/odd register pair. This assumes
8001 that the register number is odd when fregno is odd. */
8002 if (mode == TDmode && (cum->fregno % 2) == 1)
8003 cum->fregno++;
8004
8005 if (cum->fregno + (mode == TFmode || mode == TDmode ? 1 : 0)
8006 <= FP_ARG_V4_MAX_REG)
8007 cum->fregno += (GET_MODE_SIZE (mode) + 7) >> 3;
8008 else
8009 {
8010 cum->fregno = FP_ARG_V4_MAX_REG + 1;
8011 if (mode == DFmode || mode == TFmode
8012 || mode == DDmode || mode == TDmode)
8013 cum->words += cum->words & 1;
8014 cum->words += rs6000_arg_size (mode, type);
8015 }
8016 }
8017 else
8018 {
8019 int n_words = rs6000_arg_size (mode, type);
8020 int gregno = cum->sysv_gregno;
8021
8022 /* Long long and SPE vectors are put in (r3,r4), (r5,r6),
8023 (r7,r8) or (r9,r10). As does any other 2 word item such
8024 as complex int due to a historical mistake. */
8025 if (n_words == 2)
8026 gregno += (1 - gregno) & 1;
8027
8028 /* Multi-reg args are not split between registers and stack. */
8029 if (gregno + n_words - 1 > GP_ARG_MAX_REG)
8030 {
8031 /* Long long and SPE vectors are aligned on the stack.
8032 So are other 2 word items such as complex int due to
8033 a historical mistake. */
8034 if (n_words == 2)
8035 cum->words += cum->words & 1;
8036 cum->words += n_words;
8037 }
8038
8039 /* Note: continuing to accumulate gregno past when we've started
8040 spilling to the stack indicates the fact that we've started
8041 spilling to the stack to expand_builtin_saveregs. */
8042 cum->sysv_gregno = gregno + n_words;
8043 }
8044
8045 if (TARGET_DEBUG_ARG)
8046 {
8047 fprintf (stderr, "function_adv: words = %2d, fregno = %2d, ",
8048 cum->words, cum->fregno);
8049 fprintf (stderr, "gregno = %2d, nargs = %4d, proto = %d, ",
8050 cum->sysv_gregno, cum->nargs_prototype, cum->prototype);
8051 fprintf (stderr, "mode = %4s, named = %d\n",
8052 GET_MODE_NAME (mode), named);
8053 }
8054 }
8055 else
8056 {
8057 int n_words = rs6000_arg_size (mode, type);
8058 int start_words = cum->words;
8059 int align_words = rs6000_parm_start (mode, type, start_words);
8060
8061 cum->words = align_words + n_words;
8062
8063 if (SCALAR_FLOAT_MODE_P (mode)
8064 && TARGET_HARD_FLOAT && TARGET_FPRS)
8065 {
8066 /* _Decimal128 must be passed in an even/odd float register pair.
8067 This assumes that the register number is odd when fregno is
8068 odd. */
8069 if (mode == TDmode && (cum->fregno % 2) == 1)
8070 cum->fregno++;
8071 cum->fregno += (GET_MODE_SIZE (mode) + 7) >> 3;
8072 }
8073
8074 if (TARGET_DEBUG_ARG)
8075 {
8076 fprintf (stderr, "function_adv: words = %2d, fregno = %2d, ",
8077 cum->words, cum->fregno);
8078 fprintf (stderr, "nargs = %4d, proto = %d, mode = %4s, ",
8079 cum->nargs_prototype, cum->prototype, GET_MODE_NAME (mode));
8080 fprintf (stderr, "named = %d, align = %d, depth = %d\n",
8081 named, align_words - start_words, depth);
8082 }
8083 }
8084 }
8085
8086 static void
8087 rs6000_function_arg_advance (CUMULATIVE_ARGS *cum, enum machine_mode mode,
8088 const_tree type, bool named)
8089 {
8090 rs6000_function_arg_advance_1 (cum, mode, type, named, 0);
8091 }
8092
8093 static rtx
8094 spe_build_register_parallel (enum machine_mode mode, int gregno)
8095 {
8096 rtx r1, r3, r5, r7;
8097
8098 switch (mode)
8099 {
8100 case DFmode:
8101 r1 = gen_rtx_REG (DImode, gregno);
8102 r1 = gen_rtx_EXPR_LIST (VOIDmode, r1, const0_rtx);
8103 return gen_rtx_PARALLEL (mode, gen_rtvec (1, r1));
8104
8105 case DCmode:
8106 case TFmode:
8107 r1 = gen_rtx_REG (DImode, gregno);
8108 r1 = gen_rtx_EXPR_LIST (VOIDmode, r1, const0_rtx);
8109 r3 = gen_rtx_REG (DImode, gregno + 2);
8110 r3 = gen_rtx_EXPR_LIST (VOIDmode, r3, GEN_INT (8));
8111 return gen_rtx_PARALLEL (mode, gen_rtvec (2, r1, r3));
8112
8113 case TCmode:
8114 r1 = gen_rtx_REG (DImode, gregno);
8115 r1 = gen_rtx_EXPR_LIST (VOIDmode, r1, const0_rtx);
8116 r3 = gen_rtx_REG (DImode, gregno + 2);
8117 r3 = gen_rtx_EXPR_LIST (VOIDmode, r3, GEN_INT (8));
8118 r5 = gen_rtx_REG (DImode, gregno + 4);
8119 r5 = gen_rtx_EXPR_LIST (VOIDmode, r5, GEN_INT (16));
8120 r7 = gen_rtx_REG (DImode, gregno + 6);
8121 r7 = gen_rtx_EXPR_LIST (VOIDmode, r7, GEN_INT (24));
8122 return gen_rtx_PARALLEL (mode, gen_rtvec (4, r1, r3, r5, r7));
8123
8124 default:
8125 gcc_unreachable ();
8126 }
8127 }
8128
8129 /* Determine where to put a SIMD argument on the SPE. */
8130 static rtx
8131 rs6000_spe_function_arg (const CUMULATIVE_ARGS *cum, enum machine_mode mode,
8132 const_tree type)
8133 {
8134 int gregno = cum->sysv_gregno;
8135
8136 /* On E500 v2, double arithmetic is done on the full 64-bit GPR, but
8137 are passed and returned in a pair of GPRs for ABI compatibility. */
8138 if (TARGET_E500_DOUBLE && (mode == DFmode || mode == TFmode
8139 || mode == DCmode || mode == TCmode))
8140 {
8141 int n_words = rs6000_arg_size (mode, type);
8142
8143 /* Doubles go in an odd/even register pair (r5/r6, etc). */
8144 if (mode == DFmode)
8145 gregno += (1 - gregno) & 1;
8146
8147 /* Multi-reg args are not split between registers and stack. */
8148 if (gregno + n_words - 1 > GP_ARG_MAX_REG)
8149 return NULL_RTX;
8150
8151 return spe_build_register_parallel (mode, gregno);
8152 }
8153 if (cum->stdarg)
8154 {
8155 int n_words = rs6000_arg_size (mode, type);
8156
8157 /* SPE vectors are put in odd registers. */
8158 if (n_words == 2 && (gregno & 1) == 0)
8159 gregno += 1;
8160
8161 if (gregno + n_words - 1 <= GP_ARG_MAX_REG)
8162 {
8163 rtx r1, r2;
8164 enum machine_mode m = SImode;
8165
8166 r1 = gen_rtx_REG (m, gregno);
8167 r1 = gen_rtx_EXPR_LIST (m, r1, const0_rtx);
8168 r2 = gen_rtx_REG (m, gregno + 1);
8169 r2 = gen_rtx_EXPR_LIST (m, r2, GEN_INT (4));
8170 return gen_rtx_PARALLEL (mode, gen_rtvec (2, r1, r2));
8171 }
8172 else
8173 return NULL_RTX;
8174 }
8175 else
8176 {
8177 if (gregno <= GP_ARG_MAX_REG)
8178 return gen_rtx_REG (mode, gregno);
8179 else
8180 return NULL_RTX;
8181 }
8182 }
8183
8184 /* A subroutine of rs6000_darwin64_record_arg. Assign the bits of the
8185 structure between cum->intoffset and bitpos to integer registers. */
8186
8187 static void
8188 rs6000_darwin64_record_arg_flush (CUMULATIVE_ARGS *cum,
8189 HOST_WIDE_INT bitpos, rtx rvec[], int *k)
8190 {
8191 enum machine_mode mode;
8192 unsigned int regno;
8193 unsigned int startbit, endbit;
8194 int this_regno, intregs, intoffset;
8195 rtx reg;
8196
8197 if (cum->intoffset == -1)
8198 return;
8199
8200 intoffset = cum->intoffset;
8201 cum->intoffset = -1;
8202
8203 /* If this is the trailing part of a word, try to only load that
8204 much into the register. Otherwise load the whole register. Note
8205 that in the latter case we may pick up unwanted bits. It's not a
8206 problem at the moment but may wish to revisit. */
8207
8208 if (intoffset % BITS_PER_WORD != 0)
8209 {
8210 mode = mode_for_size (BITS_PER_WORD - intoffset % BITS_PER_WORD,
8211 MODE_INT, 0);
8212 if (mode == BLKmode)
8213 {
8214 /* We couldn't find an appropriate mode, which happens,
8215 e.g., in packed structs when there are 3 bytes to load.
8216 Back intoffset back to the beginning of the word in this
8217 case. */
8218 intoffset = intoffset & -BITS_PER_WORD;
8219 mode = word_mode;
8220 }
8221 }
8222 else
8223 mode = word_mode;
8224
8225 startbit = intoffset & -BITS_PER_WORD;
8226 endbit = (bitpos + BITS_PER_WORD - 1) & -BITS_PER_WORD;
8227 intregs = (endbit - startbit) / BITS_PER_WORD;
8228 this_regno = cum->words + intoffset / BITS_PER_WORD;
8229
8230 if (intregs > 0 && intregs > GP_ARG_NUM_REG - this_regno)
8231 cum->use_stack = 1;
8232
8233 intregs = MIN (intregs, GP_ARG_NUM_REG - this_regno);
8234 if (intregs <= 0)
8235 return;
8236
8237 intoffset /= BITS_PER_UNIT;
8238 do
8239 {
8240 regno = GP_ARG_MIN_REG + this_regno;
8241 reg = gen_rtx_REG (mode, regno);
8242 rvec[(*k)++] =
8243 gen_rtx_EXPR_LIST (VOIDmode, reg, GEN_INT (intoffset));
8244
8245 this_regno += 1;
8246 intoffset = (intoffset | (UNITS_PER_WORD-1)) + 1;
8247 mode = word_mode;
8248 intregs -= 1;
8249 }
8250 while (intregs > 0);
8251 }
8252
8253 /* Recursive workhorse for the following. */
8254
8255 static void
8256 rs6000_darwin64_record_arg_recurse (CUMULATIVE_ARGS *cum, const_tree type,
8257 HOST_WIDE_INT startbitpos, rtx rvec[],
8258 int *k)
8259 {
8260 tree f;
8261
8262 for (f = TYPE_FIELDS (type); f ; f = DECL_CHAIN (f))
8263 if (TREE_CODE (f) == FIELD_DECL)
8264 {
8265 HOST_WIDE_INT bitpos = startbitpos;
8266 tree ftype = TREE_TYPE (f);
8267 enum machine_mode mode;
8268 if (ftype == error_mark_node)
8269 continue;
8270 mode = TYPE_MODE (ftype);
8271
8272 if (DECL_SIZE (f) != 0
8273 && host_integerp (bit_position (f), 1))
8274 bitpos += int_bit_position (f);
8275
8276 /* ??? FIXME: else assume zero offset. */
8277
8278 if (TREE_CODE (ftype) == RECORD_TYPE)
8279 rs6000_darwin64_record_arg_recurse (cum, ftype, bitpos, rvec, k);
8280 else if (cum->named && USE_FP_FOR_ARG_P (cum, mode, ftype))
8281 {
8282 #if 0
8283 switch (mode)
8284 {
8285 case SCmode: mode = SFmode; break;
8286 case DCmode: mode = DFmode; break;
8287 case TCmode: mode = TFmode; break;
8288 default: break;
8289 }
8290 #endif
8291 rs6000_darwin64_record_arg_flush (cum, bitpos, rvec, k);
8292 rvec[(*k)++]
8293 = gen_rtx_EXPR_LIST (VOIDmode,
8294 gen_rtx_REG (mode, cum->fregno++),
8295 GEN_INT (bitpos / BITS_PER_UNIT));
8296 if (mode == TFmode || mode == TDmode)
8297 cum->fregno++;
8298 }
8299 else if (cum->named && USE_ALTIVEC_FOR_ARG_P (cum, mode, ftype, 1))
8300 {
8301 rs6000_darwin64_record_arg_flush (cum, bitpos, rvec, k);
8302 rvec[(*k)++]
8303 = gen_rtx_EXPR_LIST (VOIDmode,
8304 gen_rtx_REG (mode, cum->vregno++),
8305 GEN_INT (bitpos / BITS_PER_UNIT));
8306 }
8307 else if (cum->intoffset == -1)
8308 cum->intoffset = bitpos;
8309 }
8310 }
8311
8312 /* For the darwin64 ABI, we want to construct a PARALLEL consisting of
8313 the register(s) to be used for each field and subfield of a struct
8314 being passed by value, along with the offset of where the
8315 register's value may be found in the block. FP fields go in FP
8316 register, vector fields go in vector registers, and everything
8317 else goes in int registers, packed as in memory.
8318
8319 This code is also used for function return values. RETVAL indicates
8320 whether this is the case.
8321
8322 Much of this is taken from the SPARC V9 port, which has a similar
8323 calling convention. */
8324
8325 static rtx
8326 rs6000_darwin64_record_arg (CUMULATIVE_ARGS *orig_cum, const_tree type,
8327 bool named, bool retval)
8328 {
8329 rtx rvec[FIRST_PSEUDO_REGISTER];
8330 int k = 1, kbase = 1;
8331 HOST_WIDE_INT typesize = int_size_in_bytes (type);
8332 /* This is a copy; modifications are not visible to our caller. */
8333 CUMULATIVE_ARGS copy_cum = *orig_cum;
8334 CUMULATIVE_ARGS *cum = &copy_cum;
8335
8336 /* Pad to 16 byte boundary if needed. */
8337 if (!retval && TYPE_ALIGN (type) >= 2 * BITS_PER_WORD
8338 && (cum->words % 2) != 0)
8339 cum->words++;
8340
8341 cum->intoffset = 0;
8342 cum->use_stack = 0;
8343 cum->named = named;
8344
8345 /* Put entries into rvec[] for individual FP and vector fields, and
8346 for the chunks of memory that go in int regs. Note we start at
8347 element 1; 0 is reserved for an indication of using memory, and
8348 may or may not be filled in below. */
8349 rs6000_darwin64_record_arg_recurse (cum, type, 0, rvec, &k);
8350 rs6000_darwin64_record_arg_flush (cum, typesize * BITS_PER_UNIT, rvec, &k);
8351
8352 /* If any part of the struct went on the stack put all of it there.
8353 This hack is because the generic code for
8354 FUNCTION_ARG_PARTIAL_NREGS cannot handle cases where the register
8355 parts of the struct are not at the beginning. */
8356 if (cum->use_stack)
8357 {
8358 if (retval)
8359 return NULL_RTX; /* doesn't go in registers at all */
8360 kbase = 0;
8361 rvec[0] = gen_rtx_EXPR_LIST (VOIDmode, NULL_RTX, const0_rtx);
8362 }
8363 if (k > 1 || cum->use_stack)
8364 return gen_rtx_PARALLEL (BLKmode, gen_rtvec_v (k - kbase, &rvec[kbase]));
8365 else
8366 return NULL_RTX;
8367 }
8368
8369 /* Determine where to place an argument in 64-bit mode with 32-bit ABI. */
8370
8371 static rtx
8372 rs6000_mixed_function_arg (enum machine_mode mode, const_tree type,
8373 int align_words)
8374 {
8375 int n_units;
8376 int i, k;
8377 rtx rvec[GP_ARG_NUM_REG + 1];
8378
8379 if (align_words >= GP_ARG_NUM_REG)
8380 return NULL_RTX;
8381
8382 n_units = rs6000_arg_size (mode, type);
8383
8384 /* Optimize the simple case where the arg fits in one gpr, except in
8385 the case of BLKmode due to assign_parms assuming that registers are
8386 BITS_PER_WORD wide. */
8387 if (n_units == 0
8388 || (n_units == 1 && mode != BLKmode))
8389 return gen_rtx_REG (mode, GP_ARG_MIN_REG + align_words);
8390
8391 k = 0;
8392 if (align_words + n_units > GP_ARG_NUM_REG)
8393 /* Not all of the arg fits in gprs. Say that it goes in memory too,
8394 using a magic NULL_RTX component.
8395 This is not strictly correct. Only some of the arg belongs in
8396 memory, not all of it. However, the normal scheme using
8397 function_arg_partial_nregs can result in unusual subregs, eg.
8398 (subreg:SI (reg:DF) 4), which are not handled well. The code to
8399 store the whole arg to memory is often more efficient than code
8400 to store pieces, and we know that space is available in the right
8401 place for the whole arg. */
8402 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, NULL_RTX, const0_rtx);
8403
8404 i = 0;
8405 do
8406 {
8407 rtx r = gen_rtx_REG (SImode, GP_ARG_MIN_REG + align_words);
8408 rtx off = GEN_INT (i++ * 4);
8409 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, r, off);
8410 }
8411 while (++align_words < GP_ARG_NUM_REG && --n_units != 0);
8412
8413 return gen_rtx_PARALLEL (mode, gen_rtvec_v (k, rvec));
8414 }
8415
8416 /* Determine where to put an argument to a function.
8417 Value is zero to push the argument on the stack,
8418 or a hard register in which to store the argument.
8419
8420 MODE is the argument's machine mode.
8421 TYPE is the data type of the argument (as a tree).
8422 This is null for libcalls where that information may
8423 not be available.
8424 CUM is a variable of type CUMULATIVE_ARGS which gives info about
8425 the preceding args and about the function being called. It is
8426 not modified in this routine.
8427 NAMED is nonzero if this argument is a named parameter
8428 (otherwise it is an extra parameter matching an ellipsis).
8429
8430 On RS/6000 the first eight words of non-FP are normally in registers
8431 and the rest are pushed. Under AIX, the first 13 FP args are in registers.
8432 Under V.4, the first 8 FP args are in registers.
8433
8434 If this is floating-point and no prototype is specified, we use
8435 both an FP and integer register (or possibly FP reg and stack). Library
8436 functions (when CALL_LIBCALL is set) always have the proper types for args,
8437 so we can pass the FP value just in one register. emit_library_function
8438 doesn't support PARALLEL anyway.
8439
8440 Note that for args passed by reference, function_arg will be called
8441 with MODE and TYPE set to that of the pointer to the arg, not the arg
8442 itself. */
8443
8444 static rtx
8445 rs6000_function_arg (CUMULATIVE_ARGS *cum, enum machine_mode mode,
8446 const_tree type, bool named)
8447 {
8448 enum rs6000_abi abi = DEFAULT_ABI;
8449
8450 /* Return a marker to indicate whether CR1 needs to set or clear the
8451 bit that V.4 uses to say fp args were passed in registers.
8452 Assume that we don't need the marker for software floating point,
8453 or compiler generated library calls. */
8454 if (mode == VOIDmode)
8455 {
8456 if (abi == ABI_V4
8457 && (cum->call_cookie & CALL_LIBCALL) == 0
8458 && (cum->stdarg
8459 || (cum->nargs_prototype < 0
8460 && (cum->prototype || TARGET_NO_PROTOTYPE))))
8461 {
8462 /* For the SPE, we need to crxor CR6 always. */
8463 if (TARGET_SPE_ABI)
8464 return GEN_INT (cum->call_cookie | CALL_V4_SET_FP_ARGS);
8465 else if (TARGET_HARD_FLOAT && TARGET_FPRS)
8466 return GEN_INT (cum->call_cookie
8467 | ((cum->fregno == FP_ARG_MIN_REG)
8468 ? CALL_V4_SET_FP_ARGS
8469 : CALL_V4_CLEAR_FP_ARGS));
8470 }
8471
8472 return GEN_INT (cum->call_cookie);
8473 }
8474
8475 if (TARGET_MACHO && rs6000_darwin64_struct_check_p (mode, type))
8476 {
8477 rtx rslt = rs6000_darwin64_record_arg (cum, type, named, false);
8478 if (rslt != NULL_RTX)
8479 return rslt;
8480 /* Else fall through to usual handling. */
8481 }
8482
8483 if (USE_ALTIVEC_FOR_ARG_P (cum, mode, type, named))
8484 if (TARGET_64BIT && ! cum->prototype)
8485 {
8486 /* Vector parameters get passed in vector register
8487 and also in GPRs or memory, in absence of prototype. */
8488 int align_words;
8489 rtx slot;
8490 align_words = (cum->words + 1) & ~1;
8491
8492 if (align_words >= GP_ARG_NUM_REG)
8493 {
8494 slot = NULL_RTX;
8495 }
8496 else
8497 {
8498 slot = gen_rtx_REG (mode, GP_ARG_MIN_REG + align_words);
8499 }
8500 return gen_rtx_PARALLEL (mode,
8501 gen_rtvec (2,
8502 gen_rtx_EXPR_LIST (VOIDmode,
8503 slot, const0_rtx),
8504 gen_rtx_EXPR_LIST (VOIDmode,
8505 gen_rtx_REG (mode, cum->vregno),
8506 const0_rtx)));
8507 }
8508 else
8509 return gen_rtx_REG (mode, cum->vregno);
8510 else if (TARGET_ALTIVEC_ABI
8511 && (ALTIVEC_VECTOR_MODE (mode)
8512 || VSX_VECTOR_MODE (mode)
8513 || (type && TREE_CODE (type) == VECTOR_TYPE
8514 && int_size_in_bytes (type) == 16)))
8515 {
8516 if (named || abi == ABI_V4)
8517 return NULL_RTX;
8518 else
8519 {
8520 /* Vector parameters to varargs functions under AIX or Darwin
8521 get passed in memory and possibly also in GPRs. */
8522 int align, align_words, n_words;
8523 enum machine_mode part_mode;
8524
8525 /* Vector parameters must be 16-byte aligned. This places them at
8526 2 mod 4 in terms of words in 32-bit mode, since the parameter
8527 save area starts at offset 24 from the stack. In 64-bit mode,
8528 they just have to start on an even word, since the parameter
8529 save area is 16-byte aligned. */
8530 if (TARGET_32BIT)
8531 align = (2 - cum->words) & 3;
8532 else
8533 align = cum->words & 1;
8534 align_words = cum->words + align;
8535
8536 /* Out of registers? Memory, then. */
8537 if (align_words >= GP_ARG_NUM_REG)
8538 return NULL_RTX;
8539
8540 if (TARGET_32BIT && TARGET_POWERPC64)
8541 return rs6000_mixed_function_arg (mode, type, align_words);
8542
8543 /* The vector value goes in GPRs. Only the part of the
8544 value in GPRs is reported here. */
8545 part_mode = mode;
8546 n_words = rs6000_arg_size (mode, type);
8547 if (align_words + n_words > GP_ARG_NUM_REG)
8548 /* Fortunately, there are only two possibilities, the value
8549 is either wholly in GPRs or half in GPRs and half not. */
8550 part_mode = DImode;
8551
8552 return gen_rtx_REG (part_mode, GP_ARG_MIN_REG + align_words);
8553 }
8554 }
8555 else if (TARGET_SPE_ABI && TARGET_SPE
8556 && (SPE_VECTOR_MODE (mode)
8557 || (TARGET_E500_DOUBLE && (mode == DFmode
8558 || mode == DCmode
8559 || mode == TFmode
8560 || mode == TCmode))))
8561 return rs6000_spe_function_arg (cum, mode, type);
8562
8563 else if (abi == ABI_V4)
8564 {
8565 if (TARGET_HARD_FLOAT && TARGET_FPRS
8566 && ((TARGET_SINGLE_FLOAT && mode == SFmode)
8567 || (TARGET_DOUBLE_FLOAT && mode == DFmode)
8568 || (mode == TFmode && !TARGET_IEEEQUAD)
8569 || mode == SDmode || mode == DDmode || mode == TDmode))
8570 {
8571 /* _Decimal128 must use an even/odd register pair. This assumes
8572 that the register number is odd when fregno is odd. */
8573 if (mode == TDmode && (cum->fregno % 2) == 1)
8574 cum->fregno++;
8575
8576 if (cum->fregno + (mode == TFmode || mode == TDmode ? 1 : 0)
8577 <= FP_ARG_V4_MAX_REG)
8578 return gen_rtx_REG (mode, cum->fregno);
8579 else
8580 return NULL_RTX;
8581 }
8582 else
8583 {
8584 int n_words = rs6000_arg_size (mode, type);
8585 int gregno = cum->sysv_gregno;
8586
8587 /* Long long and SPE vectors are put in (r3,r4), (r5,r6),
8588 (r7,r8) or (r9,r10). As does any other 2 word item such
8589 as complex int due to a historical mistake. */
8590 if (n_words == 2)
8591 gregno += (1 - gregno) & 1;
8592
8593 /* Multi-reg args are not split between registers and stack. */
8594 if (gregno + n_words - 1 > GP_ARG_MAX_REG)
8595 return NULL_RTX;
8596
8597 if (TARGET_32BIT && TARGET_POWERPC64)
8598 return rs6000_mixed_function_arg (mode, type,
8599 gregno - GP_ARG_MIN_REG);
8600 return gen_rtx_REG (mode, gregno);
8601 }
8602 }
8603 else
8604 {
8605 int align_words = rs6000_parm_start (mode, type, cum->words);
8606
8607 /* _Decimal128 must be passed in an even/odd float register pair.
8608 This assumes that the register number is odd when fregno is odd. */
8609 if (mode == TDmode && (cum->fregno % 2) == 1)
8610 cum->fregno++;
8611
8612 if (USE_FP_FOR_ARG_P (cum, mode, type))
8613 {
8614 rtx rvec[GP_ARG_NUM_REG + 1];
8615 rtx r;
8616 int k;
8617 bool needs_psave;
8618 enum machine_mode fmode = mode;
8619 unsigned long n_fpreg = (GET_MODE_SIZE (mode) + 7) >> 3;
8620
8621 if (cum->fregno + n_fpreg > FP_ARG_MAX_REG + 1)
8622 {
8623 /* Currently, we only ever need one reg here because complex
8624 doubles are split. */
8625 gcc_assert (cum->fregno == FP_ARG_MAX_REG
8626 && (fmode == TFmode || fmode == TDmode));
8627
8628 /* Long double or _Decimal128 split over regs and memory. */
8629 fmode = DECIMAL_FLOAT_MODE_P (fmode) ? DDmode : DFmode;
8630 }
8631
8632 /* Do we also need to pass this arg in the parameter save
8633 area? */
8634 needs_psave = (type
8635 && (cum->nargs_prototype <= 0
8636 || (DEFAULT_ABI == ABI_AIX
8637 && TARGET_XL_COMPAT
8638 && align_words >= GP_ARG_NUM_REG)));
8639
8640 if (!needs_psave && mode == fmode)
8641 return gen_rtx_REG (fmode, cum->fregno);
8642
8643 k = 0;
8644 if (needs_psave)
8645 {
8646 /* Describe the part that goes in gprs or the stack.
8647 This piece must come first, before the fprs. */
8648 if (align_words < GP_ARG_NUM_REG)
8649 {
8650 unsigned long n_words = rs6000_arg_size (mode, type);
8651
8652 if (align_words + n_words > GP_ARG_NUM_REG
8653 || (TARGET_32BIT && TARGET_POWERPC64))
8654 {
8655 /* If this is partially on the stack, then we only
8656 include the portion actually in registers here. */
8657 enum machine_mode rmode = TARGET_32BIT ? SImode : DImode;
8658 rtx off;
8659 int i = 0;
8660 if (align_words + n_words > GP_ARG_NUM_REG)
8661 /* Not all of the arg fits in gprs. Say that it
8662 goes in memory too, using a magic NULL_RTX
8663 component. Also see comment in
8664 rs6000_mixed_function_arg for why the normal
8665 function_arg_partial_nregs scheme doesn't work
8666 in this case. */
8667 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, NULL_RTX,
8668 const0_rtx);
8669 do
8670 {
8671 r = gen_rtx_REG (rmode,
8672 GP_ARG_MIN_REG + align_words);
8673 off = GEN_INT (i++ * GET_MODE_SIZE (rmode));
8674 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, r, off);
8675 }
8676 while (++align_words < GP_ARG_NUM_REG && --n_words != 0);
8677 }
8678 else
8679 {
8680 /* The whole arg fits in gprs. */
8681 r = gen_rtx_REG (mode, GP_ARG_MIN_REG + align_words);
8682 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, r, const0_rtx);
8683 }
8684 }
8685 else
8686 /* It's entirely in memory. */
8687 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, NULL_RTX, const0_rtx);
8688 }
8689
8690 /* Describe where this piece goes in the fprs. */
8691 r = gen_rtx_REG (fmode, cum->fregno);
8692 rvec[k++] = gen_rtx_EXPR_LIST (VOIDmode, r, const0_rtx);
8693
8694 return gen_rtx_PARALLEL (mode, gen_rtvec_v (k, rvec));
8695 }
8696 else if (align_words < GP_ARG_NUM_REG)
8697 {
8698 if (TARGET_32BIT && TARGET_POWERPC64)
8699 return rs6000_mixed_function_arg (mode, type, align_words);
8700
8701 if (mode == BLKmode)
8702 mode = Pmode;
8703
8704 return gen_rtx_REG (mode, GP_ARG_MIN_REG + align_words);
8705 }
8706 else
8707 return NULL_RTX;
8708 }
8709 }
8710 \f
8711 /* For an arg passed partly in registers and partly in memory, this is
8712 the number of bytes passed in registers. For args passed entirely in
8713 registers or entirely in memory, zero. When an arg is described by a
8714 PARALLEL, perhaps using more than one register type, this function
8715 returns the number of bytes used by the first element of the PARALLEL. */
8716
8717 static int
8718 rs6000_arg_partial_bytes (CUMULATIVE_ARGS *cum, enum machine_mode mode,
8719 tree type, bool named)
8720 {
8721 int ret = 0;
8722 int align_words;
8723
8724 if (DEFAULT_ABI == ABI_V4)
8725 return 0;
8726
8727 if (USE_ALTIVEC_FOR_ARG_P (cum, mode, type, named)
8728 && cum->nargs_prototype >= 0)
8729 return 0;
8730
8731 /* In this complicated case we just disable the partial_nregs code. */
8732 if (TARGET_MACHO && rs6000_darwin64_struct_check_p (mode, type))
8733 return 0;
8734
8735 align_words = rs6000_parm_start (mode, type, cum->words);
8736
8737 if (USE_FP_FOR_ARG_P (cum, mode, type))
8738 {
8739 /* If we are passing this arg in the fixed parameter save area
8740 (gprs or memory) as well as fprs, then this function should
8741 return the number of partial bytes passed in the parameter
8742 save area rather than partial bytes passed in fprs. */
8743 if (type
8744 && (cum->nargs_prototype <= 0
8745 || (DEFAULT_ABI == ABI_AIX
8746 && TARGET_XL_COMPAT
8747 && align_words >= GP_ARG_NUM_REG)))
8748 return 0;
8749 else if (cum->fregno + ((GET_MODE_SIZE (mode) + 7) >> 3)
8750 > FP_ARG_MAX_REG + 1)
8751 ret = (FP_ARG_MAX_REG + 1 - cum->fregno) * 8;
8752 else if (cum->nargs_prototype >= 0)
8753 return 0;
8754 }
8755
8756 if (align_words < GP_ARG_NUM_REG
8757 && GP_ARG_NUM_REG < align_words + rs6000_arg_size (mode, type))
8758 ret = (GP_ARG_NUM_REG - align_words) * (TARGET_32BIT ? 4 : 8);
8759
8760 if (ret != 0 && TARGET_DEBUG_ARG)
8761 fprintf (stderr, "rs6000_arg_partial_bytes: %d\n", ret);
8762
8763 return ret;
8764 }
8765 \f
8766 /* A C expression that indicates when an argument must be passed by
8767 reference. If nonzero for an argument, a copy of that argument is
8768 made in memory and a pointer to the argument is passed instead of
8769 the argument itself. The pointer is passed in whatever way is
8770 appropriate for passing a pointer to that type.
8771
8772 Under V.4, aggregates and long double are passed by reference.
8773
8774 As an extension to all 32-bit ABIs, AltiVec vectors are passed by
8775 reference unless the AltiVec vector extension ABI is in force.
8776
8777 As an extension to all ABIs, variable sized types are passed by
8778 reference. */
8779
8780 static bool
8781 rs6000_pass_by_reference (CUMULATIVE_ARGS *cum ATTRIBUTE_UNUSED,
8782 enum machine_mode mode, const_tree type,
8783 bool named ATTRIBUTE_UNUSED)
8784 {
8785 if (DEFAULT_ABI == ABI_V4 && TARGET_IEEEQUAD && mode == TFmode)
8786 {
8787 if (TARGET_DEBUG_ARG)
8788 fprintf (stderr, "function_arg_pass_by_reference: V4 long double\n");
8789 return 1;
8790 }
8791
8792 if (!type)
8793 return 0;
8794
8795 if (DEFAULT_ABI == ABI_V4 && AGGREGATE_TYPE_P (type))
8796 {
8797 if (TARGET_DEBUG_ARG)
8798 fprintf (stderr, "function_arg_pass_by_reference: V4 aggregate\n");
8799 return 1;
8800 }
8801
8802 if (int_size_in_bytes (type) < 0)
8803 {
8804 if (TARGET_DEBUG_ARG)
8805 fprintf (stderr, "function_arg_pass_by_reference: variable size\n");
8806 return 1;
8807 }
8808
8809 /* Allow -maltivec -mabi=no-altivec without warning. Altivec vector
8810 modes only exist for GCC vector types if -maltivec. */
8811 if (TARGET_32BIT && !TARGET_ALTIVEC_ABI && ALTIVEC_VECTOR_MODE (mode))
8812 {
8813 if (TARGET_DEBUG_ARG)
8814 fprintf (stderr, "function_arg_pass_by_reference: AltiVec\n");
8815 return 1;
8816 }
8817
8818 /* Pass synthetic vectors in memory. */
8819 if (TREE_CODE (type) == VECTOR_TYPE
8820 && int_size_in_bytes (type) > (TARGET_ALTIVEC_ABI ? 16 : 8))
8821 {
8822 static bool warned_for_pass_big_vectors = false;
8823 if (TARGET_DEBUG_ARG)
8824 fprintf (stderr, "function_arg_pass_by_reference: synthetic vector\n");
8825 if (!warned_for_pass_big_vectors)
8826 {
8827 warning (0, "GCC vector passed by reference: "
8828 "non-standard ABI extension with no compatibility guarantee");
8829 warned_for_pass_big_vectors = true;
8830 }
8831 return 1;
8832 }
8833
8834 return 0;
8835 }
8836
8837 static void
8838 rs6000_move_block_from_reg (int regno, rtx x, int nregs)
8839 {
8840 int i;
8841 enum machine_mode reg_mode = TARGET_32BIT ? SImode : DImode;
8842
8843 if (nregs == 0)
8844 return;
8845
8846 for (i = 0; i < nregs; i++)
8847 {
8848 rtx tem = adjust_address_nv (x, reg_mode, i * GET_MODE_SIZE (reg_mode));
8849 if (reload_completed)
8850 {
8851 if (! strict_memory_address_p (reg_mode, XEXP (tem, 0)))
8852 tem = NULL_RTX;
8853 else
8854 tem = simplify_gen_subreg (reg_mode, x, BLKmode,
8855 i * GET_MODE_SIZE (reg_mode));
8856 }
8857 else
8858 tem = replace_equiv_address (tem, XEXP (tem, 0));
8859
8860 gcc_assert (tem);
8861
8862 emit_move_insn (tem, gen_rtx_REG (reg_mode, regno + i));
8863 }
8864 }
8865 \f
8866 /* Perform any needed actions needed for a function that is receiving a
8867 variable number of arguments.
8868
8869 CUM is as above.
8870
8871 MODE and TYPE are the mode and type of the current parameter.
8872
8873 PRETEND_SIZE is a variable that should be set to the amount of stack
8874 that must be pushed by the prolog to pretend that our caller pushed
8875 it.
8876
8877 Normally, this macro will push all remaining incoming registers on the
8878 stack and set PRETEND_SIZE to the length of the registers pushed. */
8879
8880 static void
8881 setup_incoming_varargs (CUMULATIVE_ARGS *cum, enum machine_mode mode,
8882 tree type, int *pretend_size ATTRIBUTE_UNUSED,
8883 int no_rtl)
8884 {
8885 CUMULATIVE_ARGS next_cum;
8886 int reg_size = TARGET_32BIT ? 4 : 8;
8887 rtx save_area = NULL_RTX, mem;
8888 int first_reg_offset;
8889 alias_set_type set;
8890
8891 /* Skip the last named argument. */
8892 next_cum = *cum;
8893 rs6000_function_arg_advance_1 (&next_cum, mode, type, true, 0);
8894
8895 if (DEFAULT_ABI == ABI_V4)
8896 {
8897 first_reg_offset = next_cum.sysv_gregno - GP_ARG_MIN_REG;
8898
8899 if (! no_rtl)
8900 {
8901 int gpr_reg_num = 0, gpr_size = 0, fpr_size = 0;
8902 HOST_WIDE_INT offset = 0;
8903
8904 /* Try to optimize the size of the varargs save area.
8905 The ABI requires that ap.reg_save_area is doubleword
8906 aligned, but we don't need to allocate space for all
8907 the bytes, only those to which we actually will save
8908 anything. */
8909 if (cfun->va_list_gpr_size && first_reg_offset < GP_ARG_NUM_REG)
8910 gpr_reg_num = GP_ARG_NUM_REG - first_reg_offset;
8911 if (TARGET_HARD_FLOAT && TARGET_FPRS
8912 && next_cum.fregno <= FP_ARG_V4_MAX_REG
8913 && cfun->va_list_fpr_size)
8914 {
8915 if (gpr_reg_num)
8916 fpr_size = (next_cum.fregno - FP_ARG_MIN_REG)
8917 * UNITS_PER_FP_WORD;
8918 if (cfun->va_list_fpr_size
8919 < FP_ARG_V4_MAX_REG + 1 - next_cum.fregno)
8920 fpr_size += cfun->va_list_fpr_size * UNITS_PER_FP_WORD;
8921 else
8922 fpr_size += (FP_ARG_V4_MAX_REG + 1 - next_cum.fregno)
8923 * UNITS_PER_FP_WORD;
8924 }
8925 if (gpr_reg_num)
8926 {
8927 offset = -((first_reg_offset * reg_size) & ~7);
8928 if (!fpr_size && gpr_reg_num > cfun->va_list_gpr_size)
8929 {
8930 gpr_reg_num = cfun->va_list_gpr_size;
8931 if (reg_size == 4 && (first_reg_offset & 1))
8932 gpr_reg_num++;
8933 }
8934 gpr_size = (gpr_reg_num * reg_size + 7) & ~7;
8935 }
8936 else if (fpr_size)
8937 offset = - (int) (next_cum.fregno - FP_ARG_MIN_REG)
8938 * UNITS_PER_FP_WORD
8939 - (int) (GP_ARG_NUM_REG * reg_size);
8940
8941 if (gpr_size + fpr_size)
8942 {
8943 rtx reg_save_area
8944 = assign_stack_local (BLKmode, gpr_size + fpr_size, 64);
8945 gcc_assert (GET_CODE (reg_save_area) == MEM);
8946 reg_save_area = XEXP (reg_save_area, 0);
8947 if (GET_CODE (reg_save_area) == PLUS)
8948 {
8949 gcc_assert (XEXP (reg_save_area, 0)
8950 == virtual_stack_vars_rtx);
8951 gcc_assert (GET_CODE (XEXP (reg_save_area, 1)) == CONST_INT);
8952 offset += INTVAL (XEXP (reg_save_area, 1));
8953 }
8954 else
8955 gcc_assert (reg_save_area == virtual_stack_vars_rtx);
8956 }
8957
8958 cfun->machine->varargs_save_offset = offset;
8959 save_area = plus_constant (virtual_stack_vars_rtx, offset);
8960 }
8961 }
8962 else
8963 {
8964 first_reg_offset = next_cum.words;
8965 save_area = virtual_incoming_args_rtx;
8966
8967 if (targetm.calls.must_pass_in_stack (mode, type))
8968 first_reg_offset += rs6000_arg_size (TYPE_MODE (type), type);
8969 }
8970
8971 set = get_varargs_alias_set ();
8972 if (! no_rtl && first_reg_offset < GP_ARG_NUM_REG
8973 && cfun->va_list_gpr_size)
8974 {
8975 int nregs = GP_ARG_NUM_REG - first_reg_offset;
8976
8977 if (va_list_gpr_counter_field)
8978 {
8979 /* V4 va_list_gpr_size counts number of registers needed. */
8980 if (nregs > cfun->va_list_gpr_size)
8981 nregs = cfun->va_list_gpr_size;
8982 }
8983 else
8984 {
8985 /* char * va_list instead counts number of bytes needed. */
8986 if (nregs > cfun->va_list_gpr_size / reg_size)
8987 nregs = cfun->va_list_gpr_size / reg_size;
8988 }
8989
8990 mem = gen_rtx_MEM (BLKmode,
8991 plus_constant (save_area,
8992 first_reg_offset * reg_size));
8993 MEM_NOTRAP_P (mem) = 1;
8994 set_mem_alias_set (mem, set);
8995 set_mem_align (mem, BITS_PER_WORD);
8996
8997 rs6000_move_block_from_reg (GP_ARG_MIN_REG + first_reg_offset, mem,
8998 nregs);
8999 }
9000
9001 /* Save FP registers if needed. */
9002 if (DEFAULT_ABI == ABI_V4
9003 && TARGET_HARD_FLOAT && TARGET_FPRS
9004 && ! no_rtl
9005 && next_cum.fregno <= FP_ARG_V4_MAX_REG
9006 && cfun->va_list_fpr_size)
9007 {
9008 int fregno = next_cum.fregno, nregs;
9009 rtx cr1 = gen_rtx_REG (CCmode, CR1_REGNO);
9010 rtx lab = gen_label_rtx ();
9011 int off = (GP_ARG_NUM_REG * reg_size) + ((fregno - FP_ARG_MIN_REG)
9012 * UNITS_PER_FP_WORD);
9013
9014 emit_jump_insn
9015 (gen_rtx_SET (VOIDmode,
9016 pc_rtx,
9017 gen_rtx_IF_THEN_ELSE (VOIDmode,
9018 gen_rtx_NE (VOIDmode, cr1,
9019 const0_rtx),
9020 gen_rtx_LABEL_REF (VOIDmode, lab),
9021 pc_rtx)));
9022
9023 for (nregs = 0;
9024 fregno <= FP_ARG_V4_MAX_REG && nregs < cfun->va_list_fpr_size;
9025 fregno++, off += UNITS_PER_FP_WORD, nregs++)
9026 {
9027 mem = gen_rtx_MEM ((TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT)
9028 ? DFmode : SFmode,
9029 plus_constant (save_area, off));
9030 MEM_NOTRAP_P (mem) = 1;
9031 set_mem_alias_set (mem, set);
9032 set_mem_align (mem, GET_MODE_ALIGNMENT (
9033 (TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT)
9034 ? DFmode : SFmode));
9035 emit_move_insn (mem, gen_rtx_REG (
9036 (TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT)
9037 ? DFmode : SFmode, fregno));
9038 }
9039
9040 emit_label (lab);
9041 }
9042 }
9043
9044 /* Create the va_list data type. */
9045
9046 static tree
9047 rs6000_build_builtin_va_list (void)
9048 {
9049 tree f_gpr, f_fpr, f_res, f_ovf, f_sav, record, type_decl;
9050
9051 /* For AIX, prefer 'char *' because that's what the system
9052 header files like. */
9053 if (DEFAULT_ABI != ABI_V4)
9054 return build_pointer_type (char_type_node);
9055
9056 record = (*lang_hooks.types.make_type) (RECORD_TYPE);
9057 type_decl = build_decl (BUILTINS_LOCATION, TYPE_DECL,
9058 get_identifier ("__va_list_tag"), record);
9059
9060 f_gpr = build_decl (BUILTINS_LOCATION, FIELD_DECL, get_identifier ("gpr"),
9061 unsigned_char_type_node);
9062 f_fpr = build_decl (BUILTINS_LOCATION, FIELD_DECL, get_identifier ("fpr"),
9063 unsigned_char_type_node);
9064 /* Give the two bytes of padding a name, so that -Wpadded won't warn on
9065 every user file. */
9066 f_res = build_decl (BUILTINS_LOCATION, FIELD_DECL,
9067 get_identifier ("reserved"), short_unsigned_type_node);
9068 f_ovf = build_decl (BUILTINS_LOCATION, FIELD_DECL,
9069 get_identifier ("overflow_arg_area"),
9070 ptr_type_node);
9071 f_sav = build_decl (BUILTINS_LOCATION, FIELD_DECL,
9072 get_identifier ("reg_save_area"),
9073 ptr_type_node);
9074
9075 va_list_gpr_counter_field = f_gpr;
9076 va_list_fpr_counter_field = f_fpr;
9077
9078 DECL_FIELD_CONTEXT (f_gpr) = record;
9079 DECL_FIELD_CONTEXT (f_fpr) = record;
9080 DECL_FIELD_CONTEXT (f_res) = record;
9081 DECL_FIELD_CONTEXT (f_ovf) = record;
9082 DECL_FIELD_CONTEXT (f_sav) = record;
9083
9084 TREE_CHAIN (record) = type_decl;
9085 TYPE_NAME (record) = type_decl;
9086 TYPE_FIELDS (record) = f_gpr;
9087 DECL_CHAIN (f_gpr) = f_fpr;
9088 DECL_CHAIN (f_fpr) = f_res;
9089 DECL_CHAIN (f_res) = f_ovf;
9090 DECL_CHAIN (f_ovf) = f_sav;
9091
9092 layout_type (record);
9093
9094 /* The correct type is an array type of one element. */
9095 return build_array_type (record, build_index_type (size_zero_node));
9096 }
9097
9098 /* Implement va_start. */
9099
9100 static void
9101 rs6000_va_start (tree valist, rtx nextarg)
9102 {
9103 HOST_WIDE_INT words, n_gpr, n_fpr;
9104 tree f_gpr, f_fpr, f_res, f_ovf, f_sav;
9105 tree gpr, fpr, ovf, sav, t;
9106
9107 /* Only SVR4 needs something special. */
9108 if (DEFAULT_ABI != ABI_V4)
9109 {
9110 std_expand_builtin_va_start (valist, nextarg);
9111 return;
9112 }
9113
9114 f_gpr = TYPE_FIELDS (TREE_TYPE (va_list_type_node));
9115 f_fpr = DECL_CHAIN (f_gpr);
9116 f_res = DECL_CHAIN (f_fpr);
9117 f_ovf = DECL_CHAIN (f_res);
9118 f_sav = DECL_CHAIN (f_ovf);
9119
9120 valist = build_va_arg_indirect_ref (valist);
9121 gpr = build3 (COMPONENT_REF, TREE_TYPE (f_gpr), valist, f_gpr, NULL_TREE);
9122 fpr = build3 (COMPONENT_REF, TREE_TYPE (f_fpr), unshare_expr (valist),
9123 f_fpr, NULL_TREE);
9124 ovf = build3 (COMPONENT_REF, TREE_TYPE (f_ovf), unshare_expr (valist),
9125 f_ovf, NULL_TREE);
9126 sav = build3 (COMPONENT_REF, TREE_TYPE (f_sav), unshare_expr (valist),
9127 f_sav, NULL_TREE);
9128
9129 /* Count number of gp and fp argument registers used. */
9130 words = crtl->args.info.words;
9131 n_gpr = MIN (crtl->args.info.sysv_gregno - GP_ARG_MIN_REG,
9132 GP_ARG_NUM_REG);
9133 n_fpr = MIN (crtl->args.info.fregno - FP_ARG_MIN_REG,
9134 FP_ARG_NUM_REG);
9135
9136 if (TARGET_DEBUG_ARG)
9137 fprintf (stderr, "va_start: words = "HOST_WIDE_INT_PRINT_DEC", n_gpr = "
9138 HOST_WIDE_INT_PRINT_DEC", n_fpr = "HOST_WIDE_INT_PRINT_DEC"\n",
9139 words, n_gpr, n_fpr);
9140
9141 if (cfun->va_list_gpr_size)
9142 {
9143 t = build2 (MODIFY_EXPR, TREE_TYPE (gpr), gpr,
9144 build_int_cst (NULL_TREE, n_gpr));
9145 TREE_SIDE_EFFECTS (t) = 1;
9146 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
9147 }
9148
9149 if (cfun->va_list_fpr_size)
9150 {
9151 t = build2 (MODIFY_EXPR, TREE_TYPE (fpr), fpr,
9152 build_int_cst (NULL_TREE, n_fpr));
9153 TREE_SIDE_EFFECTS (t) = 1;
9154 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
9155 }
9156
9157 /* Find the overflow area. */
9158 t = make_tree (TREE_TYPE (ovf), virtual_incoming_args_rtx);
9159 if (words != 0)
9160 t = build2 (POINTER_PLUS_EXPR, TREE_TYPE (ovf), t,
9161 size_int (words * UNITS_PER_WORD));
9162 t = build2 (MODIFY_EXPR, TREE_TYPE (ovf), ovf, t);
9163 TREE_SIDE_EFFECTS (t) = 1;
9164 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
9165
9166 /* If there were no va_arg invocations, don't set up the register
9167 save area. */
9168 if (!cfun->va_list_gpr_size
9169 && !cfun->va_list_fpr_size
9170 && n_gpr < GP_ARG_NUM_REG
9171 && n_fpr < FP_ARG_V4_MAX_REG)
9172 return;
9173
9174 /* Find the register save area. */
9175 t = make_tree (TREE_TYPE (sav), virtual_stack_vars_rtx);
9176 if (cfun->machine->varargs_save_offset)
9177 t = build2 (POINTER_PLUS_EXPR, TREE_TYPE (sav), t,
9178 size_int (cfun->machine->varargs_save_offset));
9179 t = build2 (MODIFY_EXPR, TREE_TYPE (sav), sav, t);
9180 TREE_SIDE_EFFECTS (t) = 1;
9181 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
9182 }
9183
9184 /* Implement va_arg. */
9185
9186 tree
9187 rs6000_gimplify_va_arg (tree valist, tree type, gimple_seq *pre_p,
9188 gimple_seq *post_p)
9189 {
9190 tree f_gpr, f_fpr, f_res, f_ovf, f_sav;
9191 tree gpr, fpr, ovf, sav, reg, t, u;
9192 int size, rsize, n_reg, sav_ofs, sav_scale;
9193 tree lab_false, lab_over, addr;
9194 int align;
9195 tree ptrtype = build_pointer_type_for_mode (type, ptr_mode, true);
9196 int regalign = 0;
9197 gimple stmt;
9198
9199 if (pass_by_reference (NULL, TYPE_MODE (type), type, false))
9200 {
9201 t = rs6000_gimplify_va_arg (valist, ptrtype, pre_p, post_p);
9202 return build_va_arg_indirect_ref (t);
9203 }
9204
9205 /* We need to deal with the fact that the darwin ppc64 ABI is defined by an
9206 earlier version of gcc, with the property that it always applied alignment
9207 adjustments to the va-args (even for zero-sized types). The cheapest way
9208 to deal with this is to replicate the effect of the part of
9209 std_gimplify_va_arg_expr that carries out the align adjust, for the case
9210 of relevance.
9211 We don't need to check for pass-by-reference because of the test above.
9212 We can return a simplifed answer, since we know there's no offset to add. */
9213
9214 if (TARGET_MACHO
9215 && rs6000_darwin64_abi
9216 && integer_zerop (TYPE_SIZE (type)))
9217 {
9218 unsigned HOST_WIDE_INT align, boundary;
9219 tree valist_tmp = get_initialized_tmp_var (valist, pre_p, NULL);
9220 align = PARM_BOUNDARY / BITS_PER_UNIT;
9221 boundary = FUNCTION_ARG_BOUNDARY (TYPE_MODE (type), type);
9222 if (boundary > MAX_SUPPORTED_STACK_ALIGNMENT)
9223 boundary = MAX_SUPPORTED_STACK_ALIGNMENT;
9224 boundary /= BITS_PER_UNIT;
9225 if (boundary > align)
9226 {
9227 tree t ;
9228 /* This updates arg ptr by the amount that would be necessary
9229 to align the zero-sized (but not zero-alignment) item. */
9230 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist_tmp,
9231 fold_build2 (POINTER_PLUS_EXPR,
9232 TREE_TYPE (valist),
9233 valist_tmp, size_int (boundary - 1)));
9234 gimplify_and_add (t, pre_p);
9235
9236 t = fold_convert (sizetype, valist_tmp);
9237 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist_tmp,
9238 fold_convert (TREE_TYPE (valist),
9239 fold_build2 (BIT_AND_EXPR, sizetype, t,
9240 size_int (-boundary))));
9241 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist, t);
9242 gimplify_and_add (t, pre_p);
9243 }
9244 /* Since it is zero-sized there's no increment for the item itself. */
9245 valist_tmp = fold_convert (build_pointer_type (type), valist_tmp);
9246 return build_va_arg_indirect_ref (valist_tmp);
9247 }
9248
9249 if (DEFAULT_ABI != ABI_V4)
9250 {
9251 if (targetm.calls.split_complex_arg && TREE_CODE (type) == COMPLEX_TYPE)
9252 {
9253 tree elem_type = TREE_TYPE (type);
9254 enum machine_mode elem_mode = TYPE_MODE (elem_type);
9255 int elem_size = GET_MODE_SIZE (elem_mode);
9256
9257 if (elem_size < UNITS_PER_WORD)
9258 {
9259 tree real_part, imag_part;
9260 gimple_seq post = NULL;
9261
9262 real_part = rs6000_gimplify_va_arg (valist, elem_type, pre_p,
9263 &post);
9264 /* Copy the value into a temporary, lest the formal temporary
9265 be reused out from under us. */
9266 real_part = get_initialized_tmp_var (real_part, pre_p, &post);
9267 gimple_seq_add_seq (pre_p, post);
9268
9269 imag_part = rs6000_gimplify_va_arg (valist, elem_type, pre_p,
9270 post_p);
9271
9272 return build2 (COMPLEX_EXPR, type, real_part, imag_part);
9273 }
9274 }
9275
9276 return std_gimplify_va_arg_expr (valist, type, pre_p, post_p);
9277 }
9278
9279 f_gpr = TYPE_FIELDS (TREE_TYPE (va_list_type_node));
9280 f_fpr = DECL_CHAIN (f_gpr);
9281 f_res = DECL_CHAIN (f_fpr);
9282 f_ovf = DECL_CHAIN (f_res);
9283 f_sav = DECL_CHAIN (f_ovf);
9284
9285 valist = build_va_arg_indirect_ref (valist);
9286 gpr = build3 (COMPONENT_REF, TREE_TYPE (f_gpr), valist, f_gpr, NULL_TREE);
9287 fpr = build3 (COMPONENT_REF, TREE_TYPE (f_fpr), unshare_expr (valist),
9288 f_fpr, NULL_TREE);
9289 ovf = build3 (COMPONENT_REF, TREE_TYPE (f_ovf), unshare_expr (valist),
9290 f_ovf, NULL_TREE);
9291 sav = build3 (COMPONENT_REF, TREE_TYPE (f_sav), unshare_expr (valist),
9292 f_sav, NULL_TREE);
9293
9294 size = int_size_in_bytes (type);
9295 rsize = (size + 3) / 4;
9296 align = 1;
9297
9298 if (TARGET_HARD_FLOAT && TARGET_FPRS
9299 && ((TARGET_SINGLE_FLOAT && TYPE_MODE (type) == SFmode)
9300 || (TARGET_DOUBLE_FLOAT
9301 && (TYPE_MODE (type) == DFmode
9302 || TYPE_MODE (type) == TFmode
9303 || TYPE_MODE (type) == SDmode
9304 || TYPE_MODE (type) == DDmode
9305 || TYPE_MODE (type) == TDmode))))
9306 {
9307 /* FP args go in FP registers, if present. */
9308 reg = fpr;
9309 n_reg = (size + 7) / 8;
9310 sav_ofs = ((TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT) ? 8 : 4) * 4;
9311 sav_scale = ((TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT) ? 8 : 4);
9312 if (TYPE_MODE (type) != SFmode && TYPE_MODE (type) != SDmode)
9313 align = 8;
9314 }
9315 else
9316 {
9317 /* Otherwise into GP registers. */
9318 reg = gpr;
9319 n_reg = rsize;
9320 sav_ofs = 0;
9321 sav_scale = 4;
9322 if (n_reg == 2)
9323 align = 8;
9324 }
9325
9326 /* Pull the value out of the saved registers.... */
9327
9328 lab_over = NULL;
9329 addr = create_tmp_var (ptr_type_node, "addr");
9330
9331 /* AltiVec vectors never go in registers when -mabi=altivec. */
9332 if (TARGET_ALTIVEC_ABI && ALTIVEC_VECTOR_MODE (TYPE_MODE (type)))
9333 align = 16;
9334 else
9335 {
9336 lab_false = create_artificial_label (input_location);
9337 lab_over = create_artificial_label (input_location);
9338
9339 /* Long long and SPE vectors are aligned in the registers.
9340 As are any other 2 gpr item such as complex int due to a
9341 historical mistake. */
9342 u = reg;
9343 if (n_reg == 2 && reg == gpr)
9344 {
9345 regalign = 1;
9346 u = build2 (BIT_AND_EXPR, TREE_TYPE (reg), unshare_expr (reg),
9347 build_int_cst (TREE_TYPE (reg), n_reg - 1));
9348 u = build2 (POSTINCREMENT_EXPR, TREE_TYPE (reg),
9349 unshare_expr (reg), u);
9350 }
9351 /* _Decimal128 is passed in even/odd fpr pairs; the stored
9352 reg number is 0 for f1, so we want to make it odd. */
9353 else if (reg == fpr && TYPE_MODE (type) == TDmode)
9354 {
9355 t = build2 (BIT_IOR_EXPR, TREE_TYPE (reg), unshare_expr (reg),
9356 build_int_cst (TREE_TYPE (reg), 1));
9357 u = build2 (MODIFY_EXPR, void_type_node, unshare_expr (reg), t);
9358 }
9359
9360 t = fold_convert (TREE_TYPE (reg), size_int (8 - n_reg + 1));
9361 t = build2 (GE_EXPR, boolean_type_node, u, t);
9362 u = build1 (GOTO_EXPR, void_type_node, lab_false);
9363 t = build3 (COND_EXPR, void_type_node, t, u, NULL_TREE);
9364 gimplify_and_add (t, pre_p);
9365
9366 t = sav;
9367 if (sav_ofs)
9368 t = build2 (POINTER_PLUS_EXPR, ptr_type_node, sav, size_int (sav_ofs));
9369
9370 u = build2 (POSTINCREMENT_EXPR, TREE_TYPE (reg), unshare_expr (reg),
9371 build_int_cst (TREE_TYPE (reg), n_reg));
9372 u = fold_convert (sizetype, u);
9373 u = build2 (MULT_EXPR, sizetype, u, size_int (sav_scale));
9374 t = build2 (POINTER_PLUS_EXPR, ptr_type_node, t, u);
9375
9376 /* _Decimal32 varargs are located in the second word of the 64-bit
9377 FP register for 32-bit binaries. */
9378 if (!TARGET_POWERPC64
9379 && TARGET_HARD_FLOAT && TARGET_FPRS
9380 && TYPE_MODE (type) == SDmode)
9381 t = build2 (POINTER_PLUS_EXPR, TREE_TYPE (t), t, size_int (size));
9382
9383 gimplify_assign (addr, t, pre_p);
9384
9385 gimple_seq_add_stmt (pre_p, gimple_build_goto (lab_over));
9386
9387 stmt = gimple_build_label (lab_false);
9388 gimple_seq_add_stmt (pre_p, stmt);
9389
9390 if ((n_reg == 2 && !regalign) || n_reg > 2)
9391 {
9392 /* Ensure that we don't find any more args in regs.
9393 Alignment has taken care of for special cases. */
9394 gimplify_assign (reg, build_int_cst (TREE_TYPE (reg), 8), pre_p);
9395 }
9396 }
9397
9398 /* ... otherwise out of the overflow area. */
9399
9400 /* Care for on-stack alignment if needed. */
9401 t = ovf;
9402 if (align != 1)
9403 {
9404 t = build2 (POINTER_PLUS_EXPR, TREE_TYPE (t), t, size_int (align - 1));
9405 t = fold_convert (sizetype, t);
9406 t = build2 (BIT_AND_EXPR, TREE_TYPE (t), t,
9407 size_int (-align));
9408 t = fold_convert (TREE_TYPE (ovf), t);
9409 }
9410 gimplify_expr (&t, pre_p, NULL, is_gimple_val, fb_rvalue);
9411
9412 gimplify_assign (unshare_expr (addr), t, pre_p);
9413
9414 t = build2 (POINTER_PLUS_EXPR, TREE_TYPE (t), t, size_int (size));
9415 gimplify_assign (unshare_expr (ovf), t, pre_p);
9416
9417 if (lab_over)
9418 {
9419 stmt = gimple_build_label (lab_over);
9420 gimple_seq_add_stmt (pre_p, stmt);
9421 }
9422
9423 if (STRICT_ALIGNMENT
9424 && (TYPE_ALIGN (type)
9425 > (unsigned) BITS_PER_UNIT * (align < 4 ? 4 : align)))
9426 {
9427 /* The value (of type complex double, for example) may not be
9428 aligned in memory in the saved registers, so copy via a
9429 temporary. (This is the same code as used for SPARC.) */
9430 tree tmp = create_tmp_var (type, "va_arg_tmp");
9431 tree dest_addr = build_fold_addr_expr (tmp);
9432
9433 tree copy = build_call_expr (implicit_built_in_decls[BUILT_IN_MEMCPY],
9434 3, dest_addr, addr, size_int (rsize * 4));
9435
9436 gimplify_and_add (copy, pre_p);
9437 addr = dest_addr;
9438 }
9439
9440 addr = fold_convert (ptrtype, addr);
9441 return build_va_arg_indirect_ref (addr);
9442 }
9443
9444 /* Builtins. */
9445
9446 static void
9447 def_builtin (int mask, const char *name, tree type, int code)
9448 {
9449 if ((mask & target_flags) || TARGET_PAIRED_FLOAT)
9450 {
9451 tree t;
9452 if (rs6000_builtin_decls[code])
9453 fatal_error ("internal error: builtin function to %s already processed.",
9454 name);
9455
9456 rs6000_builtin_decls[code] = t =
9457 add_builtin_function (name, type, code, BUILT_IN_MD,
9458 NULL, NULL_TREE);
9459
9460 gcc_assert (code >= 0 && code < (int)RS6000_BUILTIN_COUNT);
9461 switch (builtin_classify[code])
9462 {
9463 default:
9464 gcc_unreachable ();
9465
9466 /* assume builtin can do anything. */
9467 case RS6000_BTC_MISC:
9468 break;
9469
9470 /* const function, function only depends on the inputs. */
9471 case RS6000_BTC_CONST:
9472 TREE_READONLY (t) = 1;
9473 TREE_NOTHROW (t) = 1;
9474 break;
9475
9476 /* pure function, function can read global memory. */
9477 case RS6000_BTC_PURE:
9478 DECL_PURE_P (t) = 1;
9479 TREE_NOTHROW (t) = 1;
9480 break;
9481
9482 /* Function is a math function. If rounding mode is on, then treat
9483 the function as not reading global memory, but it can have
9484 arbitrary side effects. If it is off, then assume the function is
9485 a const function. This mimics the ATTR_MATHFN_FPROUNDING
9486 attribute in builtin-attribute.def that is used for the math
9487 functions. */
9488 case RS6000_BTC_FP_PURE:
9489 TREE_NOTHROW (t) = 1;
9490 if (flag_rounding_math)
9491 {
9492 DECL_PURE_P (t) = 1;
9493 DECL_IS_NOVOPS (t) = 1;
9494 }
9495 else
9496 TREE_READONLY (t) = 1;
9497 break;
9498 }
9499 }
9500 }
9501
9502 /* Simple ternary operations: VECd = foo (VECa, VECb, VECc). */
9503
9504 static const struct builtin_description bdesc_3arg[] =
9505 {
9506 { MASK_ALTIVEC, CODE_FOR_altivec_vmaddfp, "__builtin_altivec_vmaddfp", ALTIVEC_BUILTIN_VMADDFP },
9507 { MASK_ALTIVEC, CODE_FOR_altivec_vmhaddshs, "__builtin_altivec_vmhaddshs", ALTIVEC_BUILTIN_VMHADDSHS },
9508 { MASK_ALTIVEC, CODE_FOR_altivec_vmhraddshs, "__builtin_altivec_vmhraddshs", ALTIVEC_BUILTIN_VMHRADDSHS },
9509 { MASK_ALTIVEC, CODE_FOR_altivec_vmladduhm, "__builtin_altivec_vmladduhm", ALTIVEC_BUILTIN_VMLADDUHM},
9510 { MASK_ALTIVEC, CODE_FOR_altivec_vmsumubm, "__builtin_altivec_vmsumubm", ALTIVEC_BUILTIN_VMSUMUBM },
9511 { MASK_ALTIVEC, CODE_FOR_altivec_vmsummbm, "__builtin_altivec_vmsummbm", ALTIVEC_BUILTIN_VMSUMMBM },
9512 { MASK_ALTIVEC, CODE_FOR_altivec_vmsumuhm, "__builtin_altivec_vmsumuhm", ALTIVEC_BUILTIN_VMSUMUHM },
9513 { MASK_ALTIVEC, CODE_FOR_altivec_vmsumshm, "__builtin_altivec_vmsumshm", ALTIVEC_BUILTIN_VMSUMSHM },
9514 { MASK_ALTIVEC, CODE_FOR_altivec_vmsumuhs, "__builtin_altivec_vmsumuhs", ALTIVEC_BUILTIN_VMSUMUHS },
9515 { MASK_ALTIVEC, CODE_FOR_altivec_vmsumshs, "__builtin_altivec_vmsumshs", ALTIVEC_BUILTIN_VMSUMSHS },
9516 { MASK_ALTIVEC, CODE_FOR_altivec_vnmsubfp, "__builtin_altivec_vnmsubfp", ALTIVEC_BUILTIN_VNMSUBFP },
9517 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v2df, "__builtin_altivec_vperm_2df", ALTIVEC_BUILTIN_VPERM_2DF },
9518 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v2di, "__builtin_altivec_vperm_2di", ALTIVEC_BUILTIN_VPERM_2DI },
9519 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v4sf, "__builtin_altivec_vperm_4sf", ALTIVEC_BUILTIN_VPERM_4SF },
9520 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v4si, "__builtin_altivec_vperm_4si", ALTIVEC_BUILTIN_VPERM_4SI },
9521 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v8hi, "__builtin_altivec_vperm_8hi", ALTIVEC_BUILTIN_VPERM_8HI },
9522 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v16qi_uns, "__builtin_altivec_vperm_16qi", ALTIVEC_BUILTIN_VPERM_16QI },
9523 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v2di_uns, "__builtin_altivec_vperm_2di_uns", ALTIVEC_BUILTIN_VPERM_2DI_UNS },
9524 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v4si_uns, "__builtin_altivec_vperm_4si_uns", ALTIVEC_BUILTIN_VPERM_4SI_UNS },
9525 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v8hi_uns, "__builtin_altivec_vperm_8hi_uns", ALTIVEC_BUILTIN_VPERM_8HI_UNS },
9526 { MASK_ALTIVEC, CODE_FOR_altivec_vperm_v16qi_uns, "__builtin_altivec_vperm_16qi_uns", ALTIVEC_BUILTIN_VPERM_16QI_UNS },
9527 { MASK_ALTIVEC, CODE_FOR_vector_select_v4sf, "__builtin_altivec_vsel_4sf", ALTIVEC_BUILTIN_VSEL_4SF },
9528 { MASK_ALTIVEC, CODE_FOR_vector_select_v4si, "__builtin_altivec_vsel_4si", ALTIVEC_BUILTIN_VSEL_4SI },
9529 { MASK_ALTIVEC, CODE_FOR_vector_select_v8hi, "__builtin_altivec_vsel_8hi", ALTIVEC_BUILTIN_VSEL_8HI },
9530 { MASK_ALTIVEC, CODE_FOR_vector_select_v16qi, "__builtin_altivec_vsel_16qi", ALTIVEC_BUILTIN_VSEL_16QI },
9531 { MASK_ALTIVEC, CODE_FOR_vector_select_v2df, "__builtin_altivec_vsel_2df", ALTIVEC_BUILTIN_VSEL_2DF },
9532 { MASK_ALTIVEC, CODE_FOR_vector_select_v2di, "__builtin_altivec_vsel_2di", ALTIVEC_BUILTIN_VSEL_2DI },
9533 { MASK_ALTIVEC, CODE_FOR_vector_select_v4si_uns, "__builtin_altivec_vsel_4si_uns", ALTIVEC_BUILTIN_VSEL_4SI_UNS },
9534 { MASK_ALTIVEC, CODE_FOR_vector_select_v8hi_uns, "__builtin_altivec_vsel_8hi_uns", ALTIVEC_BUILTIN_VSEL_8HI_UNS },
9535 { MASK_ALTIVEC, CODE_FOR_vector_select_v16qi_uns, "__builtin_altivec_vsel_16qi_uns", ALTIVEC_BUILTIN_VSEL_16QI_UNS },
9536 { MASK_ALTIVEC, CODE_FOR_vector_select_v2di_uns, "__builtin_altivec_vsel_2di_uns", ALTIVEC_BUILTIN_VSEL_2DI_UNS },
9537 { MASK_ALTIVEC, CODE_FOR_altivec_vsldoi_v16qi, "__builtin_altivec_vsldoi_16qi", ALTIVEC_BUILTIN_VSLDOI_16QI },
9538 { MASK_ALTIVEC, CODE_FOR_altivec_vsldoi_v8hi, "__builtin_altivec_vsldoi_8hi", ALTIVEC_BUILTIN_VSLDOI_8HI },
9539 { MASK_ALTIVEC, CODE_FOR_altivec_vsldoi_v4si, "__builtin_altivec_vsldoi_4si", ALTIVEC_BUILTIN_VSLDOI_4SI },
9540 { MASK_ALTIVEC, CODE_FOR_altivec_vsldoi_v4sf, "__builtin_altivec_vsldoi_4sf", ALTIVEC_BUILTIN_VSLDOI_4SF },
9541
9542 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_madd", ALTIVEC_BUILTIN_VEC_MADD },
9543 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_madds", ALTIVEC_BUILTIN_VEC_MADDS },
9544 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mladd", ALTIVEC_BUILTIN_VEC_MLADD },
9545 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mradds", ALTIVEC_BUILTIN_VEC_MRADDS },
9546 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_msum", ALTIVEC_BUILTIN_VEC_MSUM },
9547 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmsumshm", ALTIVEC_BUILTIN_VEC_VMSUMSHM },
9548 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmsumuhm", ALTIVEC_BUILTIN_VEC_VMSUMUHM },
9549 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmsummbm", ALTIVEC_BUILTIN_VEC_VMSUMMBM },
9550 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmsumubm", ALTIVEC_BUILTIN_VEC_VMSUMUBM },
9551 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_msums", ALTIVEC_BUILTIN_VEC_MSUMS },
9552 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmsumshs", ALTIVEC_BUILTIN_VEC_VMSUMSHS },
9553 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmsumuhs", ALTIVEC_BUILTIN_VEC_VMSUMUHS },
9554 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_nmsub", ALTIVEC_BUILTIN_VEC_NMSUB },
9555 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_perm", ALTIVEC_BUILTIN_VEC_PERM },
9556 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sel", ALTIVEC_BUILTIN_VEC_SEL },
9557
9558 { MASK_VSX, CODE_FOR_vsx_fmaddv2df4, "__builtin_vsx_xvmadddp", VSX_BUILTIN_XVMADDDP },
9559 { MASK_VSX, CODE_FOR_vsx_fmsubv2df4, "__builtin_vsx_xvmsubdp", VSX_BUILTIN_XVMSUBDP },
9560 { MASK_VSX, CODE_FOR_vsx_fnmaddv2df4, "__builtin_vsx_xvnmadddp", VSX_BUILTIN_XVNMADDDP },
9561 { MASK_VSX, CODE_FOR_vsx_fnmsubv2df4, "__builtin_vsx_xvnmsubdp", VSX_BUILTIN_XVNMSUBDP },
9562
9563 { MASK_VSX, CODE_FOR_vsx_fmaddv4sf4, "__builtin_vsx_xvmaddsp", VSX_BUILTIN_XVMADDSP },
9564 { MASK_VSX, CODE_FOR_vsx_fmsubv4sf4, "__builtin_vsx_xvmsubsp", VSX_BUILTIN_XVMSUBSP },
9565 { MASK_VSX, CODE_FOR_vsx_fnmaddv4sf4, "__builtin_vsx_xvnmaddsp", VSX_BUILTIN_XVNMADDSP },
9566 { MASK_VSX, CODE_FOR_vsx_fnmsubv4sf4, "__builtin_vsx_xvnmsubsp", VSX_BUILTIN_XVNMSUBSP },
9567
9568 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_msub", VSX_BUILTIN_VEC_MSUB },
9569 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_nmadd", VSX_BUILTIN_VEC_NMADD },
9570
9571 { MASK_VSX, CODE_FOR_vector_select_v2di, "__builtin_vsx_xxsel_2di", VSX_BUILTIN_XXSEL_2DI },
9572 { MASK_VSX, CODE_FOR_vector_select_v2df, "__builtin_vsx_xxsel_2df", VSX_BUILTIN_XXSEL_2DF },
9573 { MASK_VSX, CODE_FOR_vector_select_v4sf, "__builtin_vsx_xxsel_4sf", VSX_BUILTIN_XXSEL_4SF },
9574 { MASK_VSX, CODE_FOR_vector_select_v4si, "__builtin_vsx_xxsel_4si", VSX_BUILTIN_XXSEL_4SI },
9575 { MASK_VSX, CODE_FOR_vector_select_v8hi, "__builtin_vsx_xxsel_8hi", VSX_BUILTIN_XXSEL_8HI },
9576 { MASK_VSX, CODE_FOR_vector_select_v16qi, "__builtin_vsx_xxsel_16qi", VSX_BUILTIN_XXSEL_16QI },
9577 { MASK_VSX, CODE_FOR_vector_select_v2di_uns, "__builtin_vsx_xxsel_2di_uns", VSX_BUILTIN_XXSEL_2DI_UNS },
9578 { MASK_VSX, CODE_FOR_vector_select_v4si_uns, "__builtin_vsx_xxsel_4si_uns", VSX_BUILTIN_XXSEL_4SI_UNS },
9579 { MASK_VSX, CODE_FOR_vector_select_v8hi_uns, "__builtin_vsx_xxsel_8hi_uns", VSX_BUILTIN_XXSEL_8HI_UNS },
9580 { MASK_VSX, CODE_FOR_vector_select_v16qi_uns, "__builtin_vsx_xxsel_16qi_uns", VSX_BUILTIN_XXSEL_16QI_UNS },
9581
9582 { MASK_VSX, CODE_FOR_altivec_vperm_v2di, "__builtin_vsx_vperm_2di", VSX_BUILTIN_VPERM_2DI },
9583 { MASK_VSX, CODE_FOR_altivec_vperm_v2df, "__builtin_vsx_vperm_2df", VSX_BUILTIN_VPERM_2DF },
9584 { MASK_VSX, CODE_FOR_altivec_vperm_v4sf, "__builtin_vsx_vperm_4sf", VSX_BUILTIN_VPERM_4SF },
9585 { MASK_VSX, CODE_FOR_altivec_vperm_v4si, "__builtin_vsx_vperm_4si", VSX_BUILTIN_VPERM_4SI },
9586 { MASK_VSX, CODE_FOR_altivec_vperm_v8hi, "__builtin_vsx_vperm_8hi", VSX_BUILTIN_VPERM_8HI },
9587 { MASK_VSX, CODE_FOR_altivec_vperm_v16qi, "__builtin_vsx_vperm_16qi", VSX_BUILTIN_VPERM_16QI },
9588 { MASK_VSX, CODE_FOR_altivec_vperm_v2di_uns, "__builtin_vsx_vperm_2di_uns", VSX_BUILTIN_VPERM_2DI_UNS },
9589 { MASK_VSX, CODE_FOR_altivec_vperm_v4si_uns, "__builtin_vsx_vperm_4si_uns", VSX_BUILTIN_VPERM_4SI_UNS },
9590 { MASK_VSX, CODE_FOR_altivec_vperm_v8hi_uns, "__builtin_vsx_vperm_8hi_uns", VSX_BUILTIN_VPERM_8HI_UNS },
9591 { MASK_VSX, CODE_FOR_altivec_vperm_v16qi_uns, "__builtin_vsx_vperm_16qi_uns", VSX_BUILTIN_VPERM_16QI_UNS },
9592
9593 { MASK_VSX, CODE_FOR_vsx_xxpermdi_v2df, "__builtin_vsx_xxpermdi_2df", VSX_BUILTIN_XXPERMDI_2DF },
9594 { MASK_VSX, CODE_FOR_vsx_xxpermdi_v2di, "__builtin_vsx_xxpermdi_2di", VSX_BUILTIN_XXPERMDI_2DI },
9595 { MASK_VSX, CODE_FOR_vsx_xxpermdi_v4sf, "__builtin_vsx_xxpermdi_4sf", VSX_BUILTIN_XXPERMDI_4SF },
9596 { MASK_VSX, CODE_FOR_vsx_xxpermdi_v4si, "__builtin_vsx_xxpermdi_4si", VSX_BUILTIN_XXPERMDI_4SI },
9597 { MASK_VSX, CODE_FOR_vsx_xxpermdi_v8hi, "__builtin_vsx_xxpermdi_8hi", VSX_BUILTIN_XXPERMDI_8HI },
9598 { MASK_VSX, CODE_FOR_vsx_xxpermdi_v16qi, "__builtin_vsx_xxpermdi_16qi", VSX_BUILTIN_XXPERMDI_16QI },
9599 { MASK_VSX, CODE_FOR_nothing, "__builtin_vsx_xxpermdi", VSX_BUILTIN_VEC_XXPERMDI },
9600 { MASK_VSX, CODE_FOR_vsx_set_v2df, "__builtin_vsx_set_2df", VSX_BUILTIN_SET_2DF },
9601 { MASK_VSX, CODE_FOR_vsx_set_v2di, "__builtin_vsx_set_2di", VSX_BUILTIN_SET_2DI },
9602
9603 { MASK_VSX, CODE_FOR_vsx_xxsldwi_v2di, "__builtin_vsx_xxsldwi_2di", VSX_BUILTIN_XXSLDWI_2DI },
9604 { MASK_VSX, CODE_FOR_vsx_xxsldwi_v2df, "__builtin_vsx_xxsldwi_2df", VSX_BUILTIN_XXSLDWI_2DF },
9605 { MASK_VSX, CODE_FOR_vsx_xxsldwi_v4sf, "__builtin_vsx_xxsldwi_4sf", VSX_BUILTIN_XXSLDWI_4SF },
9606 { MASK_VSX, CODE_FOR_vsx_xxsldwi_v4si, "__builtin_vsx_xxsldwi_4si", VSX_BUILTIN_XXSLDWI_4SI },
9607 { MASK_VSX, CODE_FOR_vsx_xxsldwi_v8hi, "__builtin_vsx_xxsldwi_8hi", VSX_BUILTIN_XXSLDWI_8HI },
9608 { MASK_VSX, CODE_FOR_vsx_xxsldwi_v16qi, "__builtin_vsx_xxsldwi_16qi", VSX_BUILTIN_XXSLDWI_16QI },
9609 { MASK_VSX, CODE_FOR_nothing, "__builtin_vsx_xxsldwi", VSX_BUILTIN_VEC_XXSLDWI },
9610
9611 { 0, CODE_FOR_paired_msub, "__builtin_paired_msub", PAIRED_BUILTIN_MSUB },
9612 { 0, CODE_FOR_paired_madd, "__builtin_paired_madd", PAIRED_BUILTIN_MADD },
9613 { 0, CODE_FOR_paired_madds0, "__builtin_paired_madds0", PAIRED_BUILTIN_MADDS0 },
9614 { 0, CODE_FOR_paired_madds1, "__builtin_paired_madds1", PAIRED_BUILTIN_MADDS1 },
9615 { 0, CODE_FOR_paired_nmsub, "__builtin_paired_nmsub", PAIRED_BUILTIN_NMSUB },
9616 { 0, CODE_FOR_paired_nmadd, "__builtin_paired_nmadd", PAIRED_BUILTIN_NMADD },
9617 { 0, CODE_FOR_paired_sum0, "__builtin_paired_sum0", PAIRED_BUILTIN_SUM0 },
9618 { 0, CODE_FOR_paired_sum1, "__builtin_paired_sum1", PAIRED_BUILTIN_SUM1 },
9619 { 0, CODE_FOR_selv2sf4, "__builtin_paired_selv2sf4", PAIRED_BUILTIN_SELV2SF4 },
9620 };
9621
9622 /* DST operations: void foo (void *, const int, const char). */
9623
9624 static const struct builtin_description bdesc_dst[] =
9625 {
9626 { MASK_ALTIVEC, CODE_FOR_altivec_dst, "__builtin_altivec_dst", ALTIVEC_BUILTIN_DST },
9627 { MASK_ALTIVEC, CODE_FOR_altivec_dstt, "__builtin_altivec_dstt", ALTIVEC_BUILTIN_DSTT },
9628 { MASK_ALTIVEC, CODE_FOR_altivec_dstst, "__builtin_altivec_dstst", ALTIVEC_BUILTIN_DSTST },
9629 { MASK_ALTIVEC, CODE_FOR_altivec_dststt, "__builtin_altivec_dststt", ALTIVEC_BUILTIN_DSTSTT },
9630
9631 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_dst", ALTIVEC_BUILTIN_VEC_DST },
9632 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_dstt", ALTIVEC_BUILTIN_VEC_DSTT },
9633 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_dstst", ALTIVEC_BUILTIN_VEC_DSTST },
9634 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_dststt", ALTIVEC_BUILTIN_VEC_DSTSTT }
9635 };
9636
9637 /* Simple binary operations: VECc = foo (VECa, VECb). */
9638
9639 static struct builtin_description bdesc_2arg[] =
9640 {
9641 { MASK_ALTIVEC, CODE_FOR_addv16qi3, "__builtin_altivec_vaddubm", ALTIVEC_BUILTIN_VADDUBM },
9642 { MASK_ALTIVEC, CODE_FOR_addv8hi3, "__builtin_altivec_vadduhm", ALTIVEC_BUILTIN_VADDUHM },
9643 { MASK_ALTIVEC, CODE_FOR_addv4si3, "__builtin_altivec_vadduwm", ALTIVEC_BUILTIN_VADDUWM },
9644 { MASK_ALTIVEC, CODE_FOR_addv4sf3, "__builtin_altivec_vaddfp", ALTIVEC_BUILTIN_VADDFP },
9645 { MASK_ALTIVEC, CODE_FOR_altivec_vaddcuw, "__builtin_altivec_vaddcuw", ALTIVEC_BUILTIN_VADDCUW },
9646 { MASK_ALTIVEC, CODE_FOR_altivec_vaddubs, "__builtin_altivec_vaddubs", ALTIVEC_BUILTIN_VADDUBS },
9647 { MASK_ALTIVEC, CODE_FOR_altivec_vaddsbs, "__builtin_altivec_vaddsbs", ALTIVEC_BUILTIN_VADDSBS },
9648 { MASK_ALTIVEC, CODE_FOR_altivec_vadduhs, "__builtin_altivec_vadduhs", ALTIVEC_BUILTIN_VADDUHS },
9649 { MASK_ALTIVEC, CODE_FOR_altivec_vaddshs, "__builtin_altivec_vaddshs", ALTIVEC_BUILTIN_VADDSHS },
9650 { MASK_ALTIVEC, CODE_FOR_altivec_vadduws, "__builtin_altivec_vadduws", ALTIVEC_BUILTIN_VADDUWS },
9651 { MASK_ALTIVEC, CODE_FOR_altivec_vaddsws, "__builtin_altivec_vaddsws", ALTIVEC_BUILTIN_VADDSWS },
9652 { MASK_ALTIVEC, CODE_FOR_andv4si3, "__builtin_altivec_vand", ALTIVEC_BUILTIN_VAND },
9653 { MASK_ALTIVEC, CODE_FOR_andcv4si3, "__builtin_altivec_vandc", ALTIVEC_BUILTIN_VANDC },
9654 { MASK_ALTIVEC, CODE_FOR_altivec_vavgub, "__builtin_altivec_vavgub", ALTIVEC_BUILTIN_VAVGUB },
9655 { MASK_ALTIVEC, CODE_FOR_altivec_vavgsb, "__builtin_altivec_vavgsb", ALTIVEC_BUILTIN_VAVGSB },
9656 { MASK_ALTIVEC, CODE_FOR_altivec_vavguh, "__builtin_altivec_vavguh", ALTIVEC_BUILTIN_VAVGUH },
9657 { MASK_ALTIVEC, CODE_FOR_altivec_vavgsh, "__builtin_altivec_vavgsh", ALTIVEC_BUILTIN_VAVGSH },
9658 { MASK_ALTIVEC, CODE_FOR_altivec_vavguw, "__builtin_altivec_vavguw", ALTIVEC_BUILTIN_VAVGUW },
9659 { MASK_ALTIVEC, CODE_FOR_altivec_vavgsw, "__builtin_altivec_vavgsw", ALTIVEC_BUILTIN_VAVGSW },
9660 { MASK_ALTIVEC, CODE_FOR_altivec_vcfux, "__builtin_altivec_vcfux", ALTIVEC_BUILTIN_VCFUX },
9661 { MASK_ALTIVEC, CODE_FOR_altivec_vcfsx, "__builtin_altivec_vcfsx", ALTIVEC_BUILTIN_VCFSX },
9662 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpbfp, "__builtin_altivec_vcmpbfp", ALTIVEC_BUILTIN_VCMPBFP },
9663 { MASK_ALTIVEC, CODE_FOR_vector_eqv16qi, "__builtin_altivec_vcmpequb", ALTIVEC_BUILTIN_VCMPEQUB },
9664 { MASK_ALTIVEC, CODE_FOR_vector_eqv8hi, "__builtin_altivec_vcmpequh", ALTIVEC_BUILTIN_VCMPEQUH },
9665 { MASK_ALTIVEC, CODE_FOR_vector_eqv4si, "__builtin_altivec_vcmpequw", ALTIVEC_BUILTIN_VCMPEQUW },
9666 { MASK_ALTIVEC, CODE_FOR_vector_eqv4sf, "__builtin_altivec_vcmpeqfp", ALTIVEC_BUILTIN_VCMPEQFP },
9667 { MASK_ALTIVEC, CODE_FOR_vector_gev4sf, "__builtin_altivec_vcmpgefp", ALTIVEC_BUILTIN_VCMPGEFP },
9668 { MASK_ALTIVEC, CODE_FOR_vector_gtuv16qi, "__builtin_altivec_vcmpgtub", ALTIVEC_BUILTIN_VCMPGTUB },
9669 { MASK_ALTIVEC, CODE_FOR_vector_gtv16qi, "__builtin_altivec_vcmpgtsb", ALTIVEC_BUILTIN_VCMPGTSB },
9670 { MASK_ALTIVEC, CODE_FOR_vector_gtuv8hi, "__builtin_altivec_vcmpgtuh", ALTIVEC_BUILTIN_VCMPGTUH },
9671 { MASK_ALTIVEC, CODE_FOR_vector_gtv8hi, "__builtin_altivec_vcmpgtsh", ALTIVEC_BUILTIN_VCMPGTSH },
9672 { MASK_ALTIVEC, CODE_FOR_vector_gtuv4si, "__builtin_altivec_vcmpgtuw", ALTIVEC_BUILTIN_VCMPGTUW },
9673 { MASK_ALTIVEC, CODE_FOR_vector_gtv4si, "__builtin_altivec_vcmpgtsw", ALTIVEC_BUILTIN_VCMPGTSW },
9674 { MASK_ALTIVEC, CODE_FOR_vector_gtv4sf, "__builtin_altivec_vcmpgtfp", ALTIVEC_BUILTIN_VCMPGTFP },
9675 { MASK_ALTIVEC, CODE_FOR_altivec_vctsxs, "__builtin_altivec_vctsxs", ALTIVEC_BUILTIN_VCTSXS },
9676 { MASK_ALTIVEC, CODE_FOR_altivec_vctuxs, "__builtin_altivec_vctuxs", ALTIVEC_BUILTIN_VCTUXS },
9677 { MASK_ALTIVEC, CODE_FOR_umaxv16qi3, "__builtin_altivec_vmaxub", ALTIVEC_BUILTIN_VMAXUB },
9678 { MASK_ALTIVEC, CODE_FOR_smaxv16qi3, "__builtin_altivec_vmaxsb", ALTIVEC_BUILTIN_VMAXSB },
9679 { MASK_ALTIVEC, CODE_FOR_umaxv8hi3, "__builtin_altivec_vmaxuh", ALTIVEC_BUILTIN_VMAXUH },
9680 { MASK_ALTIVEC, CODE_FOR_smaxv8hi3, "__builtin_altivec_vmaxsh", ALTIVEC_BUILTIN_VMAXSH },
9681 { MASK_ALTIVEC, CODE_FOR_umaxv4si3, "__builtin_altivec_vmaxuw", ALTIVEC_BUILTIN_VMAXUW },
9682 { MASK_ALTIVEC, CODE_FOR_smaxv4si3, "__builtin_altivec_vmaxsw", ALTIVEC_BUILTIN_VMAXSW },
9683 { MASK_ALTIVEC, CODE_FOR_smaxv4sf3, "__builtin_altivec_vmaxfp", ALTIVEC_BUILTIN_VMAXFP },
9684 { MASK_ALTIVEC, CODE_FOR_altivec_vmrghb, "__builtin_altivec_vmrghb", ALTIVEC_BUILTIN_VMRGHB },
9685 { MASK_ALTIVEC, CODE_FOR_altivec_vmrghh, "__builtin_altivec_vmrghh", ALTIVEC_BUILTIN_VMRGHH },
9686 { MASK_ALTIVEC, CODE_FOR_altivec_vmrghw, "__builtin_altivec_vmrghw", ALTIVEC_BUILTIN_VMRGHW },
9687 { MASK_ALTIVEC, CODE_FOR_altivec_vmrglb, "__builtin_altivec_vmrglb", ALTIVEC_BUILTIN_VMRGLB },
9688 { MASK_ALTIVEC, CODE_FOR_altivec_vmrglh, "__builtin_altivec_vmrglh", ALTIVEC_BUILTIN_VMRGLH },
9689 { MASK_ALTIVEC, CODE_FOR_altivec_vmrglw, "__builtin_altivec_vmrglw", ALTIVEC_BUILTIN_VMRGLW },
9690 { MASK_ALTIVEC, CODE_FOR_uminv16qi3, "__builtin_altivec_vminub", ALTIVEC_BUILTIN_VMINUB },
9691 { MASK_ALTIVEC, CODE_FOR_sminv16qi3, "__builtin_altivec_vminsb", ALTIVEC_BUILTIN_VMINSB },
9692 { MASK_ALTIVEC, CODE_FOR_uminv8hi3, "__builtin_altivec_vminuh", ALTIVEC_BUILTIN_VMINUH },
9693 { MASK_ALTIVEC, CODE_FOR_sminv8hi3, "__builtin_altivec_vminsh", ALTIVEC_BUILTIN_VMINSH },
9694 { MASK_ALTIVEC, CODE_FOR_uminv4si3, "__builtin_altivec_vminuw", ALTIVEC_BUILTIN_VMINUW },
9695 { MASK_ALTIVEC, CODE_FOR_sminv4si3, "__builtin_altivec_vminsw", ALTIVEC_BUILTIN_VMINSW },
9696 { MASK_ALTIVEC, CODE_FOR_sminv4sf3, "__builtin_altivec_vminfp", ALTIVEC_BUILTIN_VMINFP },
9697 { MASK_ALTIVEC, CODE_FOR_altivec_vmuleub, "__builtin_altivec_vmuleub", ALTIVEC_BUILTIN_VMULEUB },
9698 { MASK_ALTIVEC, CODE_FOR_altivec_vmuleub, "__builtin_altivec_vmuleub_uns", ALTIVEC_BUILTIN_VMULEUB_UNS },
9699 { MASK_ALTIVEC, CODE_FOR_altivec_vmulesb, "__builtin_altivec_vmulesb", ALTIVEC_BUILTIN_VMULESB },
9700 { MASK_ALTIVEC, CODE_FOR_altivec_vmuleuh, "__builtin_altivec_vmuleuh", ALTIVEC_BUILTIN_VMULEUH },
9701 { MASK_ALTIVEC, CODE_FOR_altivec_vmuleuh, "__builtin_altivec_vmuleuh_uns", ALTIVEC_BUILTIN_VMULEUH_UNS },
9702 { MASK_ALTIVEC, CODE_FOR_altivec_vmulesh, "__builtin_altivec_vmulesh", ALTIVEC_BUILTIN_VMULESH },
9703 { MASK_ALTIVEC, CODE_FOR_altivec_vmuloub, "__builtin_altivec_vmuloub", ALTIVEC_BUILTIN_VMULOUB },
9704 { MASK_ALTIVEC, CODE_FOR_altivec_vmuloub, "__builtin_altivec_vmuloub_uns", ALTIVEC_BUILTIN_VMULOUB_UNS },
9705 { MASK_ALTIVEC, CODE_FOR_altivec_vmulosb, "__builtin_altivec_vmulosb", ALTIVEC_BUILTIN_VMULOSB },
9706 { MASK_ALTIVEC, CODE_FOR_altivec_vmulouh, "__builtin_altivec_vmulouh", ALTIVEC_BUILTIN_VMULOUH },
9707 { MASK_ALTIVEC, CODE_FOR_altivec_vmulouh, "__builtin_altivec_vmulouh_uns", ALTIVEC_BUILTIN_VMULOUH_UNS },
9708 { MASK_ALTIVEC, CODE_FOR_altivec_vmulosh, "__builtin_altivec_vmulosh", ALTIVEC_BUILTIN_VMULOSH },
9709 { MASK_ALTIVEC, CODE_FOR_norv4si3, "__builtin_altivec_vnor", ALTIVEC_BUILTIN_VNOR },
9710 { MASK_ALTIVEC, CODE_FOR_iorv4si3, "__builtin_altivec_vor", ALTIVEC_BUILTIN_VOR },
9711 { MASK_ALTIVEC, CODE_FOR_altivec_vpkuhum, "__builtin_altivec_vpkuhum", ALTIVEC_BUILTIN_VPKUHUM },
9712 { MASK_ALTIVEC, CODE_FOR_altivec_vpkuwum, "__builtin_altivec_vpkuwum", ALTIVEC_BUILTIN_VPKUWUM },
9713 { MASK_ALTIVEC, CODE_FOR_altivec_vpkpx, "__builtin_altivec_vpkpx", ALTIVEC_BUILTIN_VPKPX },
9714 { MASK_ALTIVEC, CODE_FOR_altivec_vpkshss, "__builtin_altivec_vpkshss", ALTIVEC_BUILTIN_VPKSHSS },
9715 { MASK_ALTIVEC, CODE_FOR_altivec_vpkswss, "__builtin_altivec_vpkswss", ALTIVEC_BUILTIN_VPKSWSS },
9716 { MASK_ALTIVEC, CODE_FOR_altivec_vpkuhus, "__builtin_altivec_vpkuhus", ALTIVEC_BUILTIN_VPKUHUS },
9717 { MASK_ALTIVEC, CODE_FOR_altivec_vpkshus, "__builtin_altivec_vpkshus", ALTIVEC_BUILTIN_VPKSHUS },
9718 { MASK_ALTIVEC, CODE_FOR_altivec_vpkuwus, "__builtin_altivec_vpkuwus", ALTIVEC_BUILTIN_VPKUWUS },
9719 { MASK_ALTIVEC, CODE_FOR_altivec_vpkswus, "__builtin_altivec_vpkswus", ALTIVEC_BUILTIN_VPKSWUS },
9720 { MASK_ALTIVEC, CODE_FOR_recipv4sf3, "__builtin_altivec_vrecipdivfp", ALTIVEC_BUILTIN_VRECIPFP },
9721 { MASK_ALTIVEC, CODE_FOR_vrotlv16qi3, "__builtin_altivec_vrlb", ALTIVEC_BUILTIN_VRLB },
9722 { MASK_ALTIVEC, CODE_FOR_vrotlv8hi3, "__builtin_altivec_vrlh", ALTIVEC_BUILTIN_VRLH },
9723 { MASK_ALTIVEC, CODE_FOR_vrotlv4si3, "__builtin_altivec_vrlw", ALTIVEC_BUILTIN_VRLW },
9724 { MASK_ALTIVEC, CODE_FOR_vashlv16qi3, "__builtin_altivec_vslb", ALTIVEC_BUILTIN_VSLB },
9725 { MASK_ALTIVEC, CODE_FOR_vashlv8hi3, "__builtin_altivec_vslh", ALTIVEC_BUILTIN_VSLH },
9726 { MASK_ALTIVEC, CODE_FOR_vashlv4si3, "__builtin_altivec_vslw", ALTIVEC_BUILTIN_VSLW },
9727 { MASK_ALTIVEC, CODE_FOR_altivec_vsl, "__builtin_altivec_vsl", ALTIVEC_BUILTIN_VSL },
9728 { MASK_ALTIVEC, CODE_FOR_altivec_vslo, "__builtin_altivec_vslo", ALTIVEC_BUILTIN_VSLO },
9729 { MASK_ALTIVEC, CODE_FOR_altivec_vspltb, "__builtin_altivec_vspltb", ALTIVEC_BUILTIN_VSPLTB },
9730 { MASK_ALTIVEC, CODE_FOR_altivec_vsplth, "__builtin_altivec_vsplth", ALTIVEC_BUILTIN_VSPLTH },
9731 { MASK_ALTIVEC, CODE_FOR_altivec_vspltw, "__builtin_altivec_vspltw", ALTIVEC_BUILTIN_VSPLTW },
9732 { MASK_ALTIVEC, CODE_FOR_vlshrv16qi3, "__builtin_altivec_vsrb", ALTIVEC_BUILTIN_VSRB },
9733 { MASK_ALTIVEC, CODE_FOR_vlshrv8hi3, "__builtin_altivec_vsrh", ALTIVEC_BUILTIN_VSRH },
9734 { MASK_ALTIVEC, CODE_FOR_vlshrv4si3, "__builtin_altivec_vsrw", ALTIVEC_BUILTIN_VSRW },
9735 { MASK_ALTIVEC, CODE_FOR_vashrv16qi3, "__builtin_altivec_vsrab", ALTIVEC_BUILTIN_VSRAB },
9736 { MASK_ALTIVEC, CODE_FOR_vashrv8hi3, "__builtin_altivec_vsrah", ALTIVEC_BUILTIN_VSRAH },
9737 { MASK_ALTIVEC, CODE_FOR_vashrv4si3, "__builtin_altivec_vsraw", ALTIVEC_BUILTIN_VSRAW },
9738 { MASK_ALTIVEC, CODE_FOR_altivec_vsr, "__builtin_altivec_vsr", ALTIVEC_BUILTIN_VSR },
9739 { MASK_ALTIVEC, CODE_FOR_altivec_vsro, "__builtin_altivec_vsro", ALTIVEC_BUILTIN_VSRO },
9740 { MASK_ALTIVEC, CODE_FOR_subv16qi3, "__builtin_altivec_vsububm", ALTIVEC_BUILTIN_VSUBUBM },
9741 { MASK_ALTIVEC, CODE_FOR_subv8hi3, "__builtin_altivec_vsubuhm", ALTIVEC_BUILTIN_VSUBUHM },
9742 { MASK_ALTIVEC, CODE_FOR_subv4si3, "__builtin_altivec_vsubuwm", ALTIVEC_BUILTIN_VSUBUWM },
9743 { MASK_ALTIVEC, CODE_FOR_subv4sf3, "__builtin_altivec_vsubfp", ALTIVEC_BUILTIN_VSUBFP },
9744 { MASK_ALTIVEC, CODE_FOR_altivec_vsubcuw, "__builtin_altivec_vsubcuw", ALTIVEC_BUILTIN_VSUBCUW },
9745 { MASK_ALTIVEC, CODE_FOR_altivec_vsububs, "__builtin_altivec_vsububs", ALTIVEC_BUILTIN_VSUBUBS },
9746 { MASK_ALTIVEC, CODE_FOR_altivec_vsubsbs, "__builtin_altivec_vsubsbs", ALTIVEC_BUILTIN_VSUBSBS },
9747 { MASK_ALTIVEC, CODE_FOR_altivec_vsubuhs, "__builtin_altivec_vsubuhs", ALTIVEC_BUILTIN_VSUBUHS },
9748 { MASK_ALTIVEC, CODE_FOR_altivec_vsubshs, "__builtin_altivec_vsubshs", ALTIVEC_BUILTIN_VSUBSHS },
9749 { MASK_ALTIVEC, CODE_FOR_altivec_vsubuws, "__builtin_altivec_vsubuws", ALTIVEC_BUILTIN_VSUBUWS },
9750 { MASK_ALTIVEC, CODE_FOR_altivec_vsubsws, "__builtin_altivec_vsubsws", ALTIVEC_BUILTIN_VSUBSWS },
9751 { MASK_ALTIVEC, CODE_FOR_altivec_vsum4ubs, "__builtin_altivec_vsum4ubs", ALTIVEC_BUILTIN_VSUM4UBS },
9752 { MASK_ALTIVEC, CODE_FOR_altivec_vsum4sbs, "__builtin_altivec_vsum4sbs", ALTIVEC_BUILTIN_VSUM4SBS },
9753 { MASK_ALTIVEC, CODE_FOR_altivec_vsum4shs, "__builtin_altivec_vsum4shs", ALTIVEC_BUILTIN_VSUM4SHS },
9754 { MASK_ALTIVEC, CODE_FOR_altivec_vsum2sws, "__builtin_altivec_vsum2sws", ALTIVEC_BUILTIN_VSUM2SWS },
9755 { MASK_ALTIVEC, CODE_FOR_altivec_vsumsws, "__builtin_altivec_vsumsws", ALTIVEC_BUILTIN_VSUMSWS },
9756 { MASK_ALTIVEC, CODE_FOR_xorv4si3, "__builtin_altivec_vxor", ALTIVEC_BUILTIN_VXOR },
9757 { MASK_ALTIVEC, CODE_FOR_vector_copysignv4sf3, "__builtin_altivec_copysignfp", ALTIVEC_BUILTIN_COPYSIGN_V4SF },
9758
9759 { MASK_VSX, CODE_FOR_addv2df3, "__builtin_vsx_xvadddp", VSX_BUILTIN_XVADDDP },
9760 { MASK_VSX, CODE_FOR_subv2df3, "__builtin_vsx_xvsubdp", VSX_BUILTIN_XVSUBDP },
9761 { MASK_VSX, CODE_FOR_mulv2df3, "__builtin_vsx_xvmuldp", VSX_BUILTIN_XVMULDP },
9762 { MASK_VSX, CODE_FOR_divv2df3, "__builtin_vsx_xvdivdp", VSX_BUILTIN_XVDIVDP },
9763 { MASK_VSX, CODE_FOR_recipv2df3, "__builtin_vsx_xvrecipdivdp", VSX_BUILTIN_RECIP_V2DF },
9764 { MASK_VSX, CODE_FOR_sminv2df3, "__builtin_vsx_xvmindp", VSX_BUILTIN_XVMINDP },
9765 { MASK_VSX, CODE_FOR_smaxv2df3, "__builtin_vsx_xvmaxdp", VSX_BUILTIN_XVMAXDP },
9766 { MASK_VSX, CODE_FOR_vsx_tdivv2df3_fe, "__builtin_vsx_xvtdivdp_fe", VSX_BUILTIN_XVTDIVDP_FE },
9767 { MASK_VSX, CODE_FOR_vsx_tdivv2df3_fg, "__builtin_vsx_xvtdivdp_fg", VSX_BUILTIN_XVTDIVDP_FG },
9768 { MASK_VSX, CODE_FOR_vector_eqv2df, "__builtin_vsx_xvcmpeqdp", VSX_BUILTIN_XVCMPEQDP },
9769 { MASK_VSX, CODE_FOR_vector_gtv2df, "__builtin_vsx_xvcmpgtdp", VSX_BUILTIN_XVCMPGTDP },
9770 { MASK_VSX, CODE_FOR_vector_gev2df, "__builtin_vsx_xvcmpgedp", VSX_BUILTIN_XVCMPGEDP },
9771
9772 { MASK_VSX, CODE_FOR_addv4sf3, "__builtin_vsx_xvaddsp", VSX_BUILTIN_XVADDSP },
9773 { MASK_VSX, CODE_FOR_subv4sf3, "__builtin_vsx_xvsubsp", VSX_BUILTIN_XVSUBSP },
9774 { MASK_VSX, CODE_FOR_mulv4sf3, "__builtin_vsx_xvmulsp", VSX_BUILTIN_XVMULSP },
9775 { MASK_VSX, CODE_FOR_divv4sf3, "__builtin_vsx_xvdivsp", VSX_BUILTIN_XVDIVSP },
9776 { MASK_VSX, CODE_FOR_recipv4sf3, "__builtin_vsx_xvrecipdivsp", VSX_BUILTIN_RECIP_V4SF },
9777 { MASK_VSX, CODE_FOR_sminv4sf3, "__builtin_vsx_xvminsp", VSX_BUILTIN_XVMINSP },
9778 { MASK_VSX, CODE_FOR_smaxv4sf3, "__builtin_vsx_xvmaxsp", VSX_BUILTIN_XVMAXSP },
9779 { MASK_VSX, CODE_FOR_vsx_tdivv4sf3_fe, "__builtin_vsx_xvtdivsp_fe", VSX_BUILTIN_XVTDIVSP_FE },
9780 { MASK_VSX, CODE_FOR_vsx_tdivv4sf3_fg, "__builtin_vsx_xvtdivsp_fg", VSX_BUILTIN_XVTDIVSP_FG },
9781 { MASK_VSX, CODE_FOR_vector_eqv4sf, "__builtin_vsx_xvcmpeqsp", VSX_BUILTIN_XVCMPEQSP },
9782 { MASK_VSX, CODE_FOR_vector_gtv4sf, "__builtin_vsx_xvcmpgtsp", VSX_BUILTIN_XVCMPGTSP },
9783 { MASK_VSX, CODE_FOR_vector_gev4sf, "__builtin_vsx_xvcmpgesp", VSX_BUILTIN_XVCMPGESP },
9784
9785 { MASK_VSX, CODE_FOR_smindf3, "__builtin_vsx_xsmindp", VSX_BUILTIN_XSMINDP },
9786 { MASK_VSX, CODE_FOR_smaxdf3, "__builtin_vsx_xsmaxdp", VSX_BUILTIN_XSMAXDP },
9787 { MASK_VSX, CODE_FOR_vsx_tdivdf3_fe, "__builtin_vsx_xstdivdp_fe", VSX_BUILTIN_XSTDIVDP_FE },
9788 { MASK_VSX, CODE_FOR_vsx_tdivdf3_fg, "__builtin_vsx_xstdivdp_fg", VSX_BUILTIN_XSTDIVDP_FG },
9789 { MASK_VSX, CODE_FOR_vector_copysignv2df3, "__builtin_vsx_cpsgndp", VSX_BUILTIN_CPSGNDP },
9790 { MASK_VSX, CODE_FOR_vector_copysignv4sf3, "__builtin_vsx_cpsgnsp", VSX_BUILTIN_CPSGNSP },
9791
9792 { MASK_VSX, CODE_FOR_vsx_concat_v2df, "__builtin_vsx_concat_2df", VSX_BUILTIN_CONCAT_2DF },
9793 { MASK_VSX, CODE_FOR_vsx_concat_v2di, "__builtin_vsx_concat_2di", VSX_BUILTIN_CONCAT_2DI },
9794 { MASK_VSX, CODE_FOR_vsx_splat_v2df, "__builtin_vsx_splat_2df", VSX_BUILTIN_SPLAT_2DF },
9795 { MASK_VSX, CODE_FOR_vsx_splat_v2di, "__builtin_vsx_splat_2di", VSX_BUILTIN_SPLAT_2DI },
9796 { MASK_VSX, CODE_FOR_vsx_xxmrghw_v4sf, "__builtin_vsx_xxmrghw", VSX_BUILTIN_XXMRGHW_4SF },
9797 { MASK_VSX, CODE_FOR_vsx_xxmrghw_v4si, "__builtin_vsx_xxmrghw_4si", VSX_BUILTIN_XXMRGHW_4SI },
9798 { MASK_VSX, CODE_FOR_vsx_xxmrglw_v4sf, "__builtin_vsx_xxmrglw", VSX_BUILTIN_XXMRGLW_4SF },
9799 { MASK_VSX, CODE_FOR_vsx_xxmrglw_v4si, "__builtin_vsx_xxmrglw_4si", VSX_BUILTIN_XXMRGLW_4SI },
9800 { MASK_VSX, CODE_FOR_vec_interleave_lowv2df, "__builtin_vsx_mergel_2df", VSX_BUILTIN_VEC_MERGEL_V2DF },
9801 { MASK_VSX, CODE_FOR_vec_interleave_lowv2di, "__builtin_vsx_mergel_2di", VSX_BUILTIN_VEC_MERGEL_V2DI },
9802 { MASK_VSX, CODE_FOR_vec_interleave_highv2df, "__builtin_vsx_mergeh_2df", VSX_BUILTIN_VEC_MERGEH_V2DF },
9803 { MASK_VSX, CODE_FOR_vec_interleave_highv2di, "__builtin_vsx_mergeh_2di", VSX_BUILTIN_VEC_MERGEH_V2DI },
9804
9805 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_add", ALTIVEC_BUILTIN_VEC_ADD },
9806 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_vaddfp", ALTIVEC_BUILTIN_VEC_VADDFP },
9807 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vadduwm", ALTIVEC_BUILTIN_VEC_VADDUWM },
9808 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vadduhm", ALTIVEC_BUILTIN_VEC_VADDUHM },
9809 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vaddubm", ALTIVEC_BUILTIN_VEC_VADDUBM },
9810 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_addc", ALTIVEC_BUILTIN_VEC_ADDC },
9811 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_adds", ALTIVEC_BUILTIN_VEC_ADDS },
9812 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vaddsws", ALTIVEC_BUILTIN_VEC_VADDSWS },
9813 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vadduws", ALTIVEC_BUILTIN_VEC_VADDUWS },
9814 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vaddshs", ALTIVEC_BUILTIN_VEC_VADDSHS },
9815 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vadduhs", ALTIVEC_BUILTIN_VEC_VADDUHS },
9816 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vaddsbs", ALTIVEC_BUILTIN_VEC_VADDSBS },
9817 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vaddubs", ALTIVEC_BUILTIN_VEC_VADDUBS },
9818 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_and", ALTIVEC_BUILTIN_VEC_AND },
9819 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_andc", ALTIVEC_BUILTIN_VEC_ANDC },
9820 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_avg", ALTIVEC_BUILTIN_VEC_AVG },
9821 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vavgsw", ALTIVEC_BUILTIN_VEC_VAVGSW },
9822 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vavguw", ALTIVEC_BUILTIN_VEC_VAVGUW },
9823 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vavgsh", ALTIVEC_BUILTIN_VEC_VAVGSH },
9824 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vavguh", ALTIVEC_BUILTIN_VEC_VAVGUH },
9825 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vavgsb", ALTIVEC_BUILTIN_VEC_VAVGSB },
9826 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vavgub", ALTIVEC_BUILTIN_VEC_VAVGUB },
9827 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_cmpb", ALTIVEC_BUILTIN_VEC_CMPB },
9828 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_cmpeq", ALTIVEC_BUILTIN_VEC_CMPEQ },
9829 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpeqfp", ALTIVEC_BUILTIN_VEC_VCMPEQFP },
9830 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpequw", ALTIVEC_BUILTIN_VEC_VCMPEQUW },
9831 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpequh", ALTIVEC_BUILTIN_VEC_VCMPEQUH },
9832 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpequb", ALTIVEC_BUILTIN_VEC_VCMPEQUB },
9833 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_cmpge", ALTIVEC_BUILTIN_VEC_CMPGE },
9834 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_cmpgt", ALTIVEC_BUILTIN_VEC_CMPGT },
9835 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtfp", ALTIVEC_BUILTIN_VEC_VCMPGTFP },
9836 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtsw", ALTIVEC_BUILTIN_VEC_VCMPGTSW },
9837 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtuw", ALTIVEC_BUILTIN_VEC_VCMPGTUW },
9838 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtsh", ALTIVEC_BUILTIN_VEC_VCMPGTSH },
9839 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtuh", ALTIVEC_BUILTIN_VEC_VCMPGTUH },
9840 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtsb", ALTIVEC_BUILTIN_VEC_VCMPGTSB },
9841 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vcmpgtub", ALTIVEC_BUILTIN_VEC_VCMPGTUB },
9842 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_cmple", ALTIVEC_BUILTIN_VEC_CMPLE },
9843 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_cmplt", ALTIVEC_BUILTIN_VEC_CMPLT },
9844 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_copysign", ALTIVEC_BUILTIN_VEC_COPYSIGN },
9845 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_max", ALTIVEC_BUILTIN_VEC_MAX },
9846 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_vmaxfp", ALTIVEC_BUILTIN_VEC_VMAXFP },
9847 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxsw", ALTIVEC_BUILTIN_VEC_VMAXSW },
9848 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxuw", ALTIVEC_BUILTIN_VEC_VMAXUW },
9849 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxsh", ALTIVEC_BUILTIN_VEC_VMAXSH },
9850 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxuh", ALTIVEC_BUILTIN_VEC_VMAXUH },
9851 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxsb", ALTIVEC_BUILTIN_VEC_VMAXSB },
9852 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmaxub", ALTIVEC_BUILTIN_VEC_VMAXUB },
9853 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mergeh", ALTIVEC_BUILTIN_VEC_MERGEH },
9854 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmrghw", ALTIVEC_BUILTIN_VEC_VMRGHW },
9855 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmrghh", ALTIVEC_BUILTIN_VEC_VMRGHH },
9856 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmrghb", ALTIVEC_BUILTIN_VEC_VMRGHB },
9857 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mergel", ALTIVEC_BUILTIN_VEC_MERGEL },
9858 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmrglw", ALTIVEC_BUILTIN_VEC_VMRGLW },
9859 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmrglh", ALTIVEC_BUILTIN_VEC_VMRGLH },
9860 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmrglb", ALTIVEC_BUILTIN_VEC_VMRGLB },
9861 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_min", ALTIVEC_BUILTIN_VEC_MIN },
9862 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_vminfp", ALTIVEC_BUILTIN_VEC_VMINFP },
9863 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminsw", ALTIVEC_BUILTIN_VEC_VMINSW },
9864 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminuw", ALTIVEC_BUILTIN_VEC_VMINUW },
9865 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminsh", ALTIVEC_BUILTIN_VEC_VMINSH },
9866 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminuh", ALTIVEC_BUILTIN_VEC_VMINUH },
9867 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminsb", ALTIVEC_BUILTIN_VEC_VMINSB },
9868 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vminub", ALTIVEC_BUILTIN_VEC_VMINUB },
9869 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mule", ALTIVEC_BUILTIN_VEC_MULE },
9870 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmuleub", ALTIVEC_BUILTIN_VEC_VMULEUB },
9871 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmulesb", ALTIVEC_BUILTIN_VEC_VMULESB },
9872 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmuleuh", ALTIVEC_BUILTIN_VEC_VMULEUH },
9873 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmulesh", ALTIVEC_BUILTIN_VEC_VMULESH },
9874 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mulo", ALTIVEC_BUILTIN_VEC_MULO },
9875 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmulosh", ALTIVEC_BUILTIN_VEC_VMULOSH },
9876 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmulouh", ALTIVEC_BUILTIN_VEC_VMULOUH },
9877 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmulosb", ALTIVEC_BUILTIN_VEC_VMULOSB },
9878 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vmuloub", ALTIVEC_BUILTIN_VEC_VMULOUB },
9879 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_nor", ALTIVEC_BUILTIN_VEC_NOR },
9880 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_or", ALTIVEC_BUILTIN_VEC_OR },
9881 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_pack", ALTIVEC_BUILTIN_VEC_PACK },
9882 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkuwum", ALTIVEC_BUILTIN_VEC_VPKUWUM },
9883 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkuhum", ALTIVEC_BUILTIN_VEC_VPKUHUM },
9884 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_packpx", ALTIVEC_BUILTIN_VEC_PACKPX },
9885 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_packs", ALTIVEC_BUILTIN_VEC_PACKS },
9886 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkswss", ALTIVEC_BUILTIN_VEC_VPKSWSS },
9887 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkuwus", ALTIVEC_BUILTIN_VEC_VPKUWUS },
9888 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkshss", ALTIVEC_BUILTIN_VEC_VPKSHSS },
9889 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkuhus", ALTIVEC_BUILTIN_VEC_VPKUHUS },
9890 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_packsu", ALTIVEC_BUILTIN_VEC_PACKSU },
9891 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkswus", ALTIVEC_BUILTIN_VEC_VPKSWUS },
9892 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vpkshus", ALTIVEC_BUILTIN_VEC_VPKSHUS },
9893 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_recipdiv", ALTIVEC_BUILTIN_VEC_RECIP },
9894 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_rl", ALTIVEC_BUILTIN_VEC_RL },
9895 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vrlw", ALTIVEC_BUILTIN_VEC_VRLW },
9896 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vrlh", ALTIVEC_BUILTIN_VEC_VRLH },
9897 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vrlb", ALTIVEC_BUILTIN_VEC_VRLB },
9898 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sl", ALTIVEC_BUILTIN_VEC_SL },
9899 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vslw", ALTIVEC_BUILTIN_VEC_VSLW },
9900 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vslh", ALTIVEC_BUILTIN_VEC_VSLH },
9901 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vslb", ALTIVEC_BUILTIN_VEC_VSLB },
9902 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sll", ALTIVEC_BUILTIN_VEC_SLL },
9903 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_slo", ALTIVEC_BUILTIN_VEC_SLO },
9904 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sr", ALTIVEC_BUILTIN_VEC_SR },
9905 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsrw", ALTIVEC_BUILTIN_VEC_VSRW },
9906 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsrh", ALTIVEC_BUILTIN_VEC_VSRH },
9907 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsrb", ALTIVEC_BUILTIN_VEC_VSRB },
9908 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sra", ALTIVEC_BUILTIN_VEC_SRA },
9909 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsraw", ALTIVEC_BUILTIN_VEC_VSRAW },
9910 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsrah", ALTIVEC_BUILTIN_VEC_VSRAH },
9911 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsrab", ALTIVEC_BUILTIN_VEC_VSRAB },
9912 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_srl", ALTIVEC_BUILTIN_VEC_SRL },
9913 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sro", ALTIVEC_BUILTIN_VEC_SRO },
9914 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_sub", ALTIVEC_BUILTIN_VEC_SUB },
9915 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_vsubfp", ALTIVEC_BUILTIN_VEC_VSUBFP },
9916 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubuwm", ALTIVEC_BUILTIN_VEC_VSUBUWM },
9917 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubuhm", ALTIVEC_BUILTIN_VEC_VSUBUHM },
9918 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsububm", ALTIVEC_BUILTIN_VEC_VSUBUBM },
9919 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_subc", ALTIVEC_BUILTIN_VEC_SUBC },
9920 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_subs", ALTIVEC_BUILTIN_VEC_SUBS },
9921 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubsws", ALTIVEC_BUILTIN_VEC_VSUBSWS },
9922 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubuws", ALTIVEC_BUILTIN_VEC_VSUBUWS },
9923 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubshs", ALTIVEC_BUILTIN_VEC_VSUBSHS },
9924 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubuhs", ALTIVEC_BUILTIN_VEC_VSUBUHS },
9925 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsubsbs", ALTIVEC_BUILTIN_VEC_VSUBSBS },
9926 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsububs", ALTIVEC_BUILTIN_VEC_VSUBUBS },
9927 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sum4s", ALTIVEC_BUILTIN_VEC_SUM4S },
9928 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsum4shs", ALTIVEC_BUILTIN_VEC_VSUM4SHS },
9929 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsum4sbs", ALTIVEC_BUILTIN_VEC_VSUM4SBS },
9930 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vsum4ubs", ALTIVEC_BUILTIN_VEC_VSUM4UBS },
9931 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sum2s", ALTIVEC_BUILTIN_VEC_SUM2S },
9932 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_sums", ALTIVEC_BUILTIN_VEC_SUMS },
9933 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_xor", ALTIVEC_BUILTIN_VEC_XOR },
9934
9935 { MASK_VSX, CODE_FOR_nothing, "__builtin_vec_mul", VSX_BUILTIN_VEC_MUL },
9936 { MASK_VSX, CODE_FOR_nothing, "__builtin_vec_div", VSX_BUILTIN_VEC_DIV },
9937
9938 { 0, CODE_FOR_paired_divv2sf3, "__builtin_paired_divv2sf3", PAIRED_BUILTIN_DIVV2SF3 },
9939 { 0, CODE_FOR_paired_addv2sf3, "__builtin_paired_addv2sf3", PAIRED_BUILTIN_ADDV2SF3 },
9940 { 0, CODE_FOR_paired_subv2sf3, "__builtin_paired_subv2sf3", PAIRED_BUILTIN_SUBV2SF3 },
9941 { 0, CODE_FOR_paired_mulv2sf3, "__builtin_paired_mulv2sf3", PAIRED_BUILTIN_MULV2SF3 },
9942 { 0, CODE_FOR_paired_muls0, "__builtin_paired_muls0", PAIRED_BUILTIN_MULS0 },
9943 { 0, CODE_FOR_paired_muls1, "__builtin_paired_muls1", PAIRED_BUILTIN_MULS1 },
9944 { 0, CODE_FOR_paired_merge00, "__builtin_paired_merge00", PAIRED_BUILTIN_MERGE00 },
9945 { 0, CODE_FOR_paired_merge01, "__builtin_paired_merge01", PAIRED_BUILTIN_MERGE01 },
9946 { 0, CODE_FOR_paired_merge10, "__builtin_paired_merge10", PAIRED_BUILTIN_MERGE10 },
9947 { 0, CODE_FOR_paired_merge11, "__builtin_paired_merge11", PAIRED_BUILTIN_MERGE11 },
9948
9949 /* Place holder, leave as first spe builtin. */
9950 { 0, CODE_FOR_addv2si3, "__builtin_spe_evaddw", SPE_BUILTIN_EVADDW },
9951 { 0, CODE_FOR_andv2si3, "__builtin_spe_evand", SPE_BUILTIN_EVAND },
9952 { 0, CODE_FOR_spe_evandc, "__builtin_spe_evandc", SPE_BUILTIN_EVANDC },
9953 { 0, CODE_FOR_divv2si3, "__builtin_spe_evdivws", SPE_BUILTIN_EVDIVWS },
9954 { 0, CODE_FOR_spe_evdivwu, "__builtin_spe_evdivwu", SPE_BUILTIN_EVDIVWU },
9955 { 0, CODE_FOR_spe_eveqv, "__builtin_spe_eveqv", SPE_BUILTIN_EVEQV },
9956 { 0, CODE_FOR_spe_evfsadd, "__builtin_spe_evfsadd", SPE_BUILTIN_EVFSADD },
9957 { 0, CODE_FOR_spe_evfsdiv, "__builtin_spe_evfsdiv", SPE_BUILTIN_EVFSDIV },
9958 { 0, CODE_FOR_spe_evfsmul, "__builtin_spe_evfsmul", SPE_BUILTIN_EVFSMUL },
9959 { 0, CODE_FOR_spe_evfssub, "__builtin_spe_evfssub", SPE_BUILTIN_EVFSSUB },
9960 { 0, CODE_FOR_spe_evmergehi, "__builtin_spe_evmergehi", SPE_BUILTIN_EVMERGEHI },
9961 { 0, CODE_FOR_spe_evmergehilo, "__builtin_spe_evmergehilo", SPE_BUILTIN_EVMERGEHILO },
9962 { 0, CODE_FOR_spe_evmergelo, "__builtin_spe_evmergelo", SPE_BUILTIN_EVMERGELO },
9963 { 0, CODE_FOR_spe_evmergelohi, "__builtin_spe_evmergelohi", SPE_BUILTIN_EVMERGELOHI },
9964 { 0, CODE_FOR_spe_evmhegsmfaa, "__builtin_spe_evmhegsmfaa", SPE_BUILTIN_EVMHEGSMFAA },
9965 { 0, CODE_FOR_spe_evmhegsmfan, "__builtin_spe_evmhegsmfan", SPE_BUILTIN_EVMHEGSMFAN },
9966 { 0, CODE_FOR_spe_evmhegsmiaa, "__builtin_spe_evmhegsmiaa", SPE_BUILTIN_EVMHEGSMIAA },
9967 { 0, CODE_FOR_spe_evmhegsmian, "__builtin_spe_evmhegsmian", SPE_BUILTIN_EVMHEGSMIAN },
9968 { 0, CODE_FOR_spe_evmhegumiaa, "__builtin_spe_evmhegumiaa", SPE_BUILTIN_EVMHEGUMIAA },
9969 { 0, CODE_FOR_spe_evmhegumian, "__builtin_spe_evmhegumian", SPE_BUILTIN_EVMHEGUMIAN },
9970 { 0, CODE_FOR_spe_evmhesmf, "__builtin_spe_evmhesmf", SPE_BUILTIN_EVMHESMF },
9971 { 0, CODE_FOR_spe_evmhesmfa, "__builtin_spe_evmhesmfa", SPE_BUILTIN_EVMHESMFA },
9972 { 0, CODE_FOR_spe_evmhesmfaaw, "__builtin_spe_evmhesmfaaw", SPE_BUILTIN_EVMHESMFAAW },
9973 { 0, CODE_FOR_spe_evmhesmfanw, "__builtin_spe_evmhesmfanw", SPE_BUILTIN_EVMHESMFANW },
9974 { 0, CODE_FOR_spe_evmhesmi, "__builtin_spe_evmhesmi", SPE_BUILTIN_EVMHESMI },
9975 { 0, CODE_FOR_spe_evmhesmia, "__builtin_spe_evmhesmia", SPE_BUILTIN_EVMHESMIA },
9976 { 0, CODE_FOR_spe_evmhesmiaaw, "__builtin_spe_evmhesmiaaw", SPE_BUILTIN_EVMHESMIAAW },
9977 { 0, CODE_FOR_spe_evmhesmianw, "__builtin_spe_evmhesmianw", SPE_BUILTIN_EVMHESMIANW },
9978 { 0, CODE_FOR_spe_evmhessf, "__builtin_spe_evmhessf", SPE_BUILTIN_EVMHESSF },
9979 { 0, CODE_FOR_spe_evmhessfa, "__builtin_spe_evmhessfa", SPE_BUILTIN_EVMHESSFA },
9980 { 0, CODE_FOR_spe_evmhessfaaw, "__builtin_spe_evmhessfaaw", SPE_BUILTIN_EVMHESSFAAW },
9981 { 0, CODE_FOR_spe_evmhessfanw, "__builtin_spe_evmhessfanw", SPE_BUILTIN_EVMHESSFANW },
9982 { 0, CODE_FOR_spe_evmhessiaaw, "__builtin_spe_evmhessiaaw", SPE_BUILTIN_EVMHESSIAAW },
9983 { 0, CODE_FOR_spe_evmhessianw, "__builtin_spe_evmhessianw", SPE_BUILTIN_EVMHESSIANW },
9984 { 0, CODE_FOR_spe_evmheumi, "__builtin_spe_evmheumi", SPE_BUILTIN_EVMHEUMI },
9985 { 0, CODE_FOR_spe_evmheumia, "__builtin_spe_evmheumia", SPE_BUILTIN_EVMHEUMIA },
9986 { 0, CODE_FOR_spe_evmheumiaaw, "__builtin_spe_evmheumiaaw", SPE_BUILTIN_EVMHEUMIAAW },
9987 { 0, CODE_FOR_spe_evmheumianw, "__builtin_spe_evmheumianw", SPE_BUILTIN_EVMHEUMIANW },
9988 { 0, CODE_FOR_spe_evmheusiaaw, "__builtin_spe_evmheusiaaw", SPE_BUILTIN_EVMHEUSIAAW },
9989 { 0, CODE_FOR_spe_evmheusianw, "__builtin_spe_evmheusianw", SPE_BUILTIN_EVMHEUSIANW },
9990 { 0, CODE_FOR_spe_evmhogsmfaa, "__builtin_spe_evmhogsmfaa", SPE_BUILTIN_EVMHOGSMFAA },
9991 { 0, CODE_FOR_spe_evmhogsmfan, "__builtin_spe_evmhogsmfan", SPE_BUILTIN_EVMHOGSMFAN },
9992 { 0, CODE_FOR_spe_evmhogsmiaa, "__builtin_spe_evmhogsmiaa", SPE_BUILTIN_EVMHOGSMIAA },
9993 { 0, CODE_FOR_spe_evmhogsmian, "__builtin_spe_evmhogsmian", SPE_BUILTIN_EVMHOGSMIAN },
9994 { 0, CODE_FOR_spe_evmhogumiaa, "__builtin_spe_evmhogumiaa", SPE_BUILTIN_EVMHOGUMIAA },
9995 { 0, CODE_FOR_spe_evmhogumian, "__builtin_spe_evmhogumian", SPE_BUILTIN_EVMHOGUMIAN },
9996 { 0, CODE_FOR_spe_evmhosmf, "__builtin_spe_evmhosmf", SPE_BUILTIN_EVMHOSMF },
9997 { 0, CODE_FOR_spe_evmhosmfa, "__builtin_spe_evmhosmfa", SPE_BUILTIN_EVMHOSMFA },
9998 { 0, CODE_FOR_spe_evmhosmfaaw, "__builtin_spe_evmhosmfaaw", SPE_BUILTIN_EVMHOSMFAAW },
9999 { 0, CODE_FOR_spe_evmhosmfanw, "__builtin_spe_evmhosmfanw", SPE_BUILTIN_EVMHOSMFANW },
10000 { 0, CODE_FOR_spe_evmhosmi, "__builtin_spe_evmhosmi", SPE_BUILTIN_EVMHOSMI },
10001 { 0, CODE_FOR_spe_evmhosmia, "__builtin_spe_evmhosmia", SPE_BUILTIN_EVMHOSMIA },
10002 { 0, CODE_FOR_spe_evmhosmiaaw, "__builtin_spe_evmhosmiaaw", SPE_BUILTIN_EVMHOSMIAAW },
10003 { 0, CODE_FOR_spe_evmhosmianw, "__builtin_spe_evmhosmianw", SPE_BUILTIN_EVMHOSMIANW },
10004 { 0, CODE_FOR_spe_evmhossf, "__builtin_spe_evmhossf", SPE_BUILTIN_EVMHOSSF },
10005 { 0, CODE_FOR_spe_evmhossfa, "__builtin_spe_evmhossfa", SPE_BUILTIN_EVMHOSSFA },
10006 { 0, CODE_FOR_spe_evmhossfaaw, "__builtin_spe_evmhossfaaw", SPE_BUILTIN_EVMHOSSFAAW },
10007 { 0, CODE_FOR_spe_evmhossfanw, "__builtin_spe_evmhossfanw", SPE_BUILTIN_EVMHOSSFANW },
10008 { 0, CODE_FOR_spe_evmhossiaaw, "__builtin_spe_evmhossiaaw", SPE_BUILTIN_EVMHOSSIAAW },
10009 { 0, CODE_FOR_spe_evmhossianw, "__builtin_spe_evmhossianw", SPE_BUILTIN_EVMHOSSIANW },
10010 { 0, CODE_FOR_spe_evmhoumi, "__builtin_spe_evmhoumi", SPE_BUILTIN_EVMHOUMI },
10011 { 0, CODE_FOR_spe_evmhoumia, "__builtin_spe_evmhoumia", SPE_BUILTIN_EVMHOUMIA },
10012 { 0, CODE_FOR_spe_evmhoumiaaw, "__builtin_spe_evmhoumiaaw", SPE_BUILTIN_EVMHOUMIAAW },
10013 { 0, CODE_FOR_spe_evmhoumianw, "__builtin_spe_evmhoumianw", SPE_BUILTIN_EVMHOUMIANW },
10014 { 0, CODE_FOR_spe_evmhousiaaw, "__builtin_spe_evmhousiaaw", SPE_BUILTIN_EVMHOUSIAAW },
10015 { 0, CODE_FOR_spe_evmhousianw, "__builtin_spe_evmhousianw", SPE_BUILTIN_EVMHOUSIANW },
10016 { 0, CODE_FOR_spe_evmwhsmf, "__builtin_spe_evmwhsmf", SPE_BUILTIN_EVMWHSMF },
10017 { 0, CODE_FOR_spe_evmwhsmfa, "__builtin_spe_evmwhsmfa", SPE_BUILTIN_EVMWHSMFA },
10018 { 0, CODE_FOR_spe_evmwhsmi, "__builtin_spe_evmwhsmi", SPE_BUILTIN_EVMWHSMI },
10019 { 0, CODE_FOR_spe_evmwhsmia, "__builtin_spe_evmwhsmia", SPE_BUILTIN_EVMWHSMIA },
10020 { 0, CODE_FOR_spe_evmwhssf, "__builtin_spe_evmwhssf", SPE_BUILTIN_EVMWHSSF },
10021 { 0, CODE_FOR_spe_evmwhssfa, "__builtin_spe_evmwhssfa", SPE_BUILTIN_EVMWHSSFA },
10022 { 0, CODE_FOR_spe_evmwhumi, "__builtin_spe_evmwhumi", SPE_BUILTIN_EVMWHUMI },
10023 { 0, CODE_FOR_spe_evmwhumia, "__builtin_spe_evmwhumia", SPE_BUILTIN_EVMWHUMIA },
10024 { 0, CODE_FOR_spe_evmwlsmiaaw, "__builtin_spe_evmwlsmiaaw", SPE_BUILTIN_EVMWLSMIAAW },
10025 { 0, CODE_FOR_spe_evmwlsmianw, "__builtin_spe_evmwlsmianw", SPE_BUILTIN_EVMWLSMIANW },
10026 { 0, CODE_FOR_spe_evmwlssiaaw, "__builtin_spe_evmwlssiaaw", SPE_BUILTIN_EVMWLSSIAAW },
10027 { 0, CODE_FOR_spe_evmwlssianw, "__builtin_spe_evmwlssianw", SPE_BUILTIN_EVMWLSSIANW },
10028 { 0, CODE_FOR_spe_evmwlumi, "__builtin_spe_evmwlumi", SPE_BUILTIN_EVMWLUMI },
10029 { 0, CODE_FOR_spe_evmwlumia, "__builtin_spe_evmwlumia", SPE_BUILTIN_EVMWLUMIA },
10030 { 0, CODE_FOR_spe_evmwlumiaaw, "__builtin_spe_evmwlumiaaw", SPE_BUILTIN_EVMWLUMIAAW },
10031 { 0, CODE_FOR_spe_evmwlumianw, "__builtin_spe_evmwlumianw", SPE_BUILTIN_EVMWLUMIANW },
10032 { 0, CODE_FOR_spe_evmwlusiaaw, "__builtin_spe_evmwlusiaaw", SPE_BUILTIN_EVMWLUSIAAW },
10033 { 0, CODE_FOR_spe_evmwlusianw, "__builtin_spe_evmwlusianw", SPE_BUILTIN_EVMWLUSIANW },
10034 { 0, CODE_FOR_spe_evmwsmf, "__builtin_spe_evmwsmf", SPE_BUILTIN_EVMWSMF },
10035 { 0, CODE_FOR_spe_evmwsmfa, "__builtin_spe_evmwsmfa", SPE_BUILTIN_EVMWSMFA },
10036 { 0, CODE_FOR_spe_evmwsmfaa, "__builtin_spe_evmwsmfaa", SPE_BUILTIN_EVMWSMFAA },
10037 { 0, CODE_FOR_spe_evmwsmfan, "__builtin_spe_evmwsmfan", SPE_BUILTIN_EVMWSMFAN },
10038 { 0, CODE_FOR_spe_evmwsmi, "__builtin_spe_evmwsmi", SPE_BUILTIN_EVMWSMI },
10039 { 0, CODE_FOR_spe_evmwsmia, "__builtin_spe_evmwsmia", SPE_BUILTIN_EVMWSMIA },
10040 { 0, CODE_FOR_spe_evmwsmiaa, "__builtin_spe_evmwsmiaa", SPE_BUILTIN_EVMWSMIAA },
10041 { 0, CODE_FOR_spe_evmwsmian, "__builtin_spe_evmwsmian", SPE_BUILTIN_EVMWSMIAN },
10042 { 0, CODE_FOR_spe_evmwssf, "__builtin_spe_evmwssf", SPE_BUILTIN_EVMWSSF },
10043 { 0, CODE_FOR_spe_evmwssfa, "__builtin_spe_evmwssfa", SPE_BUILTIN_EVMWSSFA },
10044 { 0, CODE_FOR_spe_evmwssfaa, "__builtin_spe_evmwssfaa", SPE_BUILTIN_EVMWSSFAA },
10045 { 0, CODE_FOR_spe_evmwssfan, "__builtin_spe_evmwssfan", SPE_BUILTIN_EVMWSSFAN },
10046 { 0, CODE_FOR_spe_evmwumi, "__builtin_spe_evmwumi", SPE_BUILTIN_EVMWUMI },
10047 { 0, CODE_FOR_spe_evmwumia, "__builtin_spe_evmwumia", SPE_BUILTIN_EVMWUMIA },
10048 { 0, CODE_FOR_spe_evmwumiaa, "__builtin_spe_evmwumiaa", SPE_BUILTIN_EVMWUMIAA },
10049 { 0, CODE_FOR_spe_evmwumian, "__builtin_spe_evmwumian", SPE_BUILTIN_EVMWUMIAN },
10050 { 0, CODE_FOR_spe_evnand, "__builtin_spe_evnand", SPE_BUILTIN_EVNAND },
10051 { 0, CODE_FOR_spe_evnor, "__builtin_spe_evnor", SPE_BUILTIN_EVNOR },
10052 { 0, CODE_FOR_spe_evor, "__builtin_spe_evor", SPE_BUILTIN_EVOR },
10053 { 0, CODE_FOR_spe_evorc, "__builtin_spe_evorc", SPE_BUILTIN_EVORC },
10054 { 0, CODE_FOR_spe_evrlw, "__builtin_spe_evrlw", SPE_BUILTIN_EVRLW },
10055 { 0, CODE_FOR_spe_evslw, "__builtin_spe_evslw", SPE_BUILTIN_EVSLW },
10056 { 0, CODE_FOR_spe_evsrws, "__builtin_spe_evsrws", SPE_BUILTIN_EVSRWS },
10057 { 0, CODE_FOR_spe_evsrwu, "__builtin_spe_evsrwu", SPE_BUILTIN_EVSRWU },
10058 { 0, CODE_FOR_subv2si3, "__builtin_spe_evsubfw", SPE_BUILTIN_EVSUBFW },
10059
10060 /* SPE binary operations expecting a 5-bit unsigned literal. */
10061 { 0, CODE_FOR_spe_evaddiw, "__builtin_spe_evaddiw", SPE_BUILTIN_EVADDIW },
10062
10063 { 0, CODE_FOR_spe_evrlwi, "__builtin_spe_evrlwi", SPE_BUILTIN_EVRLWI },
10064 { 0, CODE_FOR_spe_evslwi, "__builtin_spe_evslwi", SPE_BUILTIN_EVSLWI },
10065 { 0, CODE_FOR_spe_evsrwis, "__builtin_spe_evsrwis", SPE_BUILTIN_EVSRWIS },
10066 { 0, CODE_FOR_spe_evsrwiu, "__builtin_spe_evsrwiu", SPE_BUILTIN_EVSRWIU },
10067 { 0, CODE_FOR_spe_evsubifw, "__builtin_spe_evsubifw", SPE_BUILTIN_EVSUBIFW },
10068 { 0, CODE_FOR_spe_evmwhssfaa, "__builtin_spe_evmwhssfaa", SPE_BUILTIN_EVMWHSSFAA },
10069 { 0, CODE_FOR_spe_evmwhssmaa, "__builtin_spe_evmwhssmaa", SPE_BUILTIN_EVMWHSSMAA },
10070 { 0, CODE_FOR_spe_evmwhsmfaa, "__builtin_spe_evmwhsmfaa", SPE_BUILTIN_EVMWHSMFAA },
10071 { 0, CODE_FOR_spe_evmwhsmiaa, "__builtin_spe_evmwhsmiaa", SPE_BUILTIN_EVMWHSMIAA },
10072 { 0, CODE_FOR_spe_evmwhusiaa, "__builtin_spe_evmwhusiaa", SPE_BUILTIN_EVMWHUSIAA },
10073 { 0, CODE_FOR_spe_evmwhumiaa, "__builtin_spe_evmwhumiaa", SPE_BUILTIN_EVMWHUMIAA },
10074 { 0, CODE_FOR_spe_evmwhssfan, "__builtin_spe_evmwhssfan", SPE_BUILTIN_EVMWHSSFAN },
10075 { 0, CODE_FOR_spe_evmwhssian, "__builtin_spe_evmwhssian", SPE_BUILTIN_EVMWHSSIAN },
10076 { 0, CODE_FOR_spe_evmwhsmfan, "__builtin_spe_evmwhsmfan", SPE_BUILTIN_EVMWHSMFAN },
10077 { 0, CODE_FOR_spe_evmwhsmian, "__builtin_spe_evmwhsmian", SPE_BUILTIN_EVMWHSMIAN },
10078 { 0, CODE_FOR_spe_evmwhusian, "__builtin_spe_evmwhusian", SPE_BUILTIN_EVMWHUSIAN },
10079 { 0, CODE_FOR_spe_evmwhumian, "__builtin_spe_evmwhumian", SPE_BUILTIN_EVMWHUMIAN },
10080 { 0, CODE_FOR_spe_evmwhgssfaa, "__builtin_spe_evmwhgssfaa", SPE_BUILTIN_EVMWHGSSFAA },
10081 { 0, CODE_FOR_spe_evmwhgsmfaa, "__builtin_spe_evmwhgsmfaa", SPE_BUILTIN_EVMWHGSMFAA },
10082 { 0, CODE_FOR_spe_evmwhgsmiaa, "__builtin_spe_evmwhgsmiaa", SPE_BUILTIN_EVMWHGSMIAA },
10083 { 0, CODE_FOR_spe_evmwhgumiaa, "__builtin_spe_evmwhgumiaa", SPE_BUILTIN_EVMWHGUMIAA },
10084 { 0, CODE_FOR_spe_evmwhgssfan, "__builtin_spe_evmwhgssfan", SPE_BUILTIN_EVMWHGSSFAN },
10085 { 0, CODE_FOR_spe_evmwhgsmfan, "__builtin_spe_evmwhgsmfan", SPE_BUILTIN_EVMWHGSMFAN },
10086 { 0, CODE_FOR_spe_evmwhgsmian, "__builtin_spe_evmwhgsmian", SPE_BUILTIN_EVMWHGSMIAN },
10087 { 0, CODE_FOR_spe_evmwhgumian, "__builtin_spe_evmwhgumian", SPE_BUILTIN_EVMWHGUMIAN },
10088 { 0, CODE_FOR_spe_brinc, "__builtin_spe_brinc", SPE_BUILTIN_BRINC },
10089
10090 /* Place-holder. Leave as last binary SPE builtin. */
10091 { 0, CODE_FOR_xorv2si3, "__builtin_spe_evxor", SPE_BUILTIN_EVXOR }
10092 };
10093
10094 /* AltiVec predicates. */
10095
10096 struct builtin_description_predicates
10097 {
10098 const unsigned int mask;
10099 const enum insn_code icode;
10100 const char *const name;
10101 const enum rs6000_builtins code;
10102 };
10103
10104 static const struct builtin_description_predicates bdesc_altivec_preds[] =
10105 {
10106 { MASK_ALTIVEC, CODE_FOR_altivec_vcmpbfp_p, "__builtin_altivec_vcmpbfp_p",
10107 ALTIVEC_BUILTIN_VCMPBFP_P },
10108 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_vector_eq_v4sf_p,
10109 "__builtin_altivec_vcmpeqfp_p", ALTIVEC_BUILTIN_VCMPEQFP_P },
10110 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_vector_ge_v4sf_p,
10111 "__builtin_altivec_vcmpgefp_p", ALTIVEC_BUILTIN_VCMPGEFP_P },
10112 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_vector_gt_v4sf_p,
10113 "__builtin_altivec_vcmpgtfp_p", ALTIVEC_BUILTIN_VCMPGTFP_P },
10114 { MASK_ALTIVEC, CODE_FOR_vector_eq_v4si_p, "__builtin_altivec_vcmpequw_p",
10115 ALTIVEC_BUILTIN_VCMPEQUW_P },
10116 { MASK_ALTIVEC, CODE_FOR_vector_gt_v4si_p, "__builtin_altivec_vcmpgtsw_p",
10117 ALTIVEC_BUILTIN_VCMPGTSW_P },
10118 { MASK_ALTIVEC, CODE_FOR_vector_gtu_v4si_p, "__builtin_altivec_vcmpgtuw_p",
10119 ALTIVEC_BUILTIN_VCMPGTUW_P },
10120 { MASK_ALTIVEC, CODE_FOR_vector_eq_v8hi_p, "__builtin_altivec_vcmpequh_p",
10121 ALTIVEC_BUILTIN_VCMPEQUH_P },
10122 { MASK_ALTIVEC, CODE_FOR_vector_gt_v8hi_p, "__builtin_altivec_vcmpgtsh_p",
10123 ALTIVEC_BUILTIN_VCMPGTSH_P },
10124 { MASK_ALTIVEC, CODE_FOR_vector_gtu_v8hi_p, "__builtin_altivec_vcmpgtuh_p",
10125 ALTIVEC_BUILTIN_VCMPGTUH_P },
10126 { MASK_ALTIVEC, CODE_FOR_vector_eq_v16qi_p, "__builtin_altivec_vcmpequb_p",
10127 ALTIVEC_BUILTIN_VCMPEQUB_P },
10128 { MASK_ALTIVEC, CODE_FOR_vector_gt_v16qi_p, "__builtin_altivec_vcmpgtsb_p",
10129 ALTIVEC_BUILTIN_VCMPGTSB_P },
10130 { MASK_ALTIVEC, CODE_FOR_vector_gtu_v16qi_p, "__builtin_altivec_vcmpgtub_p",
10131 ALTIVEC_BUILTIN_VCMPGTUB_P },
10132
10133 { MASK_VSX, CODE_FOR_vector_eq_v4sf_p, "__builtin_vsx_xvcmpeqsp_p",
10134 VSX_BUILTIN_XVCMPEQSP_P },
10135 { MASK_VSX, CODE_FOR_vector_ge_v4sf_p, "__builtin_vsx_xvcmpgesp_p",
10136 VSX_BUILTIN_XVCMPGESP_P },
10137 { MASK_VSX, CODE_FOR_vector_gt_v4sf_p, "__builtin_vsx_xvcmpgtsp_p",
10138 VSX_BUILTIN_XVCMPGTSP_P },
10139 { MASK_VSX, CODE_FOR_vector_eq_v2df_p, "__builtin_vsx_xvcmpeqdp_p",
10140 VSX_BUILTIN_XVCMPEQDP_P },
10141 { MASK_VSX, CODE_FOR_vector_ge_v2df_p, "__builtin_vsx_xvcmpgedp_p",
10142 VSX_BUILTIN_XVCMPGEDP_P },
10143 { MASK_VSX, CODE_FOR_vector_gt_v2df_p, "__builtin_vsx_xvcmpgtdp_p",
10144 VSX_BUILTIN_XVCMPGTDP_P },
10145
10146 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_vcmpeq_p",
10147 ALTIVEC_BUILTIN_VCMPEQ_P },
10148 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_vcmpgt_p",
10149 ALTIVEC_BUILTIN_VCMPGT_P },
10150 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_nothing, "__builtin_vec_vcmpge_p",
10151 ALTIVEC_BUILTIN_VCMPGE_P }
10152 };
10153
10154 /* SPE predicates. */
10155 static struct builtin_description bdesc_spe_predicates[] =
10156 {
10157 /* Place-holder. Leave as first. */
10158 { 0, CODE_FOR_spe_evcmpeq, "__builtin_spe_evcmpeq", SPE_BUILTIN_EVCMPEQ },
10159 { 0, CODE_FOR_spe_evcmpgts, "__builtin_spe_evcmpgts", SPE_BUILTIN_EVCMPGTS },
10160 { 0, CODE_FOR_spe_evcmpgtu, "__builtin_spe_evcmpgtu", SPE_BUILTIN_EVCMPGTU },
10161 { 0, CODE_FOR_spe_evcmplts, "__builtin_spe_evcmplts", SPE_BUILTIN_EVCMPLTS },
10162 { 0, CODE_FOR_spe_evcmpltu, "__builtin_spe_evcmpltu", SPE_BUILTIN_EVCMPLTU },
10163 { 0, CODE_FOR_spe_evfscmpeq, "__builtin_spe_evfscmpeq", SPE_BUILTIN_EVFSCMPEQ },
10164 { 0, CODE_FOR_spe_evfscmpgt, "__builtin_spe_evfscmpgt", SPE_BUILTIN_EVFSCMPGT },
10165 { 0, CODE_FOR_spe_evfscmplt, "__builtin_spe_evfscmplt", SPE_BUILTIN_EVFSCMPLT },
10166 { 0, CODE_FOR_spe_evfststeq, "__builtin_spe_evfststeq", SPE_BUILTIN_EVFSTSTEQ },
10167 { 0, CODE_FOR_spe_evfststgt, "__builtin_spe_evfststgt", SPE_BUILTIN_EVFSTSTGT },
10168 /* Place-holder. Leave as last. */
10169 { 0, CODE_FOR_spe_evfststlt, "__builtin_spe_evfststlt", SPE_BUILTIN_EVFSTSTLT },
10170 };
10171
10172 /* SPE evsel predicates. */
10173 static struct builtin_description bdesc_spe_evsel[] =
10174 {
10175 /* Place-holder. Leave as first. */
10176 { 0, CODE_FOR_spe_evcmpgts, "__builtin_spe_evsel_gts", SPE_BUILTIN_EVSEL_CMPGTS },
10177 { 0, CODE_FOR_spe_evcmpgtu, "__builtin_spe_evsel_gtu", SPE_BUILTIN_EVSEL_CMPGTU },
10178 { 0, CODE_FOR_spe_evcmplts, "__builtin_spe_evsel_lts", SPE_BUILTIN_EVSEL_CMPLTS },
10179 { 0, CODE_FOR_spe_evcmpltu, "__builtin_spe_evsel_ltu", SPE_BUILTIN_EVSEL_CMPLTU },
10180 { 0, CODE_FOR_spe_evcmpeq, "__builtin_spe_evsel_eq", SPE_BUILTIN_EVSEL_CMPEQ },
10181 { 0, CODE_FOR_spe_evfscmpgt, "__builtin_spe_evsel_fsgt", SPE_BUILTIN_EVSEL_FSCMPGT },
10182 { 0, CODE_FOR_spe_evfscmplt, "__builtin_spe_evsel_fslt", SPE_BUILTIN_EVSEL_FSCMPLT },
10183 { 0, CODE_FOR_spe_evfscmpeq, "__builtin_spe_evsel_fseq", SPE_BUILTIN_EVSEL_FSCMPEQ },
10184 { 0, CODE_FOR_spe_evfststgt, "__builtin_spe_evsel_fststgt", SPE_BUILTIN_EVSEL_FSTSTGT },
10185 { 0, CODE_FOR_spe_evfststlt, "__builtin_spe_evsel_fststlt", SPE_BUILTIN_EVSEL_FSTSTLT },
10186 /* Place-holder. Leave as last. */
10187 { 0, CODE_FOR_spe_evfststeq, "__builtin_spe_evsel_fststeq", SPE_BUILTIN_EVSEL_FSTSTEQ },
10188 };
10189
10190 /* PAIRED predicates. */
10191 static const struct builtin_description bdesc_paired_preds[] =
10192 {
10193 /* Place-holder. Leave as first. */
10194 { 0, CODE_FOR_paired_cmpu0, "__builtin_paired_cmpu0", PAIRED_BUILTIN_CMPU0 },
10195 /* Place-holder. Leave as last. */
10196 { 0, CODE_FOR_paired_cmpu1, "__builtin_paired_cmpu1", PAIRED_BUILTIN_CMPU1 },
10197 };
10198
10199 /* ABS* operations. */
10200
10201 static const struct builtin_description bdesc_abs[] =
10202 {
10203 { MASK_ALTIVEC, CODE_FOR_absv4si2, "__builtin_altivec_abs_v4si", ALTIVEC_BUILTIN_ABS_V4SI },
10204 { MASK_ALTIVEC, CODE_FOR_absv8hi2, "__builtin_altivec_abs_v8hi", ALTIVEC_BUILTIN_ABS_V8HI },
10205 { MASK_ALTIVEC, CODE_FOR_absv4sf2, "__builtin_altivec_abs_v4sf", ALTIVEC_BUILTIN_ABS_V4SF },
10206 { MASK_ALTIVEC, CODE_FOR_absv16qi2, "__builtin_altivec_abs_v16qi", ALTIVEC_BUILTIN_ABS_V16QI },
10207 { MASK_ALTIVEC, CODE_FOR_altivec_abss_v4si, "__builtin_altivec_abss_v4si", ALTIVEC_BUILTIN_ABSS_V4SI },
10208 { MASK_ALTIVEC, CODE_FOR_altivec_abss_v8hi, "__builtin_altivec_abss_v8hi", ALTIVEC_BUILTIN_ABSS_V8HI },
10209 { MASK_ALTIVEC, CODE_FOR_altivec_abss_v16qi, "__builtin_altivec_abss_v16qi", ALTIVEC_BUILTIN_ABSS_V16QI },
10210 { MASK_VSX, CODE_FOR_absv2df2, "__builtin_vsx_xvabsdp", VSX_BUILTIN_XVABSDP },
10211 { MASK_VSX, CODE_FOR_vsx_nabsv2df2, "__builtin_vsx_xvnabsdp", VSX_BUILTIN_XVNABSDP },
10212 { MASK_VSX, CODE_FOR_absv4sf2, "__builtin_vsx_xvabssp", VSX_BUILTIN_XVABSSP },
10213 { MASK_VSX, CODE_FOR_vsx_nabsv4sf2, "__builtin_vsx_xvnabssp", VSX_BUILTIN_XVNABSSP },
10214 };
10215
10216 /* Simple unary operations: VECb = foo (unsigned literal) or VECb =
10217 foo (VECa). */
10218
10219 static struct builtin_description bdesc_1arg[] =
10220 {
10221 { MASK_ALTIVEC, CODE_FOR_altivec_vexptefp, "__builtin_altivec_vexptefp", ALTIVEC_BUILTIN_VEXPTEFP },
10222 { MASK_ALTIVEC, CODE_FOR_altivec_vlogefp, "__builtin_altivec_vlogefp", ALTIVEC_BUILTIN_VLOGEFP },
10223 { MASK_ALTIVEC, CODE_FOR_rev4sf2, "__builtin_altivec_vrefp", ALTIVEC_BUILTIN_VREFP },
10224 { MASK_ALTIVEC, CODE_FOR_vector_floorv4sf2, "__builtin_altivec_vrfim", ALTIVEC_BUILTIN_VRFIM },
10225 { MASK_ALTIVEC, CODE_FOR_altivec_vrfin, "__builtin_altivec_vrfin", ALTIVEC_BUILTIN_VRFIN },
10226 { MASK_ALTIVEC, CODE_FOR_vector_ceilv4sf2, "__builtin_altivec_vrfip", ALTIVEC_BUILTIN_VRFIP },
10227 { MASK_ALTIVEC, CODE_FOR_vector_btruncv4sf2, "__builtin_altivec_vrfiz", ALTIVEC_BUILTIN_VRFIZ },
10228 { MASK_ALTIVEC, CODE_FOR_rsqrtv4sf2, "__builtin_altivec_vrsqrtfp", ALTIVEC_BUILTIN_VRSQRTFP },
10229 { MASK_ALTIVEC, CODE_FOR_rsqrtev4sf2, "__builtin_altivec_vrsqrtefp", ALTIVEC_BUILTIN_VRSQRTEFP },
10230 { MASK_ALTIVEC, CODE_FOR_altivec_vspltisb, "__builtin_altivec_vspltisb", ALTIVEC_BUILTIN_VSPLTISB },
10231 { MASK_ALTIVEC, CODE_FOR_altivec_vspltish, "__builtin_altivec_vspltish", ALTIVEC_BUILTIN_VSPLTISH },
10232 { MASK_ALTIVEC, CODE_FOR_altivec_vspltisw, "__builtin_altivec_vspltisw", ALTIVEC_BUILTIN_VSPLTISW },
10233 { MASK_ALTIVEC, CODE_FOR_altivec_vupkhsb, "__builtin_altivec_vupkhsb", ALTIVEC_BUILTIN_VUPKHSB },
10234 { MASK_ALTIVEC, CODE_FOR_altivec_vupkhpx, "__builtin_altivec_vupkhpx", ALTIVEC_BUILTIN_VUPKHPX },
10235 { MASK_ALTIVEC, CODE_FOR_altivec_vupkhsh, "__builtin_altivec_vupkhsh", ALTIVEC_BUILTIN_VUPKHSH },
10236 { MASK_ALTIVEC, CODE_FOR_altivec_vupklsb, "__builtin_altivec_vupklsb", ALTIVEC_BUILTIN_VUPKLSB },
10237 { MASK_ALTIVEC, CODE_FOR_altivec_vupklpx, "__builtin_altivec_vupklpx", ALTIVEC_BUILTIN_VUPKLPX },
10238 { MASK_ALTIVEC, CODE_FOR_altivec_vupklsh, "__builtin_altivec_vupklsh", ALTIVEC_BUILTIN_VUPKLSH },
10239
10240 { MASK_VSX, CODE_FOR_negv2df2, "__builtin_vsx_xvnegdp", VSX_BUILTIN_XVNEGDP },
10241 { MASK_VSX, CODE_FOR_sqrtv2df2, "__builtin_vsx_xvsqrtdp", VSX_BUILTIN_XVSQRTDP },
10242 { MASK_VSX, CODE_FOR_rsqrtv2df2, "__builtin_vsx_xvrsqrtdp", VSX_BUILTIN_VEC_RSQRT_V2DF },
10243 { MASK_VSX, CODE_FOR_rsqrtev2df2, "__builtin_vsx_xvrsqrtedp", VSX_BUILTIN_XVRSQRTEDP },
10244 { MASK_VSX, CODE_FOR_vsx_tsqrtv2df2_fe, "__builtin_vsx_xvtsqrtdp_fe", VSX_BUILTIN_XVTSQRTDP_FE },
10245 { MASK_VSX, CODE_FOR_vsx_tsqrtv2df2_fg, "__builtin_vsx_xvtsqrtdp_fg", VSX_BUILTIN_XVTSQRTDP_FG },
10246 { MASK_VSX, CODE_FOR_vsx_frev2df2, "__builtin_vsx_xvredp", VSX_BUILTIN_XVREDP },
10247
10248 { MASK_VSX, CODE_FOR_negv4sf2, "__builtin_vsx_xvnegsp", VSX_BUILTIN_XVNEGSP },
10249 { MASK_VSX, CODE_FOR_sqrtv4sf2, "__builtin_vsx_xvsqrtsp", VSX_BUILTIN_XVSQRTSP },
10250 { MASK_VSX, CODE_FOR_rsqrtv4sf2, "__builtin_vsx_xvrsqrtsp", VSX_BUILTIN_VEC_RSQRT_V4SF },
10251 { MASK_VSX, CODE_FOR_rsqrtev4sf2, "__builtin_vsx_xvrsqrtesp", VSX_BUILTIN_XVRSQRTESP },
10252 { MASK_VSX, CODE_FOR_vsx_tsqrtv4sf2_fe, "__builtin_vsx_xvtsqrtsp_fe", VSX_BUILTIN_XVTSQRTSP_FE },
10253 { MASK_VSX, CODE_FOR_vsx_tsqrtv4sf2_fg, "__builtin_vsx_xvtsqrtsp_fg", VSX_BUILTIN_XVTSQRTSP_FG },
10254 { MASK_VSX, CODE_FOR_vsx_frev4sf2, "__builtin_vsx_xvresp", VSX_BUILTIN_XVRESP },
10255
10256 { MASK_VSX, CODE_FOR_vsx_xscvdpsp, "__builtin_vsx_xscvdpsp", VSX_BUILTIN_XSCVDPSP },
10257 { MASK_VSX, CODE_FOR_vsx_xscvdpsp, "__builtin_vsx_xscvspdp", VSX_BUILTIN_XSCVSPDP },
10258 { MASK_VSX, CODE_FOR_vsx_xvcvdpsp, "__builtin_vsx_xvcvdpsp", VSX_BUILTIN_XVCVDPSP },
10259 { MASK_VSX, CODE_FOR_vsx_xvcvspdp, "__builtin_vsx_xvcvspdp", VSX_BUILTIN_XVCVSPDP },
10260 { MASK_VSX, CODE_FOR_vsx_tsqrtdf2_fe, "__builtin_vsx_xstsqrtdp_fe", VSX_BUILTIN_XSTSQRTDP_FE },
10261 { MASK_VSX, CODE_FOR_vsx_tsqrtdf2_fg, "__builtin_vsx_xstsqrtdp_fg", VSX_BUILTIN_XSTSQRTDP_FG },
10262
10263 { MASK_VSX, CODE_FOR_vsx_fix_truncv2dfv2di2, "__builtin_vsx_xvcvdpsxds", VSX_BUILTIN_XVCVDPSXDS },
10264 { MASK_VSX, CODE_FOR_vsx_fixuns_truncv2dfv2di2, "__builtin_vsx_xvcvdpuxds", VSX_BUILTIN_XVCVDPUXDS },
10265 { MASK_VSX, CODE_FOR_vsx_fixuns_truncv2dfv2di2, "__builtin_vsx_xvcvdpuxds_uns", VSX_BUILTIN_XVCVDPUXDS_UNS },
10266 { MASK_VSX, CODE_FOR_vsx_floatv2div2df2, "__builtin_vsx_xvcvsxddp", VSX_BUILTIN_XVCVSXDDP },
10267 { MASK_VSX, CODE_FOR_vsx_floatunsv2div2df2, "__builtin_vsx_xvcvuxddp", VSX_BUILTIN_XVCVUXDDP },
10268 { MASK_VSX, CODE_FOR_vsx_floatunsv2div2df2, "__builtin_vsx_xvcvuxddp_uns", VSX_BUILTIN_XVCVUXDDP_UNS },
10269
10270 { MASK_VSX, CODE_FOR_vsx_fix_truncv4sfv4si2, "__builtin_vsx_xvcvspsxws", VSX_BUILTIN_XVCVSPSXWS },
10271 { MASK_VSX, CODE_FOR_vsx_fixuns_truncv4sfv4si2, "__builtin_vsx_xvcvspuxws", VSX_BUILTIN_XVCVSPUXWS },
10272 { MASK_VSX, CODE_FOR_vsx_floatv4siv4sf2, "__builtin_vsx_xvcvsxwsp", VSX_BUILTIN_XVCVSXWSP },
10273 { MASK_VSX, CODE_FOR_vsx_floatunsv4siv4sf2, "__builtin_vsx_xvcvuxwsp", VSX_BUILTIN_XVCVUXWSP },
10274
10275 { MASK_VSX, CODE_FOR_vsx_xvcvdpsxws, "__builtin_vsx_xvcvdpsxws", VSX_BUILTIN_XVCVDPSXWS },
10276 { MASK_VSX, CODE_FOR_vsx_xvcvdpuxws, "__builtin_vsx_xvcvdpuxws", VSX_BUILTIN_XVCVDPUXWS },
10277 { MASK_VSX, CODE_FOR_vsx_xvcvsxwdp, "__builtin_vsx_xvcvsxwdp", VSX_BUILTIN_XVCVSXWDP },
10278 { MASK_VSX, CODE_FOR_vsx_xvcvuxwdp, "__builtin_vsx_xvcvuxwdp", VSX_BUILTIN_XVCVUXWDP },
10279 { MASK_VSX, CODE_FOR_vsx_xvrdpi, "__builtin_vsx_xvrdpi", VSX_BUILTIN_XVRDPI },
10280 { MASK_VSX, CODE_FOR_vsx_xvrdpic, "__builtin_vsx_xvrdpic", VSX_BUILTIN_XVRDPIC },
10281 { MASK_VSX, CODE_FOR_vsx_floorv2df2, "__builtin_vsx_xvrdpim", VSX_BUILTIN_XVRDPIM },
10282 { MASK_VSX, CODE_FOR_vsx_ceilv2df2, "__builtin_vsx_xvrdpip", VSX_BUILTIN_XVRDPIP },
10283 { MASK_VSX, CODE_FOR_vsx_btruncv2df2, "__builtin_vsx_xvrdpiz", VSX_BUILTIN_XVRDPIZ },
10284
10285 { MASK_VSX, CODE_FOR_vsx_xvcvspsxds, "__builtin_vsx_xvcvspsxds", VSX_BUILTIN_XVCVSPSXDS },
10286 { MASK_VSX, CODE_FOR_vsx_xvcvspuxds, "__builtin_vsx_xvcvspuxds", VSX_BUILTIN_XVCVSPUXDS },
10287 { MASK_VSX, CODE_FOR_vsx_xvcvsxdsp, "__builtin_vsx_xvcvsxdsp", VSX_BUILTIN_XVCVSXDSP },
10288 { MASK_VSX, CODE_FOR_vsx_xvcvuxdsp, "__builtin_vsx_xvcvuxdsp", VSX_BUILTIN_XVCVUXDSP },
10289 { MASK_VSX, CODE_FOR_vsx_xvrspi, "__builtin_vsx_xvrspi", VSX_BUILTIN_XVRSPI },
10290 { MASK_VSX, CODE_FOR_vsx_xvrspic, "__builtin_vsx_xvrspic", VSX_BUILTIN_XVRSPIC },
10291 { MASK_VSX, CODE_FOR_vsx_floorv4sf2, "__builtin_vsx_xvrspim", VSX_BUILTIN_XVRSPIM },
10292 { MASK_VSX, CODE_FOR_vsx_ceilv4sf2, "__builtin_vsx_xvrspip", VSX_BUILTIN_XVRSPIP },
10293 { MASK_VSX, CODE_FOR_vsx_btruncv4sf2, "__builtin_vsx_xvrspiz", VSX_BUILTIN_XVRSPIZ },
10294
10295 { MASK_VSX, CODE_FOR_vsx_xsrdpi, "__builtin_vsx_xsrdpi", VSX_BUILTIN_XSRDPI },
10296 { MASK_VSX, CODE_FOR_vsx_xsrdpic, "__builtin_vsx_xsrdpic", VSX_BUILTIN_XSRDPIC },
10297 { MASK_VSX, CODE_FOR_vsx_floordf2, "__builtin_vsx_xsrdpim", VSX_BUILTIN_XSRDPIM },
10298 { MASK_VSX, CODE_FOR_vsx_ceildf2, "__builtin_vsx_xsrdpip", VSX_BUILTIN_XSRDPIP },
10299 { MASK_VSX, CODE_FOR_vsx_btruncdf2, "__builtin_vsx_xsrdpiz", VSX_BUILTIN_XSRDPIZ },
10300
10301 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_abs", ALTIVEC_BUILTIN_VEC_ABS },
10302 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_abss", ALTIVEC_BUILTIN_VEC_ABSS },
10303 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_ceil", ALTIVEC_BUILTIN_VEC_CEIL },
10304 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_expte", ALTIVEC_BUILTIN_VEC_EXPTE },
10305 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_floor", ALTIVEC_BUILTIN_VEC_FLOOR },
10306 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_loge", ALTIVEC_BUILTIN_VEC_LOGE },
10307 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_mtvscr", ALTIVEC_BUILTIN_VEC_MTVSCR },
10308 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_re", ALTIVEC_BUILTIN_VEC_RE },
10309 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_round", ALTIVEC_BUILTIN_VEC_ROUND },
10310 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_rsqrt", ALTIVEC_BUILTIN_VEC_RSQRT },
10311 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_rsqrte", ALTIVEC_BUILTIN_VEC_RSQRTE },
10312 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_trunc", ALTIVEC_BUILTIN_VEC_TRUNC },
10313 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_unpackh", ALTIVEC_BUILTIN_VEC_UNPACKH },
10314 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vupkhsh", ALTIVEC_BUILTIN_VEC_VUPKHSH },
10315 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vupkhpx", ALTIVEC_BUILTIN_VEC_VUPKHPX },
10316 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vupkhsb", ALTIVEC_BUILTIN_VEC_VUPKHSB },
10317 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_unpackl", ALTIVEC_BUILTIN_VEC_UNPACKL },
10318 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vupklpx", ALTIVEC_BUILTIN_VEC_VUPKLPX },
10319 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vupklsh", ALTIVEC_BUILTIN_VEC_VUPKLSH },
10320 { MASK_ALTIVEC, CODE_FOR_nothing, "__builtin_vec_vupklsb", ALTIVEC_BUILTIN_VEC_VUPKLSB },
10321
10322 { MASK_VSX, CODE_FOR_nothing, "__builtin_vec_nearbyint", ALTIVEC_BUILTIN_VEC_NEARBYINT },
10323 { MASK_VSX, CODE_FOR_nothing, "__builtin_vec_rint", ALTIVEC_BUILTIN_VEC_RINT },
10324 { MASK_VSX, CODE_FOR_nothing, "__builtin_vec_sqrt", ALTIVEC_BUILTIN_VEC_SQRT },
10325
10326 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_floatv4siv4sf2, "__builtin_vec_float_sisf", VECTOR_BUILTIN_FLOAT_V4SI_V4SF },
10327 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_unsigned_floatv4siv4sf2, "__builtin_vec_uns_float_sisf", VECTOR_BUILTIN_UNSFLOAT_V4SI_V4SF },
10328 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_fix_truncv4sfv4si2, "__builtin_vec_fix_sfsi", VECTOR_BUILTIN_FIX_V4SF_V4SI },
10329 { MASK_ALTIVEC|MASK_VSX, CODE_FOR_fixuns_truncv4sfv4si2, "__builtin_vec_fixuns_sfsi", VECTOR_BUILTIN_FIXUNS_V4SF_V4SI },
10330
10331 /* The SPE unary builtins must start with SPE_BUILTIN_EVABS and
10332 end with SPE_BUILTIN_EVSUBFUSIAAW. */
10333 { 0, CODE_FOR_absv2si2, "__builtin_spe_evabs", SPE_BUILTIN_EVABS },
10334 { 0, CODE_FOR_spe_evaddsmiaaw, "__builtin_spe_evaddsmiaaw", SPE_BUILTIN_EVADDSMIAAW },
10335 { 0, CODE_FOR_spe_evaddssiaaw, "__builtin_spe_evaddssiaaw", SPE_BUILTIN_EVADDSSIAAW },
10336 { 0, CODE_FOR_spe_evaddumiaaw, "__builtin_spe_evaddumiaaw", SPE_BUILTIN_EVADDUMIAAW },
10337 { 0, CODE_FOR_spe_evaddusiaaw, "__builtin_spe_evaddusiaaw", SPE_BUILTIN_EVADDUSIAAW },
10338 { 0, CODE_FOR_spe_evcntlsw, "__builtin_spe_evcntlsw", SPE_BUILTIN_EVCNTLSW },
10339 { 0, CODE_FOR_spe_evcntlzw, "__builtin_spe_evcntlzw", SPE_BUILTIN_EVCNTLZW },
10340 { 0, CODE_FOR_spe_evextsb, "__builtin_spe_evextsb", SPE_BUILTIN_EVEXTSB },
10341 { 0, CODE_FOR_spe_evextsh, "__builtin_spe_evextsh", SPE_BUILTIN_EVEXTSH },
10342 { 0, CODE_FOR_spe_evfsabs, "__builtin_spe_evfsabs", SPE_BUILTIN_EVFSABS },
10343 { 0, CODE_FOR_spe_evfscfsf, "__builtin_spe_evfscfsf", SPE_BUILTIN_EVFSCFSF },
10344 { 0, CODE_FOR_spe_evfscfsi, "__builtin_spe_evfscfsi", SPE_BUILTIN_EVFSCFSI },
10345 { 0, CODE_FOR_spe_evfscfuf, "__builtin_spe_evfscfuf", SPE_BUILTIN_EVFSCFUF },
10346 { 0, CODE_FOR_spe_evfscfui, "__builtin_spe_evfscfui", SPE_BUILTIN_EVFSCFUI },
10347 { 0, CODE_FOR_spe_evfsctsf, "__builtin_spe_evfsctsf", SPE_BUILTIN_EVFSCTSF },
10348 { 0, CODE_FOR_spe_evfsctsi, "__builtin_spe_evfsctsi", SPE_BUILTIN_EVFSCTSI },
10349 { 0, CODE_FOR_spe_evfsctsiz, "__builtin_spe_evfsctsiz", SPE_BUILTIN_EVFSCTSIZ },
10350 { 0, CODE_FOR_spe_evfsctuf, "__builtin_spe_evfsctuf", SPE_BUILTIN_EVFSCTUF },
10351 { 0, CODE_FOR_spe_evfsctui, "__builtin_spe_evfsctui", SPE_BUILTIN_EVFSCTUI },
10352 { 0, CODE_FOR_spe_evfsctuiz, "__builtin_spe_evfsctuiz", SPE_BUILTIN_EVFSCTUIZ },
10353 { 0, CODE_FOR_spe_evfsnabs, "__builtin_spe_evfsnabs", SPE_BUILTIN_EVFSNABS },
10354 { 0, CODE_FOR_spe_evfsneg, "__builtin_spe_evfsneg", SPE_BUILTIN_EVFSNEG },
10355 { 0, CODE_FOR_spe_evmra, "__builtin_spe_evmra", SPE_BUILTIN_EVMRA },
10356 { 0, CODE_FOR_negv2si2, "__builtin_spe_evneg", SPE_BUILTIN_EVNEG },
10357 { 0, CODE_FOR_spe_evrndw, "__builtin_spe_evrndw", SPE_BUILTIN_EVRNDW },
10358 { 0, CODE_FOR_spe_evsubfsmiaaw, "__builtin_spe_evsubfsmiaaw", SPE_BUILTIN_EVSUBFSMIAAW },
10359 { 0, CODE_FOR_spe_evsubfssiaaw, "__builtin_spe_evsubfssiaaw", SPE_BUILTIN_EVSUBFSSIAAW },
10360 { 0, CODE_FOR_spe_evsubfumiaaw, "__builtin_spe_evsubfumiaaw", SPE_BUILTIN_EVSUBFUMIAAW },
10361
10362 /* Place-holder. Leave as last unary SPE builtin. */
10363 { 0, CODE_FOR_spe_evsubfusiaaw, "__builtin_spe_evsubfusiaaw", SPE_BUILTIN_EVSUBFUSIAAW },
10364
10365 { 0, CODE_FOR_paired_absv2sf2, "__builtin_paired_absv2sf2", PAIRED_BUILTIN_ABSV2SF2 },
10366 { 0, CODE_FOR_nabsv2sf2, "__builtin_paired_nabsv2sf2", PAIRED_BUILTIN_NABSV2SF2 },
10367 { 0, CODE_FOR_paired_negv2sf2, "__builtin_paired_negv2sf2", PAIRED_BUILTIN_NEGV2SF2 },
10368 { 0, CODE_FOR_sqrtv2sf2, "__builtin_paired_sqrtv2sf2", PAIRED_BUILTIN_SQRTV2SF2 },
10369 { 0, CODE_FOR_resv2sf2, "__builtin_paired_resv2sf2", PAIRED_BUILTIN_RESV2SF2 }
10370 };
10371
10372 static rtx
10373 rs6000_expand_unop_builtin (enum insn_code icode, tree exp, rtx target)
10374 {
10375 rtx pat;
10376 tree arg0 = CALL_EXPR_ARG (exp, 0);
10377 rtx op0 = expand_normal (arg0);
10378 enum machine_mode tmode = insn_data[icode].operand[0].mode;
10379 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
10380
10381 if (icode == CODE_FOR_nothing)
10382 /* Builtin not supported on this processor. */
10383 return 0;
10384
10385 /* If we got invalid arguments bail out before generating bad rtl. */
10386 if (arg0 == error_mark_node)
10387 return const0_rtx;
10388
10389 if (icode == CODE_FOR_altivec_vspltisb
10390 || icode == CODE_FOR_altivec_vspltish
10391 || icode == CODE_FOR_altivec_vspltisw
10392 || icode == CODE_FOR_spe_evsplatfi
10393 || icode == CODE_FOR_spe_evsplati)
10394 {
10395 /* Only allow 5-bit *signed* literals. */
10396 if (GET_CODE (op0) != CONST_INT
10397 || INTVAL (op0) > 15
10398 || INTVAL (op0) < -16)
10399 {
10400 error ("argument 1 must be a 5-bit signed literal");
10401 return const0_rtx;
10402 }
10403 }
10404
10405 if (target == 0
10406 || GET_MODE (target) != tmode
10407 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
10408 target = gen_reg_rtx (tmode);
10409
10410 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
10411 op0 = copy_to_mode_reg (mode0, op0);
10412
10413 pat = GEN_FCN (icode) (target, op0);
10414 if (! pat)
10415 return 0;
10416 emit_insn (pat);
10417
10418 return target;
10419 }
10420
10421 static rtx
10422 altivec_expand_abs_builtin (enum insn_code icode, tree exp, rtx target)
10423 {
10424 rtx pat, scratch1, scratch2;
10425 tree arg0 = CALL_EXPR_ARG (exp, 0);
10426 rtx op0 = expand_normal (arg0);
10427 enum machine_mode tmode = insn_data[icode].operand[0].mode;
10428 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
10429
10430 /* If we have invalid arguments, bail out before generating bad rtl. */
10431 if (arg0 == error_mark_node)
10432 return const0_rtx;
10433
10434 if (target == 0
10435 || GET_MODE (target) != tmode
10436 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
10437 target = gen_reg_rtx (tmode);
10438
10439 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
10440 op0 = copy_to_mode_reg (mode0, op0);
10441
10442 scratch1 = gen_reg_rtx (mode0);
10443 scratch2 = gen_reg_rtx (mode0);
10444
10445 pat = GEN_FCN (icode) (target, op0, scratch1, scratch2);
10446 if (! pat)
10447 return 0;
10448 emit_insn (pat);
10449
10450 return target;
10451 }
10452
10453 static rtx
10454 rs6000_expand_binop_builtin (enum insn_code icode, tree exp, rtx target)
10455 {
10456 rtx pat;
10457 tree arg0 = CALL_EXPR_ARG (exp, 0);
10458 tree arg1 = CALL_EXPR_ARG (exp, 1);
10459 rtx op0 = expand_normal (arg0);
10460 rtx op1 = expand_normal (arg1);
10461 enum machine_mode tmode = insn_data[icode].operand[0].mode;
10462 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
10463 enum machine_mode mode1 = insn_data[icode].operand[2].mode;
10464
10465 if (icode == CODE_FOR_nothing)
10466 /* Builtin not supported on this processor. */
10467 return 0;
10468
10469 /* If we got invalid arguments bail out before generating bad rtl. */
10470 if (arg0 == error_mark_node || arg1 == error_mark_node)
10471 return const0_rtx;
10472
10473 if (icode == CODE_FOR_altivec_vcfux
10474 || icode == CODE_FOR_altivec_vcfsx
10475 || icode == CODE_FOR_altivec_vctsxs
10476 || icode == CODE_FOR_altivec_vctuxs
10477 || icode == CODE_FOR_altivec_vspltb
10478 || icode == CODE_FOR_altivec_vsplth
10479 || icode == CODE_FOR_altivec_vspltw
10480 || icode == CODE_FOR_spe_evaddiw
10481 || icode == CODE_FOR_spe_evldd
10482 || icode == CODE_FOR_spe_evldh
10483 || icode == CODE_FOR_spe_evldw
10484 || icode == CODE_FOR_spe_evlhhesplat
10485 || icode == CODE_FOR_spe_evlhhossplat
10486 || icode == CODE_FOR_spe_evlhhousplat
10487 || icode == CODE_FOR_spe_evlwhe
10488 || icode == CODE_FOR_spe_evlwhos
10489 || icode == CODE_FOR_spe_evlwhou
10490 || icode == CODE_FOR_spe_evlwhsplat
10491 || icode == CODE_FOR_spe_evlwwsplat
10492 || icode == CODE_FOR_spe_evrlwi
10493 || icode == CODE_FOR_spe_evslwi
10494 || icode == CODE_FOR_spe_evsrwis
10495 || icode == CODE_FOR_spe_evsubifw
10496 || icode == CODE_FOR_spe_evsrwiu)
10497 {
10498 /* Only allow 5-bit unsigned literals. */
10499 STRIP_NOPS (arg1);
10500 if (TREE_CODE (arg1) != INTEGER_CST
10501 || TREE_INT_CST_LOW (arg1) & ~0x1f)
10502 {
10503 error ("argument 2 must be a 5-bit unsigned literal");
10504 return const0_rtx;
10505 }
10506 }
10507
10508 if (target == 0
10509 || GET_MODE (target) != tmode
10510 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
10511 target = gen_reg_rtx (tmode);
10512
10513 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
10514 op0 = copy_to_mode_reg (mode0, op0);
10515 if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
10516 op1 = copy_to_mode_reg (mode1, op1);
10517
10518 pat = GEN_FCN (icode) (target, op0, op1);
10519 if (! pat)
10520 return 0;
10521 emit_insn (pat);
10522
10523 return target;
10524 }
10525
10526 static rtx
10527 altivec_expand_predicate_builtin (enum insn_code icode, tree exp, rtx target)
10528 {
10529 rtx pat, scratch;
10530 tree cr6_form = CALL_EXPR_ARG (exp, 0);
10531 tree arg0 = CALL_EXPR_ARG (exp, 1);
10532 tree arg1 = CALL_EXPR_ARG (exp, 2);
10533 rtx op0 = expand_normal (arg0);
10534 rtx op1 = expand_normal (arg1);
10535 enum machine_mode tmode = SImode;
10536 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
10537 enum machine_mode mode1 = insn_data[icode].operand[2].mode;
10538 int cr6_form_int;
10539
10540 if (TREE_CODE (cr6_form) != INTEGER_CST)
10541 {
10542 error ("argument 1 of __builtin_altivec_predicate must be a constant");
10543 return const0_rtx;
10544 }
10545 else
10546 cr6_form_int = TREE_INT_CST_LOW (cr6_form);
10547
10548 gcc_assert (mode0 == mode1);
10549
10550 /* If we have invalid arguments, bail out before generating bad rtl. */
10551 if (arg0 == error_mark_node || arg1 == error_mark_node)
10552 return const0_rtx;
10553
10554 if (target == 0
10555 || GET_MODE (target) != tmode
10556 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
10557 target = gen_reg_rtx (tmode);
10558
10559 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
10560 op0 = copy_to_mode_reg (mode0, op0);
10561 if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
10562 op1 = copy_to_mode_reg (mode1, op1);
10563
10564 scratch = gen_reg_rtx (mode0);
10565
10566 pat = GEN_FCN (icode) (scratch, op0, op1);
10567 if (! pat)
10568 return 0;
10569 emit_insn (pat);
10570
10571 /* The vec_any* and vec_all* predicates use the same opcodes for two
10572 different operations, but the bits in CR6 will be different
10573 depending on what information we want. So we have to play tricks
10574 with CR6 to get the right bits out.
10575
10576 If you think this is disgusting, look at the specs for the
10577 AltiVec predicates. */
10578
10579 switch (cr6_form_int)
10580 {
10581 case 0:
10582 emit_insn (gen_cr6_test_for_zero (target));
10583 break;
10584 case 1:
10585 emit_insn (gen_cr6_test_for_zero_reverse (target));
10586 break;
10587 case 2:
10588 emit_insn (gen_cr6_test_for_lt (target));
10589 break;
10590 case 3:
10591 emit_insn (gen_cr6_test_for_lt_reverse (target));
10592 break;
10593 default:
10594 error ("argument 1 of __builtin_altivec_predicate is out of range");
10595 break;
10596 }
10597
10598 return target;
10599 }
10600
10601 static rtx
10602 paired_expand_lv_builtin (enum insn_code icode, tree exp, rtx target)
10603 {
10604 rtx pat, addr;
10605 tree arg0 = CALL_EXPR_ARG (exp, 0);
10606 tree arg1 = CALL_EXPR_ARG (exp, 1);
10607 enum machine_mode tmode = insn_data[icode].operand[0].mode;
10608 enum machine_mode mode0 = Pmode;
10609 enum machine_mode mode1 = Pmode;
10610 rtx op0 = expand_normal (arg0);
10611 rtx op1 = expand_normal (arg1);
10612
10613 if (icode == CODE_FOR_nothing)
10614 /* Builtin not supported on this processor. */
10615 return 0;
10616
10617 /* If we got invalid arguments bail out before generating bad rtl. */
10618 if (arg0 == error_mark_node || arg1 == error_mark_node)
10619 return const0_rtx;
10620
10621 if (target == 0
10622 || GET_MODE (target) != tmode
10623 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
10624 target = gen_reg_rtx (tmode);
10625
10626 op1 = copy_to_mode_reg (mode1, op1);
10627
10628 if (op0 == const0_rtx)
10629 {
10630 addr = gen_rtx_MEM (tmode, op1);
10631 }
10632 else
10633 {
10634 op0 = copy_to_mode_reg (mode0, op0);
10635 addr = gen_rtx_MEM (tmode, gen_rtx_PLUS (Pmode, op0, op1));
10636 }
10637
10638 pat = GEN_FCN (icode) (target, addr);
10639
10640 if (! pat)
10641 return 0;
10642 emit_insn (pat);
10643
10644 return target;
10645 }
10646
10647 static rtx
10648 altivec_expand_lv_builtin (enum insn_code icode, tree exp, rtx target, bool blk)
10649 {
10650 rtx pat, addr;
10651 tree arg0 = CALL_EXPR_ARG (exp, 0);
10652 tree arg1 = CALL_EXPR_ARG (exp, 1);
10653 enum machine_mode tmode = insn_data[icode].operand[0].mode;
10654 enum machine_mode mode0 = Pmode;
10655 enum machine_mode mode1 = Pmode;
10656 rtx op0 = expand_normal (arg0);
10657 rtx op1 = expand_normal (arg1);
10658
10659 if (icode == CODE_FOR_nothing)
10660 /* Builtin not supported on this processor. */
10661 return 0;
10662
10663 /* If we got invalid arguments bail out before generating bad rtl. */
10664 if (arg0 == error_mark_node || arg1 == error_mark_node)
10665 return const0_rtx;
10666
10667 if (target == 0
10668 || GET_MODE (target) != tmode
10669 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
10670 target = gen_reg_rtx (tmode);
10671
10672 op1 = copy_to_mode_reg (mode1, op1);
10673
10674 if (op0 == const0_rtx)
10675 {
10676 addr = gen_rtx_MEM (blk ? BLKmode : tmode, op1);
10677 }
10678 else
10679 {
10680 op0 = copy_to_mode_reg (mode0, op0);
10681 addr = gen_rtx_MEM (blk ? BLKmode : tmode, gen_rtx_PLUS (Pmode, op0, op1));
10682 }
10683
10684 pat = GEN_FCN (icode) (target, addr);
10685
10686 if (! pat)
10687 return 0;
10688 emit_insn (pat);
10689
10690 return target;
10691 }
10692
10693 static rtx
10694 spe_expand_stv_builtin (enum insn_code icode, tree exp)
10695 {
10696 tree arg0 = CALL_EXPR_ARG (exp, 0);
10697 tree arg1 = CALL_EXPR_ARG (exp, 1);
10698 tree arg2 = CALL_EXPR_ARG (exp, 2);
10699 rtx op0 = expand_normal (arg0);
10700 rtx op1 = expand_normal (arg1);
10701 rtx op2 = expand_normal (arg2);
10702 rtx pat;
10703 enum machine_mode mode0 = insn_data[icode].operand[0].mode;
10704 enum machine_mode mode1 = insn_data[icode].operand[1].mode;
10705 enum machine_mode mode2 = insn_data[icode].operand[2].mode;
10706
10707 /* Invalid arguments. Bail before doing anything stoopid! */
10708 if (arg0 == error_mark_node
10709 || arg1 == error_mark_node
10710 || arg2 == error_mark_node)
10711 return const0_rtx;
10712
10713 if (! (*insn_data[icode].operand[2].predicate) (op0, mode2))
10714 op0 = copy_to_mode_reg (mode2, op0);
10715 if (! (*insn_data[icode].operand[0].predicate) (op1, mode0))
10716 op1 = copy_to_mode_reg (mode0, op1);
10717 if (! (*insn_data[icode].operand[1].predicate) (op2, mode1))
10718 op2 = copy_to_mode_reg (mode1, op2);
10719
10720 pat = GEN_FCN (icode) (op1, op2, op0);
10721 if (pat)
10722 emit_insn (pat);
10723 return NULL_RTX;
10724 }
10725
10726 static rtx
10727 paired_expand_stv_builtin (enum insn_code icode, tree exp)
10728 {
10729 tree arg0 = CALL_EXPR_ARG (exp, 0);
10730 tree arg1 = CALL_EXPR_ARG (exp, 1);
10731 tree arg2 = CALL_EXPR_ARG (exp, 2);
10732 rtx op0 = expand_normal (arg0);
10733 rtx op1 = expand_normal (arg1);
10734 rtx op2 = expand_normal (arg2);
10735 rtx pat, addr;
10736 enum machine_mode tmode = insn_data[icode].operand[0].mode;
10737 enum machine_mode mode1 = Pmode;
10738 enum machine_mode mode2 = Pmode;
10739
10740 /* Invalid arguments. Bail before doing anything stoopid! */
10741 if (arg0 == error_mark_node
10742 || arg1 == error_mark_node
10743 || arg2 == error_mark_node)
10744 return const0_rtx;
10745
10746 if (! (*insn_data[icode].operand[1].predicate) (op0, tmode))
10747 op0 = copy_to_mode_reg (tmode, op0);
10748
10749 op2 = copy_to_mode_reg (mode2, op2);
10750
10751 if (op1 == const0_rtx)
10752 {
10753 addr = gen_rtx_MEM (tmode, op2);
10754 }
10755 else
10756 {
10757 op1 = copy_to_mode_reg (mode1, op1);
10758 addr = gen_rtx_MEM (tmode, gen_rtx_PLUS (Pmode, op1, op2));
10759 }
10760
10761 pat = GEN_FCN (icode) (addr, op0);
10762 if (pat)
10763 emit_insn (pat);
10764 return NULL_RTX;
10765 }
10766
10767 static rtx
10768 altivec_expand_stv_builtin (enum insn_code icode, tree exp)
10769 {
10770 tree arg0 = CALL_EXPR_ARG (exp, 0);
10771 tree arg1 = CALL_EXPR_ARG (exp, 1);
10772 tree arg2 = CALL_EXPR_ARG (exp, 2);
10773 rtx op0 = expand_normal (arg0);
10774 rtx op1 = expand_normal (arg1);
10775 rtx op2 = expand_normal (arg2);
10776 rtx pat, addr;
10777 enum machine_mode tmode = insn_data[icode].operand[0].mode;
10778 enum machine_mode mode1 = Pmode;
10779 enum machine_mode mode2 = Pmode;
10780
10781 /* Invalid arguments. Bail before doing anything stoopid! */
10782 if (arg0 == error_mark_node
10783 || arg1 == error_mark_node
10784 || arg2 == error_mark_node)
10785 return const0_rtx;
10786
10787 if (! (*insn_data[icode].operand[1].predicate) (op0, tmode))
10788 op0 = copy_to_mode_reg (tmode, op0);
10789
10790 op2 = copy_to_mode_reg (mode2, op2);
10791
10792 if (op1 == const0_rtx)
10793 {
10794 addr = gen_rtx_MEM (tmode, op2);
10795 }
10796 else
10797 {
10798 op1 = copy_to_mode_reg (mode1, op1);
10799 addr = gen_rtx_MEM (tmode, gen_rtx_PLUS (Pmode, op1, op2));
10800 }
10801
10802 pat = GEN_FCN (icode) (addr, op0);
10803 if (pat)
10804 emit_insn (pat);
10805 return NULL_RTX;
10806 }
10807
10808 static rtx
10809 rs6000_expand_ternop_builtin (enum insn_code icode, tree exp, rtx target)
10810 {
10811 rtx pat;
10812 tree arg0 = CALL_EXPR_ARG (exp, 0);
10813 tree arg1 = CALL_EXPR_ARG (exp, 1);
10814 tree arg2 = CALL_EXPR_ARG (exp, 2);
10815 rtx op0 = expand_normal (arg0);
10816 rtx op1 = expand_normal (arg1);
10817 rtx op2 = expand_normal (arg2);
10818 enum machine_mode tmode = insn_data[icode].operand[0].mode;
10819 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
10820 enum machine_mode mode1 = insn_data[icode].operand[2].mode;
10821 enum machine_mode mode2 = insn_data[icode].operand[3].mode;
10822
10823 if (icode == CODE_FOR_nothing)
10824 /* Builtin not supported on this processor. */
10825 return 0;
10826
10827 /* If we got invalid arguments bail out before generating bad rtl. */
10828 if (arg0 == error_mark_node
10829 || arg1 == error_mark_node
10830 || arg2 == error_mark_node)
10831 return const0_rtx;
10832
10833 switch (icode)
10834 {
10835 case CODE_FOR_altivec_vsldoi_v4sf:
10836 case CODE_FOR_altivec_vsldoi_v4si:
10837 case CODE_FOR_altivec_vsldoi_v8hi:
10838 case CODE_FOR_altivec_vsldoi_v16qi:
10839 /* Only allow 4-bit unsigned literals. */
10840 STRIP_NOPS (arg2);
10841 if (TREE_CODE (arg2) != INTEGER_CST
10842 || TREE_INT_CST_LOW (arg2) & ~0xf)
10843 {
10844 error ("argument 3 must be a 4-bit unsigned literal");
10845 return const0_rtx;
10846 }
10847 break;
10848
10849 case CODE_FOR_vsx_xxpermdi_v2df:
10850 case CODE_FOR_vsx_xxpermdi_v2di:
10851 case CODE_FOR_vsx_xxsldwi_v16qi:
10852 case CODE_FOR_vsx_xxsldwi_v8hi:
10853 case CODE_FOR_vsx_xxsldwi_v4si:
10854 case CODE_FOR_vsx_xxsldwi_v4sf:
10855 case CODE_FOR_vsx_xxsldwi_v2di:
10856 case CODE_FOR_vsx_xxsldwi_v2df:
10857 /* Only allow 2-bit unsigned literals. */
10858 STRIP_NOPS (arg2);
10859 if (TREE_CODE (arg2) != INTEGER_CST
10860 || TREE_INT_CST_LOW (arg2) & ~0x3)
10861 {
10862 error ("argument 3 must be a 2-bit unsigned literal");
10863 return const0_rtx;
10864 }
10865 break;
10866
10867 case CODE_FOR_vsx_set_v2df:
10868 case CODE_FOR_vsx_set_v2di:
10869 /* Only allow 1-bit unsigned literals. */
10870 STRIP_NOPS (arg2);
10871 if (TREE_CODE (arg2) != INTEGER_CST
10872 || TREE_INT_CST_LOW (arg2) & ~0x1)
10873 {
10874 error ("argument 3 must be a 1-bit unsigned literal");
10875 return const0_rtx;
10876 }
10877 break;
10878
10879 default:
10880 break;
10881 }
10882
10883 if (target == 0
10884 || GET_MODE (target) != tmode
10885 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
10886 target = gen_reg_rtx (tmode);
10887
10888 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
10889 op0 = copy_to_mode_reg (mode0, op0);
10890 if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
10891 op1 = copy_to_mode_reg (mode1, op1);
10892 if (! (*insn_data[icode].operand[3].predicate) (op2, mode2))
10893 op2 = copy_to_mode_reg (mode2, op2);
10894
10895 if (TARGET_PAIRED_FLOAT && icode == CODE_FOR_selv2sf4)
10896 pat = GEN_FCN (icode) (target, op0, op1, op2, CONST0_RTX (SFmode));
10897 else
10898 pat = GEN_FCN (icode) (target, op0, op1, op2);
10899 if (! pat)
10900 return 0;
10901 emit_insn (pat);
10902
10903 return target;
10904 }
10905
10906 /* Expand the lvx builtins. */
10907 static rtx
10908 altivec_expand_ld_builtin (tree exp, rtx target, bool *expandedp)
10909 {
10910 tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
10911 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
10912 tree arg0;
10913 enum machine_mode tmode, mode0;
10914 rtx pat, op0;
10915 enum insn_code icode;
10916
10917 switch (fcode)
10918 {
10919 case ALTIVEC_BUILTIN_LD_INTERNAL_16qi:
10920 icode = CODE_FOR_vector_load_v16qi;
10921 break;
10922 case ALTIVEC_BUILTIN_LD_INTERNAL_8hi:
10923 icode = CODE_FOR_vector_load_v8hi;
10924 break;
10925 case ALTIVEC_BUILTIN_LD_INTERNAL_4si:
10926 icode = CODE_FOR_vector_load_v4si;
10927 break;
10928 case ALTIVEC_BUILTIN_LD_INTERNAL_4sf:
10929 icode = CODE_FOR_vector_load_v4sf;
10930 break;
10931 default:
10932 *expandedp = false;
10933 return NULL_RTX;
10934 }
10935
10936 *expandedp = true;
10937
10938 arg0 = CALL_EXPR_ARG (exp, 0);
10939 op0 = expand_normal (arg0);
10940 tmode = insn_data[icode].operand[0].mode;
10941 mode0 = insn_data[icode].operand[1].mode;
10942
10943 if (target == 0
10944 || GET_MODE (target) != tmode
10945 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
10946 target = gen_reg_rtx (tmode);
10947
10948 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
10949 op0 = gen_rtx_MEM (mode0, copy_to_mode_reg (Pmode, op0));
10950
10951 pat = GEN_FCN (icode) (target, op0);
10952 if (! pat)
10953 return 0;
10954 emit_insn (pat);
10955 return target;
10956 }
10957
10958 /* Expand the stvx builtins. */
10959 static rtx
10960 altivec_expand_st_builtin (tree exp, rtx target ATTRIBUTE_UNUSED,
10961 bool *expandedp)
10962 {
10963 tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
10964 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
10965 tree arg0, arg1;
10966 enum machine_mode mode0, mode1;
10967 rtx pat, op0, op1;
10968 enum insn_code icode;
10969
10970 switch (fcode)
10971 {
10972 case ALTIVEC_BUILTIN_ST_INTERNAL_16qi:
10973 icode = CODE_FOR_vector_store_v16qi;
10974 break;
10975 case ALTIVEC_BUILTIN_ST_INTERNAL_8hi:
10976 icode = CODE_FOR_vector_store_v8hi;
10977 break;
10978 case ALTIVEC_BUILTIN_ST_INTERNAL_4si:
10979 icode = CODE_FOR_vector_store_v4si;
10980 break;
10981 case ALTIVEC_BUILTIN_ST_INTERNAL_4sf:
10982 icode = CODE_FOR_vector_store_v4sf;
10983 break;
10984 default:
10985 *expandedp = false;
10986 return NULL_RTX;
10987 }
10988
10989 arg0 = CALL_EXPR_ARG (exp, 0);
10990 arg1 = CALL_EXPR_ARG (exp, 1);
10991 op0 = expand_normal (arg0);
10992 op1 = expand_normal (arg1);
10993 mode0 = insn_data[icode].operand[0].mode;
10994 mode1 = insn_data[icode].operand[1].mode;
10995
10996 if (! (*insn_data[icode].operand[0].predicate) (op0, mode0))
10997 op0 = gen_rtx_MEM (mode0, copy_to_mode_reg (Pmode, op0));
10998 if (! (*insn_data[icode].operand[1].predicate) (op1, mode1))
10999 op1 = copy_to_mode_reg (mode1, op1);
11000
11001 pat = GEN_FCN (icode) (op0, op1);
11002 if (pat)
11003 emit_insn (pat);
11004
11005 *expandedp = true;
11006 return NULL_RTX;
11007 }
11008
11009 /* Expand the dst builtins. */
11010 static rtx
11011 altivec_expand_dst_builtin (tree exp, rtx target ATTRIBUTE_UNUSED,
11012 bool *expandedp)
11013 {
11014 tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
11015 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
11016 tree arg0, arg1, arg2;
11017 enum machine_mode mode0, mode1;
11018 rtx pat, op0, op1, op2;
11019 const struct builtin_description *d;
11020 size_t i;
11021
11022 *expandedp = false;
11023
11024 /* Handle DST variants. */
11025 d = bdesc_dst;
11026 for (i = 0; i < ARRAY_SIZE (bdesc_dst); i++, d++)
11027 if (d->code == fcode)
11028 {
11029 arg0 = CALL_EXPR_ARG (exp, 0);
11030 arg1 = CALL_EXPR_ARG (exp, 1);
11031 arg2 = CALL_EXPR_ARG (exp, 2);
11032 op0 = expand_normal (arg0);
11033 op1 = expand_normal (arg1);
11034 op2 = expand_normal (arg2);
11035 mode0 = insn_data[d->icode].operand[0].mode;
11036 mode1 = insn_data[d->icode].operand[1].mode;
11037
11038 /* Invalid arguments, bail out before generating bad rtl. */
11039 if (arg0 == error_mark_node
11040 || arg1 == error_mark_node
11041 || arg2 == error_mark_node)
11042 return const0_rtx;
11043
11044 *expandedp = true;
11045 STRIP_NOPS (arg2);
11046 if (TREE_CODE (arg2) != INTEGER_CST
11047 || TREE_INT_CST_LOW (arg2) & ~0x3)
11048 {
11049 error ("argument to %qs must be a 2-bit unsigned literal", d->name);
11050 return const0_rtx;
11051 }
11052
11053 if (! (*insn_data[d->icode].operand[0].predicate) (op0, mode0))
11054 op0 = copy_to_mode_reg (Pmode, op0);
11055 if (! (*insn_data[d->icode].operand[1].predicate) (op1, mode1))
11056 op1 = copy_to_mode_reg (mode1, op1);
11057
11058 pat = GEN_FCN (d->icode) (op0, op1, op2);
11059 if (pat != 0)
11060 emit_insn (pat);
11061
11062 return NULL_RTX;
11063 }
11064
11065 return NULL_RTX;
11066 }
11067
11068 /* Expand vec_init builtin. */
11069 static rtx
11070 altivec_expand_vec_init_builtin (tree type, tree exp, rtx target)
11071 {
11072 enum machine_mode tmode = TYPE_MODE (type);
11073 enum machine_mode inner_mode = GET_MODE_INNER (tmode);
11074 int i, n_elt = GET_MODE_NUNITS (tmode);
11075 rtvec v = rtvec_alloc (n_elt);
11076
11077 gcc_assert (VECTOR_MODE_P (tmode));
11078 gcc_assert (n_elt == call_expr_nargs (exp));
11079
11080 for (i = 0; i < n_elt; ++i)
11081 {
11082 rtx x = expand_normal (CALL_EXPR_ARG (exp, i));
11083 RTVEC_ELT (v, i) = gen_lowpart (inner_mode, x);
11084 }
11085
11086 if (!target || !register_operand (target, tmode))
11087 target = gen_reg_rtx (tmode);
11088
11089 rs6000_expand_vector_init (target, gen_rtx_PARALLEL (tmode, v));
11090 return target;
11091 }
11092
11093 /* Return the integer constant in ARG. Constrain it to be in the range
11094 of the subparts of VEC_TYPE; issue an error if not. */
11095
11096 static int
11097 get_element_number (tree vec_type, tree arg)
11098 {
11099 unsigned HOST_WIDE_INT elt, max = TYPE_VECTOR_SUBPARTS (vec_type) - 1;
11100
11101 if (!host_integerp (arg, 1)
11102 || (elt = tree_low_cst (arg, 1), elt > max))
11103 {
11104 error ("selector must be an integer constant in the range 0..%wi", max);
11105 return 0;
11106 }
11107
11108 return elt;
11109 }
11110
11111 /* Expand vec_set builtin. */
11112 static rtx
11113 altivec_expand_vec_set_builtin (tree exp)
11114 {
11115 enum machine_mode tmode, mode1;
11116 tree arg0, arg1, arg2;
11117 int elt;
11118 rtx op0, op1;
11119
11120 arg0 = CALL_EXPR_ARG (exp, 0);
11121 arg1 = CALL_EXPR_ARG (exp, 1);
11122 arg2 = CALL_EXPR_ARG (exp, 2);
11123
11124 tmode = TYPE_MODE (TREE_TYPE (arg0));
11125 mode1 = TYPE_MODE (TREE_TYPE (TREE_TYPE (arg0)));
11126 gcc_assert (VECTOR_MODE_P (tmode));
11127
11128 op0 = expand_expr (arg0, NULL_RTX, tmode, EXPAND_NORMAL);
11129 op1 = expand_expr (arg1, NULL_RTX, mode1, EXPAND_NORMAL);
11130 elt = get_element_number (TREE_TYPE (arg0), arg2);
11131
11132 if (GET_MODE (op1) != mode1 && GET_MODE (op1) != VOIDmode)
11133 op1 = convert_modes (mode1, GET_MODE (op1), op1, true);
11134
11135 op0 = force_reg (tmode, op0);
11136 op1 = force_reg (mode1, op1);
11137
11138 rs6000_expand_vector_set (op0, op1, elt);
11139
11140 return op0;
11141 }
11142
11143 /* Expand vec_ext builtin. */
11144 static rtx
11145 altivec_expand_vec_ext_builtin (tree exp, rtx target)
11146 {
11147 enum machine_mode tmode, mode0;
11148 tree arg0, arg1;
11149 int elt;
11150 rtx op0;
11151
11152 arg0 = CALL_EXPR_ARG (exp, 0);
11153 arg1 = CALL_EXPR_ARG (exp, 1);
11154
11155 op0 = expand_normal (arg0);
11156 elt = get_element_number (TREE_TYPE (arg0), arg1);
11157
11158 tmode = TYPE_MODE (TREE_TYPE (TREE_TYPE (arg0)));
11159 mode0 = TYPE_MODE (TREE_TYPE (arg0));
11160 gcc_assert (VECTOR_MODE_P (mode0));
11161
11162 op0 = force_reg (mode0, op0);
11163
11164 if (optimize || !target || !register_operand (target, tmode))
11165 target = gen_reg_rtx (tmode);
11166
11167 rs6000_expand_vector_extract (target, op0, elt);
11168
11169 return target;
11170 }
11171
11172 /* Expand the builtin in EXP and store the result in TARGET. Store
11173 true in *EXPANDEDP if we found a builtin to expand. */
11174 static rtx
11175 altivec_expand_builtin (tree exp, rtx target, bool *expandedp)
11176 {
11177 const struct builtin_description *d;
11178 const struct builtin_description_predicates *dp;
11179 size_t i;
11180 enum insn_code icode;
11181 tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
11182 tree arg0;
11183 rtx op0, pat;
11184 enum machine_mode tmode, mode0;
11185 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
11186
11187 if ((fcode >= ALTIVEC_BUILTIN_OVERLOADED_FIRST
11188 && fcode <= ALTIVEC_BUILTIN_OVERLOADED_LAST)
11189 || (fcode >= VSX_BUILTIN_OVERLOADED_FIRST
11190 && fcode <= VSX_BUILTIN_OVERLOADED_LAST))
11191 {
11192 *expandedp = true;
11193 error ("unresolved overload for Altivec builtin %qF", fndecl);
11194 return const0_rtx;
11195 }
11196
11197 target = altivec_expand_ld_builtin (exp, target, expandedp);
11198 if (*expandedp)
11199 return target;
11200
11201 target = altivec_expand_st_builtin (exp, target, expandedp);
11202 if (*expandedp)
11203 return target;
11204
11205 target = altivec_expand_dst_builtin (exp, target, expandedp);
11206 if (*expandedp)
11207 return target;
11208
11209 *expandedp = true;
11210
11211 switch (fcode)
11212 {
11213 case ALTIVEC_BUILTIN_STVX:
11214 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvx, exp);
11215 case ALTIVEC_BUILTIN_STVEBX:
11216 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvebx, exp);
11217 case ALTIVEC_BUILTIN_STVEHX:
11218 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvehx, exp);
11219 case ALTIVEC_BUILTIN_STVEWX:
11220 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvewx, exp);
11221 case ALTIVEC_BUILTIN_STVXL:
11222 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvxl, exp);
11223
11224 case ALTIVEC_BUILTIN_STVLX:
11225 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvlx, exp);
11226 case ALTIVEC_BUILTIN_STVLXL:
11227 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvlxl, exp);
11228 case ALTIVEC_BUILTIN_STVRX:
11229 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvrx, exp);
11230 case ALTIVEC_BUILTIN_STVRXL:
11231 return altivec_expand_stv_builtin (CODE_FOR_altivec_stvrxl, exp);
11232
11233 case ALTIVEC_BUILTIN_MFVSCR:
11234 icode = CODE_FOR_altivec_mfvscr;
11235 tmode = insn_data[icode].operand[0].mode;
11236
11237 if (target == 0
11238 || GET_MODE (target) != tmode
11239 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
11240 target = gen_reg_rtx (tmode);
11241
11242 pat = GEN_FCN (icode) (target);
11243 if (! pat)
11244 return 0;
11245 emit_insn (pat);
11246 return target;
11247
11248 case ALTIVEC_BUILTIN_MTVSCR:
11249 icode = CODE_FOR_altivec_mtvscr;
11250 arg0 = CALL_EXPR_ARG (exp, 0);
11251 op0 = expand_normal (arg0);
11252 mode0 = insn_data[icode].operand[0].mode;
11253
11254 /* If we got invalid arguments bail out before generating bad rtl. */
11255 if (arg0 == error_mark_node)
11256 return const0_rtx;
11257
11258 if (! (*insn_data[icode].operand[0].predicate) (op0, mode0))
11259 op0 = copy_to_mode_reg (mode0, op0);
11260
11261 pat = GEN_FCN (icode) (op0);
11262 if (pat)
11263 emit_insn (pat);
11264 return NULL_RTX;
11265
11266 case ALTIVEC_BUILTIN_DSSALL:
11267 emit_insn (gen_altivec_dssall ());
11268 return NULL_RTX;
11269
11270 case ALTIVEC_BUILTIN_DSS:
11271 icode = CODE_FOR_altivec_dss;
11272 arg0 = CALL_EXPR_ARG (exp, 0);
11273 STRIP_NOPS (arg0);
11274 op0 = expand_normal (arg0);
11275 mode0 = insn_data[icode].operand[0].mode;
11276
11277 /* If we got invalid arguments bail out before generating bad rtl. */
11278 if (arg0 == error_mark_node)
11279 return const0_rtx;
11280
11281 if (TREE_CODE (arg0) != INTEGER_CST
11282 || TREE_INT_CST_LOW (arg0) & ~0x3)
11283 {
11284 error ("argument to dss must be a 2-bit unsigned literal");
11285 return const0_rtx;
11286 }
11287
11288 if (! (*insn_data[icode].operand[0].predicate) (op0, mode0))
11289 op0 = copy_to_mode_reg (mode0, op0);
11290
11291 emit_insn (gen_altivec_dss (op0));
11292 return NULL_RTX;
11293
11294 case ALTIVEC_BUILTIN_VEC_INIT_V4SI:
11295 case ALTIVEC_BUILTIN_VEC_INIT_V8HI:
11296 case ALTIVEC_BUILTIN_VEC_INIT_V16QI:
11297 case ALTIVEC_BUILTIN_VEC_INIT_V4SF:
11298 case VSX_BUILTIN_VEC_INIT_V2DF:
11299 case VSX_BUILTIN_VEC_INIT_V2DI:
11300 return altivec_expand_vec_init_builtin (TREE_TYPE (exp), exp, target);
11301
11302 case ALTIVEC_BUILTIN_VEC_SET_V4SI:
11303 case ALTIVEC_BUILTIN_VEC_SET_V8HI:
11304 case ALTIVEC_BUILTIN_VEC_SET_V16QI:
11305 case ALTIVEC_BUILTIN_VEC_SET_V4SF:
11306 case VSX_BUILTIN_VEC_SET_V2DF:
11307 case VSX_BUILTIN_VEC_SET_V2DI:
11308 return altivec_expand_vec_set_builtin (exp);
11309
11310 case ALTIVEC_BUILTIN_VEC_EXT_V4SI:
11311 case ALTIVEC_BUILTIN_VEC_EXT_V8HI:
11312 case ALTIVEC_BUILTIN_VEC_EXT_V16QI:
11313 case ALTIVEC_BUILTIN_VEC_EXT_V4SF:
11314 case VSX_BUILTIN_VEC_EXT_V2DF:
11315 case VSX_BUILTIN_VEC_EXT_V2DI:
11316 return altivec_expand_vec_ext_builtin (exp, target);
11317
11318 default:
11319 break;
11320 /* Fall through. */
11321 }
11322
11323 /* Expand abs* operations. */
11324 d = bdesc_abs;
11325 for (i = 0; i < ARRAY_SIZE (bdesc_abs); i++, d++)
11326 if (d->code == fcode)
11327 return altivec_expand_abs_builtin (d->icode, exp, target);
11328
11329 /* Expand the AltiVec predicates. */
11330 dp = bdesc_altivec_preds;
11331 for (i = 0; i < ARRAY_SIZE (bdesc_altivec_preds); i++, dp++)
11332 if (dp->code == fcode)
11333 return altivec_expand_predicate_builtin (dp->icode, exp, target);
11334
11335 /* LV* are funky. We initialized them differently. */
11336 switch (fcode)
11337 {
11338 case ALTIVEC_BUILTIN_LVSL:
11339 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvsl,
11340 exp, target, false);
11341 case ALTIVEC_BUILTIN_LVSR:
11342 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvsr,
11343 exp, target, false);
11344 case ALTIVEC_BUILTIN_LVEBX:
11345 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvebx,
11346 exp, target, false);
11347 case ALTIVEC_BUILTIN_LVEHX:
11348 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvehx,
11349 exp, target, false);
11350 case ALTIVEC_BUILTIN_LVEWX:
11351 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvewx,
11352 exp, target, false);
11353 case ALTIVEC_BUILTIN_LVXL:
11354 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvxl,
11355 exp, target, false);
11356 case ALTIVEC_BUILTIN_LVX:
11357 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvx,
11358 exp, target, false);
11359 case ALTIVEC_BUILTIN_LVLX:
11360 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvlx,
11361 exp, target, true);
11362 case ALTIVEC_BUILTIN_LVLXL:
11363 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvlxl,
11364 exp, target, true);
11365 case ALTIVEC_BUILTIN_LVRX:
11366 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvrx,
11367 exp, target, true);
11368 case ALTIVEC_BUILTIN_LVRXL:
11369 return altivec_expand_lv_builtin (CODE_FOR_altivec_lvrxl,
11370 exp, target, true);
11371 default:
11372 break;
11373 /* Fall through. */
11374 }
11375
11376 *expandedp = false;
11377 return NULL_RTX;
11378 }
11379
11380 /* Expand the builtin in EXP and store the result in TARGET. Store
11381 true in *EXPANDEDP if we found a builtin to expand. */
11382 static rtx
11383 paired_expand_builtin (tree exp, rtx target, bool * expandedp)
11384 {
11385 tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
11386 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
11387 const struct builtin_description *d;
11388 size_t i;
11389
11390 *expandedp = true;
11391
11392 switch (fcode)
11393 {
11394 case PAIRED_BUILTIN_STX:
11395 return paired_expand_stv_builtin (CODE_FOR_paired_stx, exp);
11396 case PAIRED_BUILTIN_LX:
11397 return paired_expand_lv_builtin (CODE_FOR_paired_lx, exp, target);
11398 default:
11399 break;
11400 /* Fall through. */
11401 }
11402
11403 /* Expand the paired predicates. */
11404 d = bdesc_paired_preds;
11405 for (i = 0; i < ARRAY_SIZE (bdesc_paired_preds); i++, d++)
11406 if (d->code == fcode)
11407 return paired_expand_predicate_builtin (d->icode, exp, target);
11408
11409 *expandedp = false;
11410 return NULL_RTX;
11411 }
11412
11413 /* Binops that need to be initialized manually, but can be expanded
11414 automagically by rs6000_expand_binop_builtin. */
11415 static struct builtin_description bdesc_2arg_spe[] =
11416 {
11417 { 0, CODE_FOR_spe_evlddx, "__builtin_spe_evlddx", SPE_BUILTIN_EVLDDX },
11418 { 0, CODE_FOR_spe_evldwx, "__builtin_spe_evldwx", SPE_BUILTIN_EVLDWX },
11419 { 0, CODE_FOR_spe_evldhx, "__builtin_spe_evldhx", SPE_BUILTIN_EVLDHX },
11420 { 0, CODE_FOR_spe_evlwhex, "__builtin_spe_evlwhex", SPE_BUILTIN_EVLWHEX },
11421 { 0, CODE_FOR_spe_evlwhoux, "__builtin_spe_evlwhoux", SPE_BUILTIN_EVLWHOUX },
11422 { 0, CODE_FOR_spe_evlwhosx, "__builtin_spe_evlwhosx", SPE_BUILTIN_EVLWHOSX },
11423 { 0, CODE_FOR_spe_evlwwsplatx, "__builtin_spe_evlwwsplatx", SPE_BUILTIN_EVLWWSPLATX },
11424 { 0, CODE_FOR_spe_evlwhsplatx, "__builtin_spe_evlwhsplatx", SPE_BUILTIN_EVLWHSPLATX },
11425 { 0, CODE_FOR_spe_evlhhesplatx, "__builtin_spe_evlhhesplatx", SPE_BUILTIN_EVLHHESPLATX },
11426 { 0, CODE_FOR_spe_evlhhousplatx, "__builtin_spe_evlhhousplatx", SPE_BUILTIN_EVLHHOUSPLATX },
11427 { 0, CODE_FOR_spe_evlhhossplatx, "__builtin_spe_evlhhossplatx", SPE_BUILTIN_EVLHHOSSPLATX },
11428 { 0, CODE_FOR_spe_evldd, "__builtin_spe_evldd", SPE_BUILTIN_EVLDD },
11429 { 0, CODE_FOR_spe_evldw, "__builtin_spe_evldw", SPE_BUILTIN_EVLDW },
11430 { 0, CODE_FOR_spe_evldh, "__builtin_spe_evldh", SPE_BUILTIN_EVLDH },
11431 { 0, CODE_FOR_spe_evlwhe, "__builtin_spe_evlwhe", SPE_BUILTIN_EVLWHE },
11432 { 0, CODE_FOR_spe_evlwhou, "__builtin_spe_evlwhou", SPE_BUILTIN_EVLWHOU },
11433 { 0, CODE_FOR_spe_evlwhos, "__builtin_spe_evlwhos", SPE_BUILTIN_EVLWHOS },
11434 { 0, CODE_FOR_spe_evlwwsplat, "__builtin_spe_evlwwsplat", SPE_BUILTIN_EVLWWSPLAT },
11435 { 0, CODE_FOR_spe_evlwhsplat, "__builtin_spe_evlwhsplat", SPE_BUILTIN_EVLWHSPLAT },
11436 { 0, CODE_FOR_spe_evlhhesplat, "__builtin_spe_evlhhesplat", SPE_BUILTIN_EVLHHESPLAT },
11437 { 0, CODE_FOR_spe_evlhhousplat, "__builtin_spe_evlhhousplat", SPE_BUILTIN_EVLHHOUSPLAT },
11438 { 0, CODE_FOR_spe_evlhhossplat, "__builtin_spe_evlhhossplat", SPE_BUILTIN_EVLHHOSSPLAT }
11439 };
11440
11441 /* Expand the builtin in EXP and store the result in TARGET. Store
11442 true in *EXPANDEDP if we found a builtin to expand.
11443
11444 This expands the SPE builtins that are not simple unary and binary
11445 operations. */
11446 static rtx
11447 spe_expand_builtin (tree exp, rtx target, bool *expandedp)
11448 {
11449 tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
11450 tree arg1, arg0;
11451 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
11452 enum insn_code icode;
11453 enum machine_mode tmode, mode0;
11454 rtx pat, op0;
11455 struct builtin_description *d;
11456 size_t i;
11457
11458 *expandedp = true;
11459
11460 /* Syntax check for a 5-bit unsigned immediate. */
11461 switch (fcode)
11462 {
11463 case SPE_BUILTIN_EVSTDD:
11464 case SPE_BUILTIN_EVSTDH:
11465 case SPE_BUILTIN_EVSTDW:
11466 case SPE_BUILTIN_EVSTWHE:
11467 case SPE_BUILTIN_EVSTWHO:
11468 case SPE_BUILTIN_EVSTWWE:
11469 case SPE_BUILTIN_EVSTWWO:
11470 arg1 = CALL_EXPR_ARG (exp, 2);
11471 if (TREE_CODE (arg1) != INTEGER_CST
11472 || TREE_INT_CST_LOW (arg1) & ~0x1f)
11473 {
11474 error ("argument 2 must be a 5-bit unsigned literal");
11475 return const0_rtx;
11476 }
11477 break;
11478 default:
11479 break;
11480 }
11481
11482 /* The evsplat*i instructions are not quite generic. */
11483 switch (fcode)
11484 {
11485 case SPE_BUILTIN_EVSPLATFI:
11486 return rs6000_expand_unop_builtin (CODE_FOR_spe_evsplatfi,
11487 exp, target);
11488 case SPE_BUILTIN_EVSPLATI:
11489 return rs6000_expand_unop_builtin (CODE_FOR_spe_evsplati,
11490 exp, target);
11491 default:
11492 break;
11493 }
11494
11495 d = (struct builtin_description *) bdesc_2arg_spe;
11496 for (i = 0; i < ARRAY_SIZE (bdesc_2arg_spe); ++i, ++d)
11497 if (d->code == fcode)
11498 return rs6000_expand_binop_builtin (d->icode, exp, target);
11499
11500 d = (struct builtin_description *) bdesc_spe_predicates;
11501 for (i = 0; i < ARRAY_SIZE (bdesc_spe_predicates); ++i, ++d)
11502 if (d->code == fcode)
11503 return spe_expand_predicate_builtin (d->icode, exp, target);
11504
11505 d = (struct builtin_description *) bdesc_spe_evsel;
11506 for (i = 0; i < ARRAY_SIZE (bdesc_spe_evsel); ++i, ++d)
11507 if (d->code == fcode)
11508 return spe_expand_evsel_builtin (d->icode, exp, target);
11509
11510 switch (fcode)
11511 {
11512 case SPE_BUILTIN_EVSTDDX:
11513 return spe_expand_stv_builtin (CODE_FOR_spe_evstddx, exp);
11514 case SPE_BUILTIN_EVSTDHX:
11515 return spe_expand_stv_builtin (CODE_FOR_spe_evstdhx, exp);
11516 case SPE_BUILTIN_EVSTDWX:
11517 return spe_expand_stv_builtin (CODE_FOR_spe_evstdwx, exp);
11518 case SPE_BUILTIN_EVSTWHEX:
11519 return spe_expand_stv_builtin (CODE_FOR_spe_evstwhex, exp);
11520 case SPE_BUILTIN_EVSTWHOX:
11521 return spe_expand_stv_builtin (CODE_FOR_spe_evstwhox, exp);
11522 case SPE_BUILTIN_EVSTWWEX:
11523 return spe_expand_stv_builtin (CODE_FOR_spe_evstwwex, exp);
11524 case SPE_BUILTIN_EVSTWWOX:
11525 return spe_expand_stv_builtin (CODE_FOR_spe_evstwwox, exp);
11526 case SPE_BUILTIN_EVSTDD:
11527 return spe_expand_stv_builtin (CODE_FOR_spe_evstdd, exp);
11528 case SPE_BUILTIN_EVSTDH:
11529 return spe_expand_stv_builtin (CODE_FOR_spe_evstdh, exp);
11530 case SPE_BUILTIN_EVSTDW:
11531 return spe_expand_stv_builtin (CODE_FOR_spe_evstdw, exp);
11532 case SPE_BUILTIN_EVSTWHE:
11533 return spe_expand_stv_builtin (CODE_FOR_spe_evstwhe, exp);
11534 case SPE_BUILTIN_EVSTWHO:
11535 return spe_expand_stv_builtin (CODE_FOR_spe_evstwho, exp);
11536 case SPE_BUILTIN_EVSTWWE:
11537 return spe_expand_stv_builtin (CODE_FOR_spe_evstwwe, exp);
11538 case SPE_BUILTIN_EVSTWWO:
11539 return spe_expand_stv_builtin (CODE_FOR_spe_evstwwo, exp);
11540 case SPE_BUILTIN_MFSPEFSCR:
11541 icode = CODE_FOR_spe_mfspefscr;
11542 tmode = insn_data[icode].operand[0].mode;
11543
11544 if (target == 0
11545 || GET_MODE (target) != tmode
11546 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
11547 target = gen_reg_rtx (tmode);
11548
11549 pat = GEN_FCN (icode) (target);
11550 if (! pat)
11551 return 0;
11552 emit_insn (pat);
11553 return target;
11554 case SPE_BUILTIN_MTSPEFSCR:
11555 icode = CODE_FOR_spe_mtspefscr;
11556 arg0 = CALL_EXPR_ARG (exp, 0);
11557 op0 = expand_normal (arg0);
11558 mode0 = insn_data[icode].operand[0].mode;
11559
11560 if (arg0 == error_mark_node)
11561 return const0_rtx;
11562
11563 if (! (*insn_data[icode].operand[0].predicate) (op0, mode0))
11564 op0 = copy_to_mode_reg (mode0, op0);
11565
11566 pat = GEN_FCN (icode) (op0);
11567 if (pat)
11568 emit_insn (pat);
11569 return NULL_RTX;
11570 default:
11571 break;
11572 }
11573
11574 *expandedp = false;
11575 return NULL_RTX;
11576 }
11577
11578 static rtx
11579 paired_expand_predicate_builtin (enum insn_code icode, tree exp, rtx target)
11580 {
11581 rtx pat, scratch, tmp;
11582 tree form = CALL_EXPR_ARG (exp, 0);
11583 tree arg0 = CALL_EXPR_ARG (exp, 1);
11584 tree arg1 = CALL_EXPR_ARG (exp, 2);
11585 rtx op0 = expand_normal (arg0);
11586 rtx op1 = expand_normal (arg1);
11587 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
11588 enum machine_mode mode1 = insn_data[icode].operand[2].mode;
11589 int form_int;
11590 enum rtx_code code;
11591
11592 if (TREE_CODE (form) != INTEGER_CST)
11593 {
11594 error ("argument 1 of __builtin_paired_predicate must be a constant");
11595 return const0_rtx;
11596 }
11597 else
11598 form_int = TREE_INT_CST_LOW (form);
11599
11600 gcc_assert (mode0 == mode1);
11601
11602 if (arg0 == error_mark_node || arg1 == error_mark_node)
11603 return const0_rtx;
11604
11605 if (target == 0
11606 || GET_MODE (target) != SImode
11607 || !(*insn_data[icode].operand[0].predicate) (target, SImode))
11608 target = gen_reg_rtx (SImode);
11609 if (!(*insn_data[icode].operand[1].predicate) (op0, mode0))
11610 op0 = copy_to_mode_reg (mode0, op0);
11611 if (!(*insn_data[icode].operand[2].predicate) (op1, mode1))
11612 op1 = copy_to_mode_reg (mode1, op1);
11613
11614 scratch = gen_reg_rtx (CCFPmode);
11615
11616 pat = GEN_FCN (icode) (scratch, op0, op1);
11617 if (!pat)
11618 return const0_rtx;
11619
11620 emit_insn (pat);
11621
11622 switch (form_int)
11623 {
11624 /* LT bit. */
11625 case 0:
11626 code = LT;
11627 break;
11628 /* GT bit. */
11629 case 1:
11630 code = GT;
11631 break;
11632 /* EQ bit. */
11633 case 2:
11634 code = EQ;
11635 break;
11636 /* UN bit. */
11637 case 3:
11638 emit_insn (gen_move_from_CR_ov_bit (target, scratch));
11639 return target;
11640 default:
11641 error ("argument 1 of __builtin_paired_predicate is out of range");
11642 return const0_rtx;
11643 }
11644
11645 tmp = gen_rtx_fmt_ee (code, SImode, scratch, const0_rtx);
11646 emit_move_insn (target, tmp);
11647 return target;
11648 }
11649
11650 static rtx
11651 spe_expand_predicate_builtin (enum insn_code icode, tree exp, rtx target)
11652 {
11653 rtx pat, scratch, tmp;
11654 tree form = CALL_EXPR_ARG (exp, 0);
11655 tree arg0 = CALL_EXPR_ARG (exp, 1);
11656 tree arg1 = CALL_EXPR_ARG (exp, 2);
11657 rtx op0 = expand_normal (arg0);
11658 rtx op1 = expand_normal (arg1);
11659 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
11660 enum machine_mode mode1 = insn_data[icode].operand[2].mode;
11661 int form_int;
11662 enum rtx_code code;
11663
11664 if (TREE_CODE (form) != INTEGER_CST)
11665 {
11666 error ("argument 1 of __builtin_spe_predicate must be a constant");
11667 return const0_rtx;
11668 }
11669 else
11670 form_int = TREE_INT_CST_LOW (form);
11671
11672 gcc_assert (mode0 == mode1);
11673
11674 if (arg0 == error_mark_node || arg1 == error_mark_node)
11675 return const0_rtx;
11676
11677 if (target == 0
11678 || GET_MODE (target) != SImode
11679 || ! (*insn_data[icode].operand[0].predicate) (target, SImode))
11680 target = gen_reg_rtx (SImode);
11681
11682 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
11683 op0 = copy_to_mode_reg (mode0, op0);
11684 if (! (*insn_data[icode].operand[2].predicate) (op1, mode1))
11685 op1 = copy_to_mode_reg (mode1, op1);
11686
11687 scratch = gen_reg_rtx (CCmode);
11688
11689 pat = GEN_FCN (icode) (scratch, op0, op1);
11690 if (! pat)
11691 return const0_rtx;
11692 emit_insn (pat);
11693
11694 /* There are 4 variants for each predicate: _any_, _all_, _upper_,
11695 _lower_. We use one compare, but look in different bits of the
11696 CR for each variant.
11697
11698 There are 2 elements in each SPE simd type (upper/lower). The CR
11699 bits are set as follows:
11700
11701 BIT0 | BIT 1 | BIT 2 | BIT 3
11702 U | L | (U | L) | (U & L)
11703
11704 So, for an "all" relationship, BIT 3 would be set.
11705 For an "any" relationship, BIT 2 would be set. Etc.
11706
11707 Following traditional nomenclature, these bits map to:
11708
11709 BIT0 | BIT 1 | BIT 2 | BIT 3
11710 LT | GT | EQ | OV
11711
11712 Later, we will generate rtl to look in the LT/EQ/EQ/OV bits.
11713 */
11714
11715 switch (form_int)
11716 {
11717 /* All variant. OV bit. */
11718 case 0:
11719 /* We need to get to the OV bit, which is the ORDERED bit. We
11720 could generate (ordered:SI (reg:CC xx) (const_int 0)), but
11721 that's ugly and will make validate_condition_mode die.
11722 So let's just use another pattern. */
11723 emit_insn (gen_move_from_CR_ov_bit (target, scratch));
11724 return target;
11725 /* Any variant. EQ bit. */
11726 case 1:
11727 code = EQ;
11728 break;
11729 /* Upper variant. LT bit. */
11730 case 2:
11731 code = LT;
11732 break;
11733 /* Lower variant. GT bit. */
11734 case 3:
11735 code = GT;
11736 break;
11737 default:
11738 error ("argument 1 of __builtin_spe_predicate is out of range");
11739 return const0_rtx;
11740 }
11741
11742 tmp = gen_rtx_fmt_ee (code, SImode, scratch, const0_rtx);
11743 emit_move_insn (target, tmp);
11744
11745 return target;
11746 }
11747
11748 /* The evsel builtins look like this:
11749
11750 e = __builtin_spe_evsel_OP (a, b, c, d);
11751
11752 and work like this:
11753
11754 e[upper] = a[upper] *OP* b[upper] ? c[upper] : d[upper];
11755 e[lower] = a[lower] *OP* b[lower] ? c[lower] : d[lower];
11756 */
11757
11758 static rtx
11759 spe_expand_evsel_builtin (enum insn_code icode, tree exp, rtx target)
11760 {
11761 rtx pat, scratch;
11762 tree arg0 = CALL_EXPR_ARG (exp, 0);
11763 tree arg1 = CALL_EXPR_ARG (exp, 1);
11764 tree arg2 = CALL_EXPR_ARG (exp, 2);
11765 tree arg3 = CALL_EXPR_ARG (exp, 3);
11766 rtx op0 = expand_normal (arg0);
11767 rtx op1 = expand_normal (arg1);
11768 rtx op2 = expand_normal (arg2);
11769 rtx op3 = expand_normal (arg3);
11770 enum machine_mode mode0 = insn_data[icode].operand[1].mode;
11771 enum machine_mode mode1 = insn_data[icode].operand[2].mode;
11772
11773 gcc_assert (mode0 == mode1);
11774
11775 if (arg0 == error_mark_node || arg1 == error_mark_node
11776 || arg2 == error_mark_node || arg3 == error_mark_node)
11777 return const0_rtx;
11778
11779 if (target == 0
11780 || GET_MODE (target) != mode0
11781 || ! (*insn_data[icode].operand[0].predicate) (target, mode0))
11782 target = gen_reg_rtx (mode0);
11783
11784 if (! (*insn_data[icode].operand[1].predicate) (op0, mode0))
11785 op0 = copy_to_mode_reg (mode0, op0);
11786 if (! (*insn_data[icode].operand[1].predicate) (op1, mode1))
11787 op1 = copy_to_mode_reg (mode0, op1);
11788 if (! (*insn_data[icode].operand[1].predicate) (op2, mode1))
11789 op2 = copy_to_mode_reg (mode0, op2);
11790 if (! (*insn_data[icode].operand[1].predicate) (op3, mode1))
11791 op3 = copy_to_mode_reg (mode0, op3);
11792
11793 /* Generate the compare. */
11794 scratch = gen_reg_rtx (CCmode);
11795 pat = GEN_FCN (icode) (scratch, op0, op1);
11796 if (! pat)
11797 return const0_rtx;
11798 emit_insn (pat);
11799
11800 if (mode0 == V2SImode)
11801 emit_insn (gen_spe_evsel (target, op2, op3, scratch));
11802 else
11803 emit_insn (gen_spe_evsel_fs (target, op2, op3, scratch));
11804
11805 return target;
11806 }
11807
11808 /* Expand an expression EXP that calls a built-in function,
11809 with result going to TARGET if that's convenient
11810 (and in mode MODE if that's convenient).
11811 SUBTARGET may be used as the target for computing one of EXP's operands.
11812 IGNORE is nonzero if the value is to be ignored. */
11813
11814 static rtx
11815 rs6000_expand_builtin (tree exp, rtx target, rtx subtarget ATTRIBUTE_UNUSED,
11816 enum machine_mode mode ATTRIBUTE_UNUSED,
11817 int ignore ATTRIBUTE_UNUSED)
11818 {
11819 tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
11820 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
11821 const struct builtin_description *d;
11822 size_t i;
11823 rtx ret;
11824 bool success;
11825
11826 switch (fcode)
11827 {
11828 case RS6000_BUILTIN_RECIP:
11829 return rs6000_expand_binop_builtin (CODE_FOR_recipdf3, exp, target);
11830
11831 case RS6000_BUILTIN_RECIPF:
11832 return rs6000_expand_binop_builtin (CODE_FOR_recipsf3, exp, target);
11833
11834 case RS6000_BUILTIN_RSQRTF:
11835 return rs6000_expand_unop_builtin (CODE_FOR_rsqrtsf2, exp, target);
11836
11837 case RS6000_BUILTIN_RSQRT:
11838 return rs6000_expand_unop_builtin (CODE_FOR_rsqrtdf2, exp, target);
11839
11840 case RS6000_BUILTIN_BSWAP_HI:
11841 return rs6000_expand_unop_builtin (CODE_FOR_bswaphi2, exp, target);
11842
11843 case POWER7_BUILTIN_BPERMD:
11844 return rs6000_expand_binop_builtin (((TARGET_64BIT)
11845 ? CODE_FOR_bpermd_di
11846 : CODE_FOR_bpermd_si), exp, target);
11847
11848 case ALTIVEC_BUILTIN_MASK_FOR_LOAD:
11849 case ALTIVEC_BUILTIN_MASK_FOR_STORE:
11850 {
11851 int icode = (int) CODE_FOR_altivec_lvsr;
11852 enum machine_mode tmode = insn_data[icode].operand[0].mode;
11853 enum machine_mode mode = insn_data[icode].operand[1].mode;
11854 tree arg;
11855 rtx op, addr, pat;
11856
11857 gcc_assert (TARGET_ALTIVEC);
11858
11859 arg = CALL_EXPR_ARG (exp, 0);
11860 gcc_assert (POINTER_TYPE_P (TREE_TYPE (arg)));
11861 op = expand_expr (arg, NULL_RTX, Pmode, EXPAND_NORMAL);
11862 addr = memory_address (mode, op);
11863 if (fcode == ALTIVEC_BUILTIN_MASK_FOR_STORE)
11864 op = addr;
11865 else
11866 {
11867 /* For the load case need to negate the address. */
11868 op = gen_reg_rtx (GET_MODE (addr));
11869 emit_insn (gen_rtx_SET (VOIDmode, op,
11870 gen_rtx_NEG (GET_MODE (addr), addr)));
11871 }
11872 op = gen_rtx_MEM (mode, op);
11873
11874 if (target == 0
11875 || GET_MODE (target) != tmode
11876 || ! (*insn_data[icode].operand[0].predicate) (target, tmode))
11877 target = gen_reg_rtx (tmode);
11878
11879 /*pat = gen_altivec_lvsr (target, op);*/
11880 pat = GEN_FCN (icode) (target, op);
11881 if (!pat)
11882 return 0;
11883 emit_insn (pat);
11884
11885 return target;
11886 }
11887
11888 case ALTIVEC_BUILTIN_VCFUX:
11889 case ALTIVEC_BUILTIN_VCFSX:
11890 case ALTIVEC_BUILTIN_VCTUXS:
11891 case ALTIVEC_BUILTIN_VCTSXS:
11892 /* FIXME: There's got to be a nicer way to handle this case than
11893 constructing a new CALL_EXPR. */
11894 if (call_expr_nargs (exp) == 1)
11895 {
11896 exp = build_call_nary (TREE_TYPE (exp), CALL_EXPR_FN (exp),
11897 2, CALL_EXPR_ARG (exp, 0), integer_zero_node);
11898 }
11899 break;
11900
11901 default:
11902 break;
11903 }
11904
11905 if (TARGET_ALTIVEC)
11906 {
11907 ret = altivec_expand_builtin (exp, target, &success);
11908
11909 if (success)
11910 return ret;
11911 }
11912 if (TARGET_SPE)
11913 {
11914 ret = spe_expand_builtin (exp, target, &success);
11915
11916 if (success)
11917 return ret;
11918 }
11919 if (TARGET_PAIRED_FLOAT)
11920 {
11921 ret = paired_expand_builtin (exp, target, &success);
11922
11923 if (success)
11924 return ret;
11925 }
11926
11927 gcc_assert (TARGET_ALTIVEC || TARGET_VSX || TARGET_SPE || TARGET_PAIRED_FLOAT);
11928
11929 /* Handle simple unary operations. */
11930 d = (struct builtin_description *) bdesc_1arg;
11931 for (i = 0; i < ARRAY_SIZE (bdesc_1arg); i++, d++)
11932 if (d->code == fcode)
11933 return rs6000_expand_unop_builtin (d->icode, exp, target);
11934
11935 /* Handle simple binary operations. */
11936 d = (struct builtin_description *) bdesc_2arg;
11937 for (i = 0; i < ARRAY_SIZE (bdesc_2arg); i++, d++)
11938 if (d->code == fcode)
11939 return rs6000_expand_binop_builtin (d->icode, exp, target);
11940
11941 /* Handle simple ternary operations. */
11942 d = bdesc_3arg;
11943 for (i = 0; i < ARRAY_SIZE (bdesc_3arg); i++, d++)
11944 if (d->code == fcode)
11945 return rs6000_expand_ternop_builtin (d->icode, exp, target);
11946
11947 gcc_unreachable ();
11948 }
11949
11950 static void
11951 rs6000_init_builtins (void)
11952 {
11953 tree tdecl;
11954 tree ftype;
11955
11956 V2SI_type_node = build_vector_type (intSI_type_node, 2);
11957 V2SF_type_node = build_vector_type (float_type_node, 2);
11958 V2DI_type_node = build_vector_type (intDI_type_node, 2);
11959 V2DF_type_node = build_vector_type (double_type_node, 2);
11960 V4HI_type_node = build_vector_type (intHI_type_node, 4);
11961 V4SI_type_node = build_vector_type (intSI_type_node, 4);
11962 V4SF_type_node = build_vector_type (float_type_node, 4);
11963 V8HI_type_node = build_vector_type (intHI_type_node, 8);
11964 V16QI_type_node = build_vector_type (intQI_type_node, 16);
11965
11966 unsigned_V16QI_type_node = build_vector_type (unsigned_intQI_type_node, 16);
11967 unsigned_V8HI_type_node = build_vector_type (unsigned_intHI_type_node, 8);
11968 unsigned_V4SI_type_node = build_vector_type (unsigned_intSI_type_node, 4);
11969 unsigned_V2DI_type_node = build_vector_type (unsigned_intDI_type_node, 2);
11970
11971 opaque_V2SF_type_node = build_opaque_vector_type (float_type_node, 2);
11972 opaque_V2SI_type_node = build_opaque_vector_type (intSI_type_node, 2);
11973 opaque_p_V2SI_type_node = build_pointer_type (opaque_V2SI_type_node);
11974 opaque_V4SI_type_node = build_opaque_vector_type (intSI_type_node, 4);
11975
11976 /* The 'vector bool ...' types must be kept distinct from 'vector unsigned ...'
11977 types, especially in C++ land. Similarly, 'vector pixel' is distinct from
11978 'vector unsigned short'. */
11979
11980 bool_char_type_node = build_distinct_type_copy (unsigned_intQI_type_node);
11981 bool_short_type_node = build_distinct_type_copy (unsigned_intHI_type_node);
11982 bool_int_type_node = build_distinct_type_copy (unsigned_intSI_type_node);
11983 bool_long_type_node = build_distinct_type_copy (unsigned_intDI_type_node);
11984 pixel_type_node = build_distinct_type_copy (unsigned_intHI_type_node);
11985
11986 long_integer_type_internal_node = long_integer_type_node;
11987 long_unsigned_type_internal_node = long_unsigned_type_node;
11988 intQI_type_internal_node = intQI_type_node;
11989 uintQI_type_internal_node = unsigned_intQI_type_node;
11990 intHI_type_internal_node = intHI_type_node;
11991 uintHI_type_internal_node = unsigned_intHI_type_node;
11992 intSI_type_internal_node = intSI_type_node;
11993 uintSI_type_internal_node = unsigned_intSI_type_node;
11994 intDI_type_internal_node = intDI_type_node;
11995 uintDI_type_internal_node = unsigned_intDI_type_node;
11996 float_type_internal_node = float_type_node;
11997 double_type_internal_node = float_type_node;
11998 void_type_internal_node = void_type_node;
11999
12000 /* Initialize the modes for builtin_function_type, mapping a machine mode to
12001 tree type node. */
12002 builtin_mode_to_type[QImode][0] = integer_type_node;
12003 builtin_mode_to_type[HImode][0] = integer_type_node;
12004 builtin_mode_to_type[SImode][0] = intSI_type_node;
12005 builtin_mode_to_type[SImode][1] = unsigned_intSI_type_node;
12006 builtin_mode_to_type[DImode][0] = intDI_type_node;
12007 builtin_mode_to_type[DImode][1] = unsigned_intDI_type_node;
12008 builtin_mode_to_type[SFmode][0] = float_type_node;
12009 builtin_mode_to_type[DFmode][0] = double_type_node;
12010 builtin_mode_to_type[V2SImode][0] = V2SI_type_node;
12011 builtin_mode_to_type[V2SFmode][0] = V2SF_type_node;
12012 builtin_mode_to_type[V2DImode][0] = V2DI_type_node;
12013 builtin_mode_to_type[V2DImode][1] = unsigned_V2DI_type_node;
12014 builtin_mode_to_type[V2DFmode][0] = V2DF_type_node;
12015 builtin_mode_to_type[V4HImode][0] = V4HI_type_node;
12016 builtin_mode_to_type[V4SImode][0] = V4SI_type_node;
12017 builtin_mode_to_type[V4SImode][1] = unsigned_V4SI_type_node;
12018 builtin_mode_to_type[V4SFmode][0] = V4SF_type_node;
12019 builtin_mode_to_type[V8HImode][0] = V8HI_type_node;
12020 builtin_mode_to_type[V8HImode][1] = unsigned_V8HI_type_node;
12021 builtin_mode_to_type[V16QImode][0] = V16QI_type_node;
12022 builtin_mode_to_type[V16QImode][1] = unsigned_V16QI_type_node;
12023
12024 tdecl = build_decl (BUILTINS_LOCATION, TYPE_DECL,
12025 get_identifier ("__bool char"),
12026 bool_char_type_node);
12027 TYPE_NAME (bool_char_type_node) = tdecl;
12028 (*lang_hooks.decls.pushdecl) (tdecl);
12029 tdecl = build_decl (BUILTINS_LOCATION, TYPE_DECL,
12030 get_identifier ("__bool short"),
12031 bool_short_type_node);
12032 TYPE_NAME (bool_short_type_node) = tdecl;
12033 (*lang_hooks.decls.pushdecl) (tdecl);
12034 tdecl = build_decl (BUILTINS_LOCATION, TYPE_DECL,
12035 get_identifier ("__bool int"),
12036 bool_int_type_node);
12037 TYPE_NAME (bool_int_type_node) = tdecl;
12038 (*lang_hooks.decls.pushdecl) (tdecl);
12039 tdecl = build_decl (BUILTINS_LOCATION, TYPE_DECL, get_identifier ("__pixel"),
12040 pixel_type_node);
12041 TYPE_NAME (pixel_type_node) = tdecl;
12042 (*lang_hooks.decls.pushdecl) (tdecl);
12043
12044 bool_V16QI_type_node = build_vector_type (bool_char_type_node, 16);
12045 bool_V8HI_type_node = build_vector_type (bool_short_type_node, 8);
12046 bool_V4SI_type_node = build_vector_type (bool_int_type_node, 4);
12047 bool_V2DI_type_node = build_vector_type (bool_long_type_node, 2);
12048 pixel_V8HI_type_node = build_vector_type (pixel_type_node, 8);
12049
12050 tdecl = build_decl (BUILTINS_LOCATION, TYPE_DECL,
12051 get_identifier ("__vector unsigned char"),
12052 unsigned_V16QI_type_node);
12053 TYPE_NAME (unsigned_V16QI_type_node) = tdecl;
12054 (*lang_hooks.decls.pushdecl) (tdecl);
12055 tdecl = build_decl (BUILTINS_LOCATION,
12056 TYPE_DECL, get_identifier ("__vector signed char"),
12057 V16QI_type_node);
12058 TYPE_NAME (V16QI_type_node) = tdecl;
12059 (*lang_hooks.decls.pushdecl) (tdecl);
12060 tdecl = build_decl (BUILTINS_LOCATION,
12061 TYPE_DECL, get_identifier ("__vector __bool char"),
12062 bool_V16QI_type_node);
12063 TYPE_NAME ( bool_V16QI_type_node) = tdecl;
12064 (*lang_hooks.decls.pushdecl) (tdecl);
12065
12066 tdecl = build_decl (BUILTINS_LOCATION,
12067 TYPE_DECL, get_identifier ("__vector unsigned short"),
12068 unsigned_V8HI_type_node);
12069 TYPE_NAME (unsigned_V8HI_type_node) = tdecl;
12070 (*lang_hooks.decls.pushdecl) (tdecl);
12071 tdecl = build_decl (BUILTINS_LOCATION,
12072 TYPE_DECL, get_identifier ("__vector signed short"),
12073 V8HI_type_node);
12074 TYPE_NAME (V8HI_type_node) = tdecl;
12075 (*lang_hooks.decls.pushdecl) (tdecl);
12076 tdecl = build_decl (BUILTINS_LOCATION, TYPE_DECL,
12077 get_identifier ("__vector __bool short"),
12078 bool_V8HI_type_node);
12079 TYPE_NAME (bool_V8HI_type_node) = tdecl;
12080 (*lang_hooks.decls.pushdecl) (tdecl);
12081
12082 tdecl = build_decl (BUILTINS_LOCATION, TYPE_DECL,
12083 get_identifier ("__vector unsigned int"),
12084 unsigned_V4SI_type_node);
12085 TYPE_NAME (unsigned_V4SI_type_node) = tdecl;
12086 (*lang_hooks.decls.pushdecl) (tdecl);
12087 tdecl = build_decl (BUILTINS_LOCATION,
12088 TYPE_DECL, get_identifier ("__vector signed int"),
12089 V4SI_type_node);
12090 TYPE_NAME (V4SI_type_node) = tdecl;
12091 (*lang_hooks.decls.pushdecl) (tdecl);
12092 tdecl = build_decl (BUILTINS_LOCATION,
12093 TYPE_DECL, get_identifier ("__vector __bool int"),
12094 bool_V4SI_type_node);
12095 TYPE_NAME (bool_V4SI_type_node) = tdecl;
12096 (*lang_hooks.decls.pushdecl) (tdecl);
12097
12098 tdecl = build_decl (BUILTINS_LOCATION,
12099 TYPE_DECL, get_identifier ("__vector float"),
12100 V4SF_type_node);
12101 TYPE_NAME (V4SF_type_node) = tdecl;
12102 (*lang_hooks.decls.pushdecl) (tdecl);
12103 tdecl = build_decl (BUILTINS_LOCATION,
12104 TYPE_DECL, get_identifier ("__vector __pixel"),
12105 pixel_V8HI_type_node);
12106 TYPE_NAME (pixel_V8HI_type_node) = tdecl;
12107 (*lang_hooks.decls.pushdecl) (tdecl);
12108
12109 if (TARGET_VSX)
12110 {
12111 tdecl = build_decl (BUILTINS_LOCATION,
12112 TYPE_DECL, get_identifier ("__vector double"),
12113 V2DF_type_node);
12114 TYPE_NAME (V2DF_type_node) = tdecl;
12115 (*lang_hooks.decls.pushdecl) (tdecl);
12116
12117 tdecl = build_decl (BUILTINS_LOCATION,
12118 TYPE_DECL, get_identifier ("__vector long"),
12119 V2DI_type_node);
12120 TYPE_NAME (V2DI_type_node) = tdecl;
12121 (*lang_hooks.decls.pushdecl) (tdecl);
12122
12123 tdecl = build_decl (BUILTINS_LOCATION,
12124 TYPE_DECL, get_identifier ("__vector unsigned long"),
12125 unsigned_V2DI_type_node);
12126 TYPE_NAME (unsigned_V2DI_type_node) = tdecl;
12127 (*lang_hooks.decls.pushdecl) (tdecl);
12128
12129 tdecl = build_decl (BUILTINS_LOCATION,
12130 TYPE_DECL, get_identifier ("__vector __bool long"),
12131 bool_V2DI_type_node);
12132 TYPE_NAME (bool_V2DI_type_node) = tdecl;
12133 (*lang_hooks.decls.pushdecl) (tdecl);
12134 }
12135
12136 if (TARGET_PAIRED_FLOAT)
12137 paired_init_builtins ();
12138 if (TARGET_SPE)
12139 spe_init_builtins ();
12140 if (TARGET_ALTIVEC)
12141 altivec_init_builtins ();
12142 if (TARGET_ALTIVEC || TARGET_SPE || TARGET_PAIRED_FLOAT || TARGET_VSX)
12143 rs6000_common_init_builtins ();
12144 if (TARGET_FRE)
12145 {
12146 ftype = builtin_function_type (DFmode, DFmode, DFmode, VOIDmode,
12147 RS6000_BUILTIN_RECIP,
12148 "__builtin_recipdiv");
12149 def_builtin (MASK_POPCNTB, "__builtin_recipdiv", ftype,
12150 RS6000_BUILTIN_RECIP);
12151 }
12152 if (TARGET_FRES)
12153 {
12154 ftype = builtin_function_type (SFmode, SFmode, SFmode, VOIDmode,
12155 RS6000_BUILTIN_RECIPF,
12156 "__builtin_recipdivf");
12157 def_builtin (MASK_PPC_GFXOPT, "__builtin_recipdivf", ftype,
12158 RS6000_BUILTIN_RECIPF);
12159 }
12160 if (TARGET_FRSQRTE)
12161 {
12162 ftype = builtin_function_type (DFmode, DFmode, VOIDmode, VOIDmode,
12163 RS6000_BUILTIN_RSQRT,
12164 "__builtin_rsqrt");
12165 def_builtin (MASK_PPC_GFXOPT, "__builtin_rsqrt", ftype,
12166 RS6000_BUILTIN_RSQRT);
12167 }
12168 if (TARGET_FRSQRTES)
12169 {
12170 ftype = builtin_function_type (SFmode, SFmode, VOIDmode, VOIDmode,
12171 RS6000_BUILTIN_RSQRTF,
12172 "__builtin_rsqrtf");
12173 def_builtin (MASK_PPC_GFXOPT, "__builtin_rsqrtf", ftype,
12174 RS6000_BUILTIN_RSQRTF);
12175 }
12176 if (TARGET_POPCNTD)
12177 {
12178 enum machine_mode mode = (TARGET_64BIT) ? DImode : SImode;
12179 tree ftype = builtin_function_type (mode, mode, mode, VOIDmode,
12180 POWER7_BUILTIN_BPERMD,
12181 "__builtin_bpermd");
12182 def_builtin (MASK_POPCNTD, "__builtin_bpermd", ftype,
12183 POWER7_BUILTIN_BPERMD);
12184 }
12185 if (TARGET_POWERPC)
12186 {
12187 /* Don't use builtin_function_type here, as it maps HI/QI to SI. */
12188 tree ftype = build_function_type_list (unsigned_intHI_type_node,
12189 unsigned_intHI_type_node,
12190 NULL_TREE);
12191 def_builtin (MASK_POWERPC, "__builtin_bswap16", ftype,
12192 RS6000_BUILTIN_BSWAP_HI);
12193 }
12194
12195 #if TARGET_XCOFF
12196 /* AIX libm provides clog as __clog. */
12197 if (built_in_decls [BUILT_IN_CLOG])
12198 set_user_assembler_name (built_in_decls [BUILT_IN_CLOG], "__clog");
12199 #endif
12200
12201 #ifdef SUBTARGET_INIT_BUILTINS
12202 SUBTARGET_INIT_BUILTINS;
12203 #endif
12204 }
12205
12206 /* Returns the rs6000 builtin decl for CODE. */
12207
12208 static tree
12209 rs6000_builtin_decl (unsigned code, bool initialize_p ATTRIBUTE_UNUSED)
12210 {
12211 if (code >= RS6000_BUILTIN_COUNT)
12212 return error_mark_node;
12213
12214 return rs6000_builtin_decls[code];
12215 }
12216
12217 /* Search through a set of builtins and enable the mask bits.
12218 DESC is an array of builtins.
12219 SIZE is the total number of builtins.
12220 START is the builtin enum at which to start.
12221 END is the builtin enum at which to end. */
12222 static void
12223 enable_mask_for_builtins (struct builtin_description *desc, int size,
12224 enum rs6000_builtins start,
12225 enum rs6000_builtins end)
12226 {
12227 int i;
12228
12229 for (i = 0; i < size; ++i)
12230 if (desc[i].code == start)
12231 break;
12232
12233 if (i == size)
12234 return;
12235
12236 for (; i < size; ++i)
12237 {
12238 /* Flip all the bits on. */
12239 desc[i].mask = target_flags;
12240 if (desc[i].code == end)
12241 break;
12242 }
12243 }
12244
12245 static void
12246 spe_init_builtins (void)
12247 {
12248 tree endlink = void_list_node;
12249 tree puint_type_node = build_pointer_type (unsigned_type_node);
12250 tree pushort_type_node = build_pointer_type (short_unsigned_type_node);
12251 struct builtin_description *d;
12252 size_t i;
12253
12254 tree v2si_ftype_4_v2si
12255 = build_function_type
12256 (opaque_V2SI_type_node,
12257 tree_cons (NULL_TREE, opaque_V2SI_type_node,
12258 tree_cons (NULL_TREE, opaque_V2SI_type_node,
12259 tree_cons (NULL_TREE, opaque_V2SI_type_node,
12260 tree_cons (NULL_TREE, opaque_V2SI_type_node,
12261 endlink)))));
12262
12263 tree v2sf_ftype_4_v2sf
12264 = build_function_type
12265 (opaque_V2SF_type_node,
12266 tree_cons (NULL_TREE, opaque_V2SF_type_node,
12267 tree_cons (NULL_TREE, opaque_V2SF_type_node,
12268 tree_cons (NULL_TREE, opaque_V2SF_type_node,
12269 tree_cons (NULL_TREE, opaque_V2SF_type_node,
12270 endlink)))));
12271
12272 tree int_ftype_int_v2si_v2si
12273 = build_function_type
12274 (integer_type_node,
12275 tree_cons (NULL_TREE, integer_type_node,
12276 tree_cons (NULL_TREE, opaque_V2SI_type_node,
12277 tree_cons (NULL_TREE, opaque_V2SI_type_node,
12278 endlink))));
12279
12280 tree int_ftype_int_v2sf_v2sf
12281 = build_function_type
12282 (integer_type_node,
12283 tree_cons (NULL_TREE, integer_type_node,
12284 tree_cons (NULL_TREE, opaque_V2SF_type_node,
12285 tree_cons (NULL_TREE, opaque_V2SF_type_node,
12286 endlink))));
12287
12288 tree void_ftype_v2si_puint_int
12289 = build_function_type (void_type_node,
12290 tree_cons (NULL_TREE, opaque_V2SI_type_node,
12291 tree_cons (NULL_TREE, puint_type_node,
12292 tree_cons (NULL_TREE,
12293 integer_type_node,
12294 endlink))));
12295
12296 tree void_ftype_v2si_puint_char
12297 = build_function_type (void_type_node,
12298 tree_cons (NULL_TREE, opaque_V2SI_type_node,
12299 tree_cons (NULL_TREE, puint_type_node,
12300 tree_cons (NULL_TREE,
12301 char_type_node,
12302 endlink))));
12303
12304 tree void_ftype_v2si_pv2si_int
12305 = build_function_type (void_type_node,
12306 tree_cons (NULL_TREE, opaque_V2SI_type_node,
12307 tree_cons (NULL_TREE, opaque_p_V2SI_type_node,
12308 tree_cons (NULL_TREE,
12309 integer_type_node,
12310 endlink))));
12311
12312 tree void_ftype_v2si_pv2si_char
12313 = build_function_type (void_type_node,
12314 tree_cons (NULL_TREE, opaque_V2SI_type_node,
12315 tree_cons (NULL_TREE, opaque_p_V2SI_type_node,
12316 tree_cons (NULL_TREE,
12317 char_type_node,
12318 endlink))));
12319
12320 tree void_ftype_int
12321 = build_function_type (void_type_node,
12322 tree_cons (NULL_TREE, integer_type_node, endlink));
12323
12324 tree int_ftype_void
12325 = build_function_type (integer_type_node, endlink);
12326
12327 tree v2si_ftype_pv2si_int
12328 = build_function_type (opaque_V2SI_type_node,
12329 tree_cons (NULL_TREE, opaque_p_V2SI_type_node,
12330 tree_cons (NULL_TREE, integer_type_node,
12331 endlink)));
12332
12333 tree v2si_ftype_puint_int
12334 = build_function_type (opaque_V2SI_type_node,
12335 tree_cons (NULL_TREE, puint_type_node,
12336 tree_cons (NULL_TREE, integer_type_node,
12337 endlink)));
12338
12339 tree v2si_ftype_pushort_int
12340 = build_function_type (opaque_V2SI_type_node,
12341 tree_cons (NULL_TREE, pushort_type_node,
12342 tree_cons (NULL_TREE, integer_type_node,
12343 endlink)));
12344
12345 tree v2si_ftype_signed_char
12346 = build_function_type (opaque_V2SI_type_node,
12347 tree_cons (NULL_TREE, signed_char_type_node,
12348 endlink));
12349
12350 /* The initialization of the simple binary and unary builtins is
12351 done in rs6000_common_init_builtins, but we have to enable the
12352 mask bits here manually because we have run out of `target_flags'
12353 bits. We really need to redesign this mask business. */
12354
12355 enable_mask_for_builtins ((struct builtin_description *) bdesc_2arg,
12356 ARRAY_SIZE (bdesc_2arg),
12357 SPE_BUILTIN_EVADDW,
12358 SPE_BUILTIN_EVXOR);
12359 enable_mask_for_builtins ((struct builtin_description *) bdesc_1arg,
12360 ARRAY_SIZE (bdesc_1arg),
12361 SPE_BUILTIN_EVABS,
12362 SPE_BUILTIN_EVSUBFUSIAAW);
12363 enable_mask_for_builtins ((struct builtin_description *) bdesc_spe_predicates,
12364 ARRAY_SIZE (bdesc_spe_predicates),
12365 SPE_BUILTIN_EVCMPEQ,
12366 SPE_BUILTIN_EVFSTSTLT);
12367 enable_mask_for_builtins ((struct builtin_description *) bdesc_spe_evsel,
12368 ARRAY_SIZE (bdesc_spe_evsel),
12369 SPE_BUILTIN_EVSEL_CMPGTS,
12370 SPE_BUILTIN_EVSEL_FSTSTEQ);
12371
12372 (*lang_hooks.decls.pushdecl)
12373 (build_decl (BUILTINS_LOCATION, TYPE_DECL,
12374 get_identifier ("__ev64_opaque__"),
12375 opaque_V2SI_type_node));
12376
12377 /* Initialize irregular SPE builtins. */
12378
12379 def_builtin (target_flags, "__builtin_spe_mtspefscr", void_ftype_int, SPE_BUILTIN_MTSPEFSCR);
12380 def_builtin (target_flags, "__builtin_spe_mfspefscr", int_ftype_void, SPE_BUILTIN_MFSPEFSCR);
12381 def_builtin (target_flags, "__builtin_spe_evstddx", void_ftype_v2si_pv2si_int, SPE_BUILTIN_EVSTDDX);
12382 def_builtin (target_flags, "__builtin_spe_evstdhx", void_ftype_v2si_pv2si_int, SPE_BUILTIN_EVSTDHX);
12383 def_builtin (target_flags, "__builtin_spe_evstdwx", void_ftype_v2si_pv2si_int, SPE_BUILTIN_EVSTDWX);
12384 def_builtin (target_flags, "__builtin_spe_evstwhex", void_ftype_v2si_puint_int, SPE_BUILTIN_EVSTWHEX);
12385 def_builtin (target_flags, "__builtin_spe_evstwhox", void_ftype_v2si_puint_int, SPE_BUILTIN_EVSTWHOX);
12386 def_builtin (target_flags, "__builtin_spe_evstwwex", void_ftype_v2si_puint_int, SPE_BUILTIN_EVSTWWEX);
12387 def_builtin (target_flags, "__builtin_spe_evstwwox", void_ftype_v2si_puint_int, SPE_BUILTIN_EVSTWWOX);
12388 def_builtin (target_flags, "__builtin_spe_evstdd", void_ftype_v2si_pv2si_char, SPE_BUILTIN_EVSTDD);
12389 def_builtin (target_flags, "__builtin_spe_evstdh", void_ftype_v2si_pv2si_char, SPE_BUILTIN_EVSTDH);
12390 def_builtin (target_flags, "__builtin_spe_evstdw", void_ftype_v2si_pv2si_char, SPE_BUILTIN_EVSTDW);
12391 def_builtin (target_flags, "__builtin_spe_evstwhe", void_ftype_v2si_puint_char, SPE_BUILTIN_EVSTWHE);
12392 def_builtin (target_flags, "__builtin_spe_evstwho", void_ftype_v2si_puint_char, SPE_BUILTIN_EVSTWHO);
12393 def_builtin (target_flags, "__builtin_spe_evstwwe", void_ftype_v2si_puint_char, SPE_BUILTIN_EVSTWWE);
12394 def_builtin (target_flags, "__builtin_spe_evstwwo", void_ftype_v2si_puint_char, SPE_BUILTIN_EVSTWWO);
12395 def_builtin (target_flags, "__builtin_spe_evsplatfi", v2si_ftype_signed_char, SPE_BUILTIN_EVSPLATFI);
12396 def_builtin (target_flags, "__builtin_spe_evsplati", v2si_ftype_signed_char, SPE_BUILTIN_EVSPLATI);
12397
12398 /* Loads. */
12399 def_builtin (target_flags, "__builtin_spe_evlddx", v2si_ftype_pv2si_int, SPE_BUILTIN_EVLDDX);
12400 def_builtin (target_flags, "__builtin_spe_evldwx", v2si_ftype_pv2si_int, SPE_BUILTIN_EVLDWX);
12401 def_builtin (target_flags, "__builtin_spe_evldhx", v2si_ftype_pv2si_int, SPE_BUILTIN_EVLDHX);
12402 def_builtin (target_flags, "__builtin_spe_evlwhex", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHEX);
12403 def_builtin (target_flags, "__builtin_spe_evlwhoux", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHOUX);
12404 def_builtin (target_flags, "__builtin_spe_evlwhosx", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHOSX);
12405 def_builtin (target_flags, "__builtin_spe_evlwwsplatx", v2si_ftype_puint_int, SPE_BUILTIN_EVLWWSPLATX);
12406 def_builtin (target_flags, "__builtin_spe_evlwhsplatx", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHSPLATX);
12407 def_builtin (target_flags, "__builtin_spe_evlhhesplatx", v2si_ftype_pushort_int, SPE_BUILTIN_EVLHHESPLATX);
12408 def_builtin (target_flags, "__builtin_spe_evlhhousplatx", v2si_ftype_pushort_int, SPE_BUILTIN_EVLHHOUSPLATX);
12409 def_builtin (target_flags, "__builtin_spe_evlhhossplatx", v2si_ftype_pushort_int, SPE_BUILTIN_EVLHHOSSPLATX);
12410 def_builtin (target_flags, "__builtin_spe_evldd", v2si_ftype_pv2si_int, SPE_BUILTIN_EVLDD);
12411 def_builtin (target_flags, "__builtin_spe_evldw", v2si_ftype_pv2si_int, SPE_BUILTIN_EVLDW);
12412 def_builtin (target_flags, "__builtin_spe_evldh", v2si_ftype_pv2si_int, SPE_BUILTIN_EVLDH);
12413 def_builtin (target_flags, "__builtin_spe_evlhhesplat", v2si_ftype_pushort_int, SPE_BUILTIN_EVLHHESPLAT);
12414 def_builtin (target_flags, "__builtin_spe_evlhhossplat", v2si_ftype_pushort_int, SPE_BUILTIN_EVLHHOSSPLAT);
12415 def_builtin (target_flags, "__builtin_spe_evlhhousplat", v2si_ftype_pushort_int, SPE_BUILTIN_EVLHHOUSPLAT);
12416 def_builtin (target_flags, "__builtin_spe_evlwhe", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHE);
12417 def_builtin (target_flags, "__builtin_spe_evlwhos", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHOS);
12418 def_builtin (target_flags, "__builtin_spe_evlwhou", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHOU);
12419 def_builtin (target_flags, "__builtin_spe_evlwhsplat", v2si_ftype_puint_int, SPE_BUILTIN_EVLWHSPLAT);
12420 def_builtin (target_flags, "__builtin_spe_evlwwsplat", v2si_ftype_puint_int, SPE_BUILTIN_EVLWWSPLAT);
12421
12422 /* Predicates. */
12423 d = (struct builtin_description *) bdesc_spe_predicates;
12424 for (i = 0; i < ARRAY_SIZE (bdesc_spe_predicates); ++i, d++)
12425 {
12426 tree type;
12427
12428 switch (insn_data[d->icode].operand[1].mode)
12429 {
12430 case V2SImode:
12431 type = int_ftype_int_v2si_v2si;
12432 break;
12433 case V2SFmode:
12434 type = int_ftype_int_v2sf_v2sf;
12435 break;
12436 default:
12437 gcc_unreachable ();
12438 }
12439
12440 def_builtin (d->mask, d->name, type, d->code);
12441 }
12442
12443 /* Evsel predicates. */
12444 d = (struct builtin_description *) bdesc_spe_evsel;
12445 for (i = 0; i < ARRAY_SIZE (bdesc_spe_evsel); ++i, d++)
12446 {
12447 tree type;
12448
12449 switch (insn_data[d->icode].operand[1].mode)
12450 {
12451 case V2SImode:
12452 type = v2si_ftype_4_v2si;
12453 break;
12454 case V2SFmode:
12455 type = v2sf_ftype_4_v2sf;
12456 break;
12457 default:
12458 gcc_unreachable ();
12459 }
12460
12461 def_builtin (d->mask, d->name, type, d->code);
12462 }
12463 }
12464
12465 static void
12466 paired_init_builtins (void)
12467 {
12468 const struct builtin_description *d;
12469 size_t i;
12470 tree endlink = void_list_node;
12471
12472 tree int_ftype_int_v2sf_v2sf
12473 = build_function_type
12474 (integer_type_node,
12475 tree_cons (NULL_TREE, integer_type_node,
12476 tree_cons (NULL_TREE, V2SF_type_node,
12477 tree_cons (NULL_TREE, V2SF_type_node,
12478 endlink))));
12479 tree pcfloat_type_node =
12480 build_pointer_type (build_qualified_type
12481 (float_type_node, TYPE_QUAL_CONST));
12482
12483 tree v2sf_ftype_long_pcfloat = build_function_type_list (V2SF_type_node,
12484 long_integer_type_node,
12485 pcfloat_type_node,
12486 NULL_TREE);
12487 tree void_ftype_v2sf_long_pcfloat =
12488 build_function_type_list (void_type_node,
12489 V2SF_type_node,
12490 long_integer_type_node,
12491 pcfloat_type_node,
12492 NULL_TREE);
12493
12494
12495 def_builtin (0, "__builtin_paired_lx", v2sf_ftype_long_pcfloat,
12496 PAIRED_BUILTIN_LX);
12497
12498
12499 def_builtin (0, "__builtin_paired_stx", void_ftype_v2sf_long_pcfloat,
12500 PAIRED_BUILTIN_STX);
12501
12502 /* Predicates. */
12503 d = bdesc_paired_preds;
12504 for (i = 0; i < ARRAY_SIZE (bdesc_paired_preds); ++i, d++)
12505 {
12506 tree type;
12507
12508 switch (insn_data[d->icode].operand[1].mode)
12509 {
12510 case V2SFmode:
12511 type = int_ftype_int_v2sf_v2sf;
12512 break;
12513 default:
12514 gcc_unreachable ();
12515 }
12516
12517 def_builtin (d->mask, d->name, type, d->code);
12518 }
12519 }
12520
12521 static void
12522 altivec_init_builtins (void)
12523 {
12524 const struct builtin_description *d;
12525 const struct builtin_description_predicates *dp;
12526 size_t i;
12527 tree ftype;
12528
12529 tree pfloat_type_node = build_pointer_type (float_type_node);
12530 tree pint_type_node = build_pointer_type (integer_type_node);
12531 tree pshort_type_node = build_pointer_type (short_integer_type_node);
12532 tree pchar_type_node = build_pointer_type (char_type_node);
12533
12534 tree pvoid_type_node = build_pointer_type (void_type_node);
12535
12536 tree pcfloat_type_node = build_pointer_type (build_qualified_type (float_type_node, TYPE_QUAL_CONST));
12537 tree pcint_type_node = build_pointer_type (build_qualified_type (integer_type_node, TYPE_QUAL_CONST));
12538 tree pcshort_type_node = build_pointer_type (build_qualified_type (short_integer_type_node, TYPE_QUAL_CONST));
12539 tree pcchar_type_node = build_pointer_type (build_qualified_type (char_type_node, TYPE_QUAL_CONST));
12540
12541 tree pcvoid_type_node = build_pointer_type (build_qualified_type (void_type_node, TYPE_QUAL_CONST));
12542
12543 tree int_ftype_opaque
12544 = build_function_type_list (integer_type_node,
12545 opaque_V4SI_type_node, NULL_TREE);
12546 tree opaque_ftype_opaque
12547 = build_function_type (integer_type_node,
12548 NULL_TREE);
12549 tree opaque_ftype_opaque_int
12550 = build_function_type_list (opaque_V4SI_type_node,
12551 opaque_V4SI_type_node, integer_type_node, NULL_TREE);
12552 tree opaque_ftype_opaque_opaque_int
12553 = build_function_type_list (opaque_V4SI_type_node,
12554 opaque_V4SI_type_node, opaque_V4SI_type_node,
12555 integer_type_node, NULL_TREE);
12556 tree int_ftype_int_opaque_opaque
12557 = build_function_type_list (integer_type_node,
12558 integer_type_node, opaque_V4SI_type_node,
12559 opaque_V4SI_type_node, NULL_TREE);
12560 tree int_ftype_int_v4si_v4si
12561 = build_function_type_list (integer_type_node,
12562 integer_type_node, V4SI_type_node,
12563 V4SI_type_node, NULL_TREE);
12564 tree v4sf_ftype_pcfloat
12565 = build_function_type_list (V4SF_type_node, pcfloat_type_node, NULL_TREE);
12566 tree void_ftype_pfloat_v4sf
12567 = build_function_type_list (void_type_node,
12568 pfloat_type_node, V4SF_type_node, NULL_TREE);
12569 tree v4si_ftype_pcint
12570 = build_function_type_list (V4SI_type_node, pcint_type_node, NULL_TREE);
12571 tree void_ftype_pint_v4si
12572 = build_function_type_list (void_type_node,
12573 pint_type_node, V4SI_type_node, NULL_TREE);
12574 tree v8hi_ftype_pcshort
12575 = build_function_type_list (V8HI_type_node, pcshort_type_node, NULL_TREE);
12576 tree void_ftype_pshort_v8hi
12577 = build_function_type_list (void_type_node,
12578 pshort_type_node, V8HI_type_node, NULL_TREE);
12579 tree v16qi_ftype_pcchar
12580 = build_function_type_list (V16QI_type_node, pcchar_type_node, NULL_TREE);
12581 tree void_ftype_pchar_v16qi
12582 = build_function_type_list (void_type_node,
12583 pchar_type_node, V16QI_type_node, NULL_TREE);
12584 tree void_ftype_v4si
12585 = build_function_type_list (void_type_node, V4SI_type_node, NULL_TREE);
12586 tree v8hi_ftype_void
12587 = build_function_type (V8HI_type_node, void_list_node);
12588 tree void_ftype_void
12589 = build_function_type (void_type_node, void_list_node);
12590 tree void_ftype_int
12591 = build_function_type_list (void_type_node, integer_type_node, NULL_TREE);
12592
12593 tree opaque_ftype_long_pcvoid
12594 = build_function_type_list (opaque_V4SI_type_node,
12595 long_integer_type_node, pcvoid_type_node, NULL_TREE);
12596 tree v16qi_ftype_long_pcvoid
12597 = build_function_type_list (V16QI_type_node,
12598 long_integer_type_node, pcvoid_type_node, NULL_TREE);
12599 tree v8hi_ftype_long_pcvoid
12600 = build_function_type_list (V8HI_type_node,
12601 long_integer_type_node, pcvoid_type_node, NULL_TREE);
12602 tree v4si_ftype_long_pcvoid
12603 = build_function_type_list (V4SI_type_node,
12604 long_integer_type_node, pcvoid_type_node, NULL_TREE);
12605
12606 tree void_ftype_opaque_long_pvoid
12607 = build_function_type_list (void_type_node,
12608 opaque_V4SI_type_node, long_integer_type_node,
12609 pvoid_type_node, NULL_TREE);
12610 tree void_ftype_v4si_long_pvoid
12611 = build_function_type_list (void_type_node,
12612 V4SI_type_node, long_integer_type_node,
12613 pvoid_type_node, NULL_TREE);
12614 tree void_ftype_v16qi_long_pvoid
12615 = build_function_type_list (void_type_node,
12616 V16QI_type_node, long_integer_type_node,
12617 pvoid_type_node, NULL_TREE);
12618 tree void_ftype_v8hi_long_pvoid
12619 = build_function_type_list (void_type_node,
12620 V8HI_type_node, long_integer_type_node,
12621 pvoid_type_node, NULL_TREE);
12622 tree int_ftype_int_v8hi_v8hi
12623 = build_function_type_list (integer_type_node,
12624 integer_type_node, V8HI_type_node,
12625 V8HI_type_node, NULL_TREE);
12626 tree int_ftype_int_v16qi_v16qi
12627 = build_function_type_list (integer_type_node,
12628 integer_type_node, V16QI_type_node,
12629 V16QI_type_node, NULL_TREE);
12630 tree int_ftype_int_v4sf_v4sf
12631 = build_function_type_list (integer_type_node,
12632 integer_type_node, V4SF_type_node,
12633 V4SF_type_node, NULL_TREE);
12634 tree int_ftype_int_v2df_v2df
12635 = build_function_type_list (integer_type_node,
12636 integer_type_node, V2DF_type_node,
12637 V2DF_type_node, NULL_TREE);
12638 tree v4si_ftype_v4si
12639 = build_function_type_list (V4SI_type_node, V4SI_type_node, NULL_TREE);
12640 tree v8hi_ftype_v8hi
12641 = build_function_type_list (V8HI_type_node, V8HI_type_node, NULL_TREE);
12642 tree v16qi_ftype_v16qi
12643 = build_function_type_list (V16QI_type_node, V16QI_type_node, NULL_TREE);
12644 tree v4sf_ftype_v4sf
12645 = build_function_type_list (V4SF_type_node, V4SF_type_node, NULL_TREE);
12646 tree v2df_ftype_v2df
12647 = build_function_type_list (V2DF_type_node, V2DF_type_node, NULL_TREE);
12648 tree void_ftype_pcvoid_int_int
12649 = build_function_type_list (void_type_node,
12650 pcvoid_type_node, integer_type_node,
12651 integer_type_node, NULL_TREE);
12652
12653 def_builtin (MASK_ALTIVEC, "__builtin_altivec_ld_internal_4sf", v4sf_ftype_pcfloat,
12654 ALTIVEC_BUILTIN_LD_INTERNAL_4sf);
12655 def_builtin (MASK_ALTIVEC, "__builtin_altivec_st_internal_4sf", void_ftype_pfloat_v4sf,
12656 ALTIVEC_BUILTIN_ST_INTERNAL_4sf);
12657 def_builtin (MASK_ALTIVEC, "__builtin_altivec_ld_internal_4si", v4si_ftype_pcint,
12658 ALTIVEC_BUILTIN_LD_INTERNAL_4si);
12659 def_builtin (MASK_ALTIVEC, "__builtin_altivec_st_internal_4si", void_ftype_pint_v4si,
12660 ALTIVEC_BUILTIN_ST_INTERNAL_4si);
12661 def_builtin (MASK_ALTIVEC, "__builtin_altivec_ld_internal_8hi", v8hi_ftype_pcshort,
12662 ALTIVEC_BUILTIN_LD_INTERNAL_8hi);
12663 def_builtin (MASK_ALTIVEC, "__builtin_altivec_st_internal_8hi", void_ftype_pshort_v8hi,
12664 ALTIVEC_BUILTIN_ST_INTERNAL_8hi);
12665 def_builtin (MASK_ALTIVEC, "__builtin_altivec_ld_internal_16qi", v16qi_ftype_pcchar,
12666 ALTIVEC_BUILTIN_LD_INTERNAL_16qi);
12667 def_builtin (MASK_ALTIVEC, "__builtin_altivec_st_internal_16qi", void_ftype_pchar_v16qi,
12668 ALTIVEC_BUILTIN_ST_INTERNAL_16qi);
12669 def_builtin (MASK_ALTIVEC, "__builtin_altivec_mtvscr", void_ftype_v4si, ALTIVEC_BUILTIN_MTVSCR);
12670 def_builtin (MASK_ALTIVEC, "__builtin_altivec_mfvscr", v8hi_ftype_void, ALTIVEC_BUILTIN_MFVSCR);
12671 def_builtin (MASK_ALTIVEC, "__builtin_altivec_dssall", void_ftype_void, ALTIVEC_BUILTIN_DSSALL);
12672 def_builtin (MASK_ALTIVEC, "__builtin_altivec_dss", void_ftype_int, ALTIVEC_BUILTIN_DSS);
12673 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvsl", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVSL);
12674 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvsr", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVSR);
12675 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvebx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVEBX);
12676 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvehx", v8hi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVEHX);
12677 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvewx", v4si_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVEWX);
12678 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvxl", v4si_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVXL);
12679 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvx", v4si_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVX);
12680 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvx", void_ftype_v4si_long_pvoid, ALTIVEC_BUILTIN_STVX);
12681 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvewx", void_ftype_v4si_long_pvoid, ALTIVEC_BUILTIN_STVEWX);
12682 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvxl", void_ftype_v4si_long_pvoid, ALTIVEC_BUILTIN_STVXL);
12683 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvebx", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_STVEBX);
12684 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvehx", void_ftype_v8hi_long_pvoid, ALTIVEC_BUILTIN_STVEHX);
12685 def_builtin (MASK_ALTIVEC, "__builtin_vec_ld", opaque_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LD);
12686 def_builtin (MASK_ALTIVEC, "__builtin_vec_lde", opaque_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LDE);
12687 def_builtin (MASK_ALTIVEC, "__builtin_vec_ldl", opaque_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LDL);
12688 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvsl", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVSL);
12689 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvsr", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVSR);
12690 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvebx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVEBX);
12691 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvehx", v8hi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVEHX);
12692 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvewx", v4si_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVEWX);
12693 def_builtin (MASK_ALTIVEC, "__builtin_vec_st", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_ST);
12694 def_builtin (MASK_ALTIVEC, "__builtin_vec_ste", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_STE);
12695 def_builtin (MASK_ALTIVEC, "__builtin_vec_stl", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_STL);
12696 def_builtin (MASK_ALTIVEC, "__builtin_vec_stvewx", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_STVEWX);
12697 def_builtin (MASK_ALTIVEC, "__builtin_vec_stvebx", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_STVEBX);
12698 def_builtin (MASK_ALTIVEC, "__builtin_vec_stvehx", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_STVEHX);
12699
12700 if (rs6000_cpu == PROCESSOR_CELL)
12701 {
12702 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvlx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVLX);
12703 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvlxl", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVLXL);
12704 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvrx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVRX);
12705 def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvrxl", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVRXL);
12706
12707 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvlx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVLX);
12708 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvlxl", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVLXL);
12709 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvrx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVRX);
12710 def_builtin (MASK_ALTIVEC, "__builtin_vec_lvrxl", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVRXL);
12711
12712 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvlx", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_STVLX);
12713 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvlxl", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_STVLXL);
12714 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvrx", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_STVRX);
12715 def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvrxl", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_STVRXL);
12716
12717 def_builtin (MASK_ALTIVEC, "__builtin_vec_stvlx", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_VEC_STVLX);
12718 def_builtin (MASK_ALTIVEC, "__builtin_vec_stvlxl", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_VEC_STVLXL);
12719 def_builtin (MASK_ALTIVEC, "__builtin_vec_stvrx", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_VEC_STVRX);
12720 def_builtin (MASK_ALTIVEC, "__builtin_vec_stvrxl", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_VEC_STVRXL);
12721 }
12722 def_builtin (MASK_ALTIVEC, "__builtin_vec_step", int_ftype_opaque, ALTIVEC_BUILTIN_VEC_STEP);
12723 def_builtin (MASK_ALTIVEC, "__builtin_vec_splats", opaque_ftype_opaque, ALTIVEC_BUILTIN_VEC_SPLATS);
12724 def_builtin (MASK_ALTIVEC, "__builtin_vec_promote", opaque_ftype_opaque, ALTIVEC_BUILTIN_VEC_PROMOTE);
12725
12726 def_builtin (MASK_ALTIVEC, "__builtin_vec_sld", opaque_ftype_opaque_opaque_int, ALTIVEC_BUILTIN_VEC_SLD);
12727 def_builtin (MASK_ALTIVEC, "__builtin_vec_splat", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_SPLAT);
12728 def_builtin (MASK_ALTIVEC, "__builtin_vec_extract", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_EXTRACT);
12729 def_builtin (MASK_ALTIVEC, "__builtin_vec_insert", opaque_ftype_opaque_opaque_int, ALTIVEC_BUILTIN_VEC_INSERT);
12730 def_builtin (MASK_ALTIVEC, "__builtin_vec_vspltw", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VSPLTW);
12731 def_builtin (MASK_ALTIVEC, "__builtin_vec_vsplth", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VSPLTH);
12732 def_builtin (MASK_ALTIVEC, "__builtin_vec_vspltb", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VSPLTB);
12733 def_builtin (MASK_ALTIVEC, "__builtin_vec_ctf", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_CTF);
12734 def_builtin (MASK_ALTIVEC, "__builtin_vec_vcfsx", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VCFSX);
12735 def_builtin (MASK_ALTIVEC, "__builtin_vec_vcfux", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VCFUX);
12736 def_builtin (MASK_ALTIVEC, "__builtin_vec_cts", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_CTS);
12737 def_builtin (MASK_ALTIVEC, "__builtin_vec_ctu", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_CTU);
12738
12739 /* Add the DST variants. */
12740 d = bdesc_dst;
12741 for (i = 0; i < ARRAY_SIZE (bdesc_dst); i++, d++)
12742 def_builtin (d->mask, d->name, void_ftype_pcvoid_int_int, d->code);
12743
12744 /* Initialize the predicates. */
12745 dp = bdesc_altivec_preds;
12746 for (i = 0; i < ARRAY_SIZE (bdesc_altivec_preds); i++, dp++)
12747 {
12748 enum machine_mode mode1;
12749 tree type;
12750 bool is_overloaded = ((dp->code >= ALTIVEC_BUILTIN_OVERLOADED_FIRST
12751 && dp->code <= ALTIVEC_BUILTIN_OVERLOADED_LAST)
12752 || (dp->code >= VSX_BUILTIN_OVERLOADED_FIRST
12753 && dp->code <= VSX_BUILTIN_OVERLOADED_LAST));
12754
12755 if (is_overloaded)
12756 mode1 = VOIDmode;
12757 else
12758 mode1 = insn_data[dp->icode].operand[1].mode;
12759
12760 switch (mode1)
12761 {
12762 case VOIDmode:
12763 type = int_ftype_int_opaque_opaque;
12764 break;
12765 case V4SImode:
12766 type = int_ftype_int_v4si_v4si;
12767 break;
12768 case V8HImode:
12769 type = int_ftype_int_v8hi_v8hi;
12770 break;
12771 case V16QImode:
12772 type = int_ftype_int_v16qi_v16qi;
12773 break;
12774 case V4SFmode:
12775 type = int_ftype_int_v4sf_v4sf;
12776 break;
12777 case V2DFmode:
12778 type = int_ftype_int_v2df_v2df;
12779 break;
12780 default:
12781 gcc_unreachable ();
12782 }
12783
12784 def_builtin (dp->mask, dp->name, type, dp->code);
12785 }
12786
12787 /* Initialize the abs* operators. */
12788 d = bdesc_abs;
12789 for (i = 0; i < ARRAY_SIZE (bdesc_abs); i++, d++)
12790 {
12791 enum machine_mode mode0;
12792 tree type;
12793
12794 mode0 = insn_data[d->icode].operand[0].mode;
12795
12796 switch (mode0)
12797 {
12798 case V4SImode:
12799 type = v4si_ftype_v4si;
12800 break;
12801 case V8HImode:
12802 type = v8hi_ftype_v8hi;
12803 break;
12804 case V16QImode:
12805 type = v16qi_ftype_v16qi;
12806 break;
12807 case V4SFmode:
12808 type = v4sf_ftype_v4sf;
12809 break;
12810 case V2DFmode:
12811 type = v2df_ftype_v2df;
12812 break;
12813 default:
12814 gcc_unreachable ();
12815 }
12816
12817 def_builtin (d->mask, d->name, type, d->code);
12818 }
12819
12820 if (TARGET_ALTIVEC)
12821 {
12822 tree decl;
12823
12824 /* Initialize target builtin that implements
12825 targetm.vectorize.builtin_mask_for_load. */
12826
12827 decl = add_builtin_function ("__builtin_altivec_mask_for_load",
12828 v16qi_ftype_long_pcvoid,
12829 ALTIVEC_BUILTIN_MASK_FOR_LOAD,
12830 BUILT_IN_MD, NULL, NULL_TREE);
12831 TREE_READONLY (decl) = 1;
12832 /* Record the decl. Will be used by rs6000_builtin_mask_for_load. */
12833 altivec_builtin_mask_for_load = decl;
12834 }
12835
12836 /* Access to the vec_init patterns. */
12837 ftype = build_function_type_list (V4SI_type_node, integer_type_node,
12838 integer_type_node, integer_type_node,
12839 integer_type_node, NULL_TREE);
12840 def_builtin (MASK_ALTIVEC, "__builtin_vec_init_v4si", ftype,
12841 ALTIVEC_BUILTIN_VEC_INIT_V4SI);
12842
12843 ftype = build_function_type_list (V8HI_type_node, short_integer_type_node,
12844 short_integer_type_node,
12845 short_integer_type_node,
12846 short_integer_type_node,
12847 short_integer_type_node,
12848 short_integer_type_node,
12849 short_integer_type_node,
12850 short_integer_type_node, NULL_TREE);
12851 def_builtin (MASK_ALTIVEC, "__builtin_vec_init_v8hi", ftype,
12852 ALTIVEC_BUILTIN_VEC_INIT_V8HI);
12853
12854 ftype = build_function_type_list (V16QI_type_node, char_type_node,
12855 char_type_node, char_type_node,
12856 char_type_node, char_type_node,
12857 char_type_node, char_type_node,
12858 char_type_node, char_type_node,
12859 char_type_node, char_type_node,
12860 char_type_node, char_type_node,
12861 char_type_node, char_type_node,
12862 char_type_node, NULL_TREE);
12863 def_builtin (MASK_ALTIVEC, "__builtin_vec_init_v16qi", ftype,
12864 ALTIVEC_BUILTIN_VEC_INIT_V16QI);
12865
12866 ftype = build_function_type_list (V4SF_type_node, float_type_node,
12867 float_type_node, float_type_node,
12868 float_type_node, NULL_TREE);
12869 def_builtin (MASK_ALTIVEC, "__builtin_vec_init_v4sf", ftype,
12870 ALTIVEC_BUILTIN_VEC_INIT_V4SF);
12871
12872 if (TARGET_VSX)
12873 {
12874 ftype = build_function_type_list (V2DF_type_node, double_type_node,
12875 double_type_node, NULL_TREE);
12876 def_builtin (MASK_VSX, "__builtin_vec_init_v2df", ftype,
12877 VSX_BUILTIN_VEC_INIT_V2DF);
12878
12879 ftype = build_function_type_list (V2DI_type_node, intDI_type_node,
12880 intDI_type_node, NULL_TREE);
12881 def_builtin (MASK_VSX, "__builtin_vec_init_v2di", ftype,
12882 VSX_BUILTIN_VEC_INIT_V2DI);
12883 }
12884
12885 /* Access to the vec_set patterns. */
12886 ftype = build_function_type_list (V4SI_type_node, V4SI_type_node,
12887 intSI_type_node,
12888 integer_type_node, NULL_TREE);
12889 def_builtin (MASK_ALTIVEC, "__builtin_vec_set_v4si", ftype,
12890 ALTIVEC_BUILTIN_VEC_SET_V4SI);
12891
12892 ftype = build_function_type_list (V8HI_type_node, V8HI_type_node,
12893 intHI_type_node,
12894 integer_type_node, NULL_TREE);
12895 def_builtin (MASK_ALTIVEC, "__builtin_vec_set_v8hi", ftype,
12896 ALTIVEC_BUILTIN_VEC_SET_V8HI);
12897
12898 ftype = build_function_type_list (V16QI_type_node, V16QI_type_node,
12899 intQI_type_node,
12900 integer_type_node, NULL_TREE);
12901 def_builtin (MASK_ALTIVEC, "__builtin_vec_set_v16qi", ftype,
12902 ALTIVEC_BUILTIN_VEC_SET_V16QI);
12903
12904 ftype = build_function_type_list (V4SF_type_node, V4SF_type_node,
12905 float_type_node,
12906 integer_type_node, NULL_TREE);
12907 def_builtin (MASK_ALTIVEC|MASK_VSX, "__builtin_vec_set_v4sf", ftype,
12908 ALTIVEC_BUILTIN_VEC_SET_V4SF);
12909
12910 if (TARGET_VSX)
12911 {
12912 ftype = build_function_type_list (V2DF_type_node, V2DF_type_node,
12913 double_type_node,
12914 integer_type_node, NULL_TREE);
12915 def_builtin (MASK_VSX, "__builtin_vec_set_v2df", ftype,
12916 VSX_BUILTIN_VEC_SET_V2DF);
12917
12918 ftype = build_function_type_list (V2DI_type_node, V2DI_type_node,
12919 intDI_type_node,
12920 integer_type_node, NULL_TREE);
12921 def_builtin (MASK_VSX, "__builtin_vec_set_v2di", ftype,
12922 VSX_BUILTIN_VEC_SET_V2DI);
12923 }
12924
12925 /* Access to the vec_extract patterns. */
12926 ftype = build_function_type_list (intSI_type_node, V4SI_type_node,
12927 integer_type_node, NULL_TREE);
12928 def_builtin (MASK_ALTIVEC, "__builtin_vec_ext_v4si", ftype,
12929 ALTIVEC_BUILTIN_VEC_EXT_V4SI);
12930
12931 ftype = build_function_type_list (intHI_type_node, V8HI_type_node,
12932 integer_type_node, NULL_TREE);
12933 def_builtin (MASK_ALTIVEC, "__builtin_vec_ext_v8hi", ftype,
12934 ALTIVEC_BUILTIN_VEC_EXT_V8HI);
12935
12936 ftype = build_function_type_list (intQI_type_node, V16QI_type_node,
12937 integer_type_node, NULL_TREE);
12938 def_builtin (MASK_ALTIVEC, "__builtin_vec_ext_v16qi", ftype,
12939 ALTIVEC_BUILTIN_VEC_EXT_V16QI);
12940
12941 ftype = build_function_type_list (float_type_node, V4SF_type_node,
12942 integer_type_node, NULL_TREE);
12943 def_builtin (MASK_ALTIVEC|MASK_VSX, "__builtin_vec_ext_v4sf", ftype,
12944 ALTIVEC_BUILTIN_VEC_EXT_V4SF);
12945
12946 if (TARGET_VSX)
12947 {
12948 ftype = build_function_type_list (double_type_node, V2DF_type_node,
12949 integer_type_node, NULL_TREE);
12950 def_builtin (MASK_VSX, "__builtin_vec_ext_v2df", ftype,
12951 VSX_BUILTIN_VEC_EXT_V2DF);
12952
12953 ftype = build_function_type_list (intDI_type_node, V2DI_type_node,
12954 integer_type_node, NULL_TREE);
12955 def_builtin (MASK_VSX, "__builtin_vec_ext_v2di", ftype,
12956 VSX_BUILTIN_VEC_EXT_V2DI);
12957 }
12958 }
12959
12960 /* Hash function for builtin functions with up to 3 arguments and a return
12961 type. */
12962 static unsigned
12963 builtin_hash_function (const void *hash_entry)
12964 {
12965 unsigned ret = 0;
12966 int i;
12967 const struct builtin_hash_struct *bh =
12968 (const struct builtin_hash_struct *) hash_entry;
12969
12970 for (i = 0; i < 4; i++)
12971 {
12972 ret = (ret * (unsigned)MAX_MACHINE_MODE) + ((unsigned)bh->mode[i]);
12973 ret = (ret * 2) + bh->uns_p[i];
12974 }
12975
12976 return ret;
12977 }
12978
12979 /* Compare builtin hash entries H1 and H2 for equivalence. */
12980 static int
12981 builtin_hash_eq (const void *h1, const void *h2)
12982 {
12983 const struct builtin_hash_struct *p1 = (const struct builtin_hash_struct *) h1;
12984 const struct builtin_hash_struct *p2 = (const struct builtin_hash_struct *) h2;
12985
12986 return ((p1->mode[0] == p2->mode[0])
12987 && (p1->mode[1] == p2->mode[1])
12988 && (p1->mode[2] == p2->mode[2])
12989 && (p1->mode[3] == p2->mode[3])
12990 && (p1->uns_p[0] == p2->uns_p[0])
12991 && (p1->uns_p[1] == p2->uns_p[1])
12992 && (p1->uns_p[2] == p2->uns_p[2])
12993 && (p1->uns_p[3] == p2->uns_p[3]));
12994 }
12995
12996 /* Map types for builtin functions with an explicit return type and up to 3
12997 arguments. Functions with fewer than 3 arguments use VOIDmode as the type
12998 of the argument. */
12999 static tree
13000 builtin_function_type (enum machine_mode mode_ret, enum machine_mode mode_arg0,
13001 enum machine_mode mode_arg1, enum machine_mode mode_arg2,
13002 enum rs6000_builtins builtin, const char *name)
13003 {
13004 struct builtin_hash_struct h;
13005 struct builtin_hash_struct *h2;
13006 void **found;
13007 int num_args = 3;
13008 int i;
13009 tree ret_type = NULL_TREE;
13010 tree arg_type[3] = { NULL_TREE, NULL_TREE, NULL_TREE };
13011 tree args;
13012
13013 /* Create builtin_hash_table. */
13014 if (builtin_hash_table == NULL)
13015 builtin_hash_table = htab_create_ggc (1500, builtin_hash_function,
13016 builtin_hash_eq, NULL);
13017
13018 h.type = NULL_TREE;
13019 h.mode[0] = mode_ret;
13020 h.mode[1] = mode_arg0;
13021 h.mode[2] = mode_arg1;
13022 h.mode[3] = mode_arg2;
13023 h.uns_p[0] = 0;
13024 h.uns_p[1] = 0;
13025 h.uns_p[2] = 0;
13026 h.uns_p[3] = 0;
13027
13028 /* If the builtin is a type that produces unsigned results or takes unsigned
13029 arguments, and it is returned as a decl for the vectorizer (such as
13030 widening multiplies, permute), make sure the arguments and return value
13031 are type correct. */
13032 switch (builtin)
13033 {
13034 /* unsigned 2 argument functions. */
13035 case ALTIVEC_BUILTIN_VMULEUB_UNS:
13036 case ALTIVEC_BUILTIN_VMULEUH_UNS:
13037 case ALTIVEC_BUILTIN_VMULOUB_UNS:
13038 case ALTIVEC_BUILTIN_VMULOUH_UNS:
13039 h.uns_p[0] = 1;
13040 h.uns_p[1] = 1;
13041 h.uns_p[2] = 1;
13042 break;
13043
13044 /* unsigned 3 argument functions. */
13045 case ALTIVEC_BUILTIN_VPERM_16QI_UNS:
13046 case ALTIVEC_BUILTIN_VPERM_8HI_UNS:
13047 case ALTIVEC_BUILTIN_VPERM_4SI_UNS:
13048 case ALTIVEC_BUILTIN_VPERM_2DI_UNS:
13049 case ALTIVEC_BUILTIN_VSEL_16QI_UNS:
13050 case ALTIVEC_BUILTIN_VSEL_8HI_UNS:
13051 case ALTIVEC_BUILTIN_VSEL_4SI_UNS:
13052 case ALTIVEC_BUILTIN_VSEL_2DI_UNS:
13053 case VSX_BUILTIN_VPERM_16QI_UNS:
13054 case VSX_BUILTIN_VPERM_8HI_UNS:
13055 case VSX_BUILTIN_VPERM_4SI_UNS:
13056 case VSX_BUILTIN_VPERM_2DI_UNS:
13057 case VSX_BUILTIN_XXSEL_16QI_UNS:
13058 case VSX_BUILTIN_XXSEL_8HI_UNS:
13059 case VSX_BUILTIN_XXSEL_4SI_UNS:
13060 case VSX_BUILTIN_XXSEL_2DI_UNS:
13061 h.uns_p[0] = 1;
13062 h.uns_p[1] = 1;
13063 h.uns_p[2] = 1;
13064 h.uns_p[3] = 1;
13065 break;
13066
13067 /* signed permute functions with unsigned char mask. */
13068 case ALTIVEC_BUILTIN_VPERM_16QI:
13069 case ALTIVEC_BUILTIN_VPERM_8HI:
13070 case ALTIVEC_BUILTIN_VPERM_4SI:
13071 case ALTIVEC_BUILTIN_VPERM_4SF:
13072 case ALTIVEC_BUILTIN_VPERM_2DI:
13073 case ALTIVEC_BUILTIN_VPERM_2DF:
13074 case VSX_BUILTIN_VPERM_16QI:
13075 case VSX_BUILTIN_VPERM_8HI:
13076 case VSX_BUILTIN_VPERM_4SI:
13077 case VSX_BUILTIN_VPERM_4SF:
13078 case VSX_BUILTIN_VPERM_2DI:
13079 case VSX_BUILTIN_VPERM_2DF:
13080 h.uns_p[3] = 1;
13081 break;
13082
13083 /* unsigned args, signed return. */
13084 case VSX_BUILTIN_XVCVUXDDP_UNS:
13085 case VECTOR_BUILTIN_UNSFLOAT_V4SI_V4SF:
13086 h.uns_p[1] = 1;
13087 break;
13088
13089 /* signed args, unsigned return. */
13090 case VSX_BUILTIN_XVCVDPUXDS_UNS:
13091 case VECTOR_BUILTIN_FIXUNS_V4SF_V4SI:
13092 h.uns_p[0] = 1;
13093 break;
13094
13095 default:
13096 break;
13097 }
13098
13099 /* Figure out how many args are present. */
13100 while (num_args > 0 && h.mode[num_args] == VOIDmode)
13101 num_args--;
13102
13103 if (num_args == 0)
13104 fatal_error ("internal error: builtin function %s had no type", name);
13105
13106 ret_type = builtin_mode_to_type[h.mode[0]][h.uns_p[0]];
13107 if (!ret_type && h.uns_p[0])
13108 ret_type = builtin_mode_to_type[h.mode[0]][0];
13109
13110 if (!ret_type)
13111 fatal_error ("internal error: builtin function %s had an unexpected "
13112 "return type %s", name, GET_MODE_NAME (h.mode[0]));
13113
13114 for (i = 0; i < num_args; i++)
13115 {
13116 int m = (int) h.mode[i+1];
13117 int uns_p = h.uns_p[i+1];
13118
13119 arg_type[i] = builtin_mode_to_type[m][uns_p];
13120 if (!arg_type[i] && uns_p)
13121 arg_type[i] = builtin_mode_to_type[m][0];
13122
13123 if (!arg_type[i])
13124 fatal_error ("internal error: builtin function %s, argument %d "
13125 "had unexpected argument type %s", name, i,
13126 GET_MODE_NAME (m));
13127 }
13128
13129 found = htab_find_slot (builtin_hash_table, &h, INSERT);
13130 if (*found == NULL)
13131 {
13132 h2 = ggc_alloc_builtin_hash_struct ();
13133 *h2 = h;
13134 *found = (void *)h2;
13135 args = void_list_node;
13136
13137 for (i = num_args - 1; i >= 0; i--)
13138 args = tree_cons (NULL_TREE, arg_type[i], args);
13139
13140 h2->type = build_function_type (ret_type, args);
13141 }
13142
13143 return ((struct builtin_hash_struct *)(*found))->type;
13144 }
13145
13146 static void
13147 rs6000_common_init_builtins (void)
13148 {
13149 const struct builtin_description *d;
13150 size_t i;
13151
13152 tree opaque_ftype_opaque = NULL_TREE;
13153 tree opaque_ftype_opaque_opaque = NULL_TREE;
13154 tree opaque_ftype_opaque_opaque_opaque = NULL_TREE;
13155 tree v2si_ftype_qi = NULL_TREE;
13156 tree v2si_ftype_v2si_qi = NULL_TREE;
13157 tree v2si_ftype_int_qi = NULL_TREE;
13158
13159 if (!TARGET_PAIRED_FLOAT)
13160 {
13161 builtin_mode_to_type[V2SImode][0] = opaque_V2SI_type_node;
13162 builtin_mode_to_type[V2SFmode][0] = opaque_V2SF_type_node;
13163 }
13164
13165 /* Add the ternary operators. */
13166 d = bdesc_3arg;
13167 for (i = 0; i < ARRAY_SIZE (bdesc_3arg); i++, d++)
13168 {
13169 tree type;
13170 int mask = d->mask;
13171
13172 if ((mask != 0 && (mask & target_flags) == 0)
13173 || (mask == 0 && !TARGET_PAIRED_FLOAT))
13174 continue;
13175
13176 if ((d->code >= ALTIVEC_BUILTIN_OVERLOADED_FIRST
13177 && d->code <= ALTIVEC_BUILTIN_OVERLOADED_LAST)
13178 || (d->code >= VSX_BUILTIN_OVERLOADED_FIRST
13179 && d->code <= VSX_BUILTIN_OVERLOADED_LAST))
13180 {
13181 if (! (type = opaque_ftype_opaque_opaque_opaque))
13182 type = opaque_ftype_opaque_opaque_opaque
13183 = build_function_type_list (opaque_V4SI_type_node,
13184 opaque_V4SI_type_node,
13185 opaque_V4SI_type_node,
13186 opaque_V4SI_type_node,
13187 NULL_TREE);
13188 }
13189 else
13190 {
13191 enum insn_code icode = d->icode;
13192 if (d->name == 0 || icode == CODE_FOR_nothing)
13193 continue;
13194
13195 type = builtin_function_type (insn_data[icode].operand[0].mode,
13196 insn_data[icode].operand[1].mode,
13197 insn_data[icode].operand[2].mode,
13198 insn_data[icode].operand[3].mode,
13199 d->code, d->name);
13200 }
13201
13202 def_builtin (d->mask, d->name, type, d->code);
13203 }
13204
13205 /* Add the binary operators. */
13206 d = bdesc_2arg;
13207 for (i = 0; i < ARRAY_SIZE (bdesc_2arg); i++, d++)
13208 {
13209 enum machine_mode mode0, mode1, mode2;
13210 tree type;
13211 int mask = d->mask;
13212
13213 if ((mask != 0 && (mask & target_flags) == 0)
13214 || (mask == 0 && !TARGET_PAIRED_FLOAT))
13215 continue;
13216
13217 if ((d->code >= ALTIVEC_BUILTIN_OVERLOADED_FIRST
13218 && d->code <= ALTIVEC_BUILTIN_OVERLOADED_LAST)
13219 || (d->code >= VSX_BUILTIN_OVERLOADED_FIRST
13220 && d->code <= VSX_BUILTIN_OVERLOADED_LAST))
13221 {
13222 if (! (type = opaque_ftype_opaque_opaque))
13223 type = opaque_ftype_opaque_opaque
13224 = build_function_type_list (opaque_V4SI_type_node,
13225 opaque_V4SI_type_node,
13226 opaque_V4SI_type_node,
13227 NULL_TREE);
13228 }
13229 else
13230 {
13231 enum insn_code icode = d->icode;
13232 if (d->name == 0 || icode == CODE_FOR_nothing)
13233 continue;
13234
13235 mode0 = insn_data[icode].operand[0].mode;
13236 mode1 = insn_data[icode].operand[1].mode;
13237 mode2 = insn_data[icode].operand[2].mode;
13238
13239 if (mode0 == V2SImode && mode1 == V2SImode && mode2 == QImode)
13240 {
13241 if (! (type = v2si_ftype_v2si_qi))
13242 type = v2si_ftype_v2si_qi
13243 = build_function_type_list (opaque_V2SI_type_node,
13244 opaque_V2SI_type_node,
13245 char_type_node,
13246 NULL_TREE);
13247 }
13248
13249 else if (mode0 == V2SImode && GET_MODE_CLASS (mode1) == MODE_INT
13250 && mode2 == QImode)
13251 {
13252 if (! (type = v2si_ftype_int_qi))
13253 type = v2si_ftype_int_qi
13254 = build_function_type_list (opaque_V2SI_type_node,
13255 integer_type_node,
13256 char_type_node,
13257 NULL_TREE);
13258 }
13259
13260 else
13261 type = builtin_function_type (mode0, mode1, mode2, VOIDmode,
13262 d->code, d->name);
13263 }
13264
13265 def_builtin (d->mask, d->name, type, d->code);
13266 }
13267
13268 /* Add the simple unary operators. */
13269 d = (struct builtin_description *) bdesc_1arg;
13270 for (i = 0; i < ARRAY_SIZE (bdesc_1arg); i++, d++)
13271 {
13272 enum machine_mode mode0, mode1;
13273 tree type;
13274 int mask = d->mask;
13275
13276 if ((mask != 0 && (mask & target_flags) == 0)
13277 || (mask == 0 && !TARGET_PAIRED_FLOAT))
13278 continue;
13279
13280 if ((d->code >= ALTIVEC_BUILTIN_OVERLOADED_FIRST
13281 && d->code <= ALTIVEC_BUILTIN_OVERLOADED_LAST)
13282 || (d->code >= VSX_BUILTIN_OVERLOADED_FIRST
13283 && d->code <= VSX_BUILTIN_OVERLOADED_LAST))
13284 {
13285 if (! (type = opaque_ftype_opaque))
13286 type = opaque_ftype_opaque
13287 = build_function_type_list (opaque_V4SI_type_node,
13288 opaque_V4SI_type_node,
13289 NULL_TREE);
13290 }
13291 else
13292 {
13293 enum insn_code icode = d->icode;
13294 if (d->name == 0 || icode == CODE_FOR_nothing)
13295 continue;
13296
13297 mode0 = insn_data[icode].operand[0].mode;
13298 mode1 = insn_data[icode].operand[1].mode;
13299
13300 if (mode0 == V2SImode && mode1 == QImode)
13301 {
13302 if (! (type = v2si_ftype_qi))
13303 type = v2si_ftype_qi
13304 = build_function_type_list (opaque_V2SI_type_node,
13305 char_type_node,
13306 NULL_TREE);
13307 }
13308
13309 else
13310 type = builtin_function_type (mode0, mode1, VOIDmode, VOIDmode,
13311 d->code, d->name);
13312 }
13313
13314 def_builtin (d->mask, d->name, type, d->code);
13315 }
13316 }
13317
13318 static void
13319 rs6000_init_libfuncs (void)
13320 {
13321 if (DEFAULT_ABI != ABI_V4 && TARGET_XCOFF
13322 && !TARGET_POWER2 && !TARGET_POWERPC)
13323 {
13324 /* AIX library routines for float->int conversion. */
13325 set_conv_libfunc (sfix_optab, SImode, DFmode, "__itrunc");
13326 set_conv_libfunc (ufix_optab, SImode, DFmode, "__uitrunc");
13327 set_conv_libfunc (sfix_optab, SImode, TFmode, "_qitrunc");
13328 set_conv_libfunc (ufix_optab, SImode, TFmode, "_quitrunc");
13329 }
13330
13331 if (!TARGET_IEEEQUAD)
13332 /* AIX/Darwin/64-bit Linux quad floating point routines. */
13333 if (!TARGET_XL_COMPAT)
13334 {
13335 set_optab_libfunc (add_optab, TFmode, "__gcc_qadd");
13336 set_optab_libfunc (sub_optab, TFmode, "__gcc_qsub");
13337 set_optab_libfunc (smul_optab, TFmode, "__gcc_qmul");
13338 set_optab_libfunc (sdiv_optab, TFmode, "__gcc_qdiv");
13339
13340 if (!(TARGET_HARD_FLOAT && (TARGET_FPRS || TARGET_E500_DOUBLE)))
13341 {
13342 set_optab_libfunc (neg_optab, TFmode, "__gcc_qneg");
13343 set_optab_libfunc (eq_optab, TFmode, "__gcc_qeq");
13344 set_optab_libfunc (ne_optab, TFmode, "__gcc_qne");
13345 set_optab_libfunc (gt_optab, TFmode, "__gcc_qgt");
13346 set_optab_libfunc (ge_optab, TFmode, "__gcc_qge");
13347 set_optab_libfunc (lt_optab, TFmode, "__gcc_qlt");
13348 set_optab_libfunc (le_optab, TFmode, "__gcc_qle");
13349
13350 set_conv_libfunc (sext_optab, TFmode, SFmode, "__gcc_stoq");
13351 set_conv_libfunc (sext_optab, TFmode, DFmode, "__gcc_dtoq");
13352 set_conv_libfunc (trunc_optab, SFmode, TFmode, "__gcc_qtos");
13353 set_conv_libfunc (trunc_optab, DFmode, TFmode, "__gcc_qtod");
13354 set_conv_libfunc (sfix_optab, SImode, TFmode, "__gcc_qtoi");
13355 set_conv_libfunc (ufix_optab, SImode, TFmode, "__gcc_qtou");
13356 set_conv_libfunc (sfloat_optab, TFmode, SImode, "__gcc_itoq");
13357 set_conv_libfunc (ufloat_optab, TFmode, SImode, "__gcc_utoq");
13358 }
13359
13360 if (!(TARGET_HARD_FLOAT && TARGET_FPRS))
13361 set_optab_libfunc (unord_optab, TFmode, "__gcc_qunord");
13362 }
13363 else
13364 {
13365 set_optab_libfunc (add_optab, TFmode, "_xlqadd");
13366 set_optab_libfunc (sub_optab, TFmode, "_xlqsub");
13367 set_optab_libfunc (smul_optab, TFmode, "_xlqmul");
13368 set_optab_libfunc (sdiv_optab, TFmode, "_xlqdiv");
13369 }
13370 else
13371 {
13372 /* 32-bit SVR4 quad floating point routines. */
13373
13374 set_optab_libfunc (add_optab, TFmode, "_q_add");
13375 set_optab_libfunc (sub_optab, TFmode, "_q_sub");
13376 set_optab_libfunc (neg_optab, TFmode, "_q_neg");
13377 set_optab_libfunc (smul_optab, TFmode, "_q_mul");
13378 set_optab_libfunc (sdiv_optab, TFmode, "_q_div");
13379 if (TARGET_PPC_GPOPT || TARGET_POWER2)
13380 set_optab_libfunc (sqrt_optab, TFmode, "_q_sqrt");
13381
13382 set_optab_libfunc (eq_optab, TFmode, "_q_feq");
13383 set_optab_libfunc (ne_optab, TFmode, "_q_fne");
13384 set_optab_libfunc (gt_optab, TFmode, "_q_fgt");
13385 set_optab_libfunc (ge_optab, TFmode, "_q_fge");
13386 set_optab_libfunc (lt_optab, TFmode, "_q_flt");
13387 set_optab_libfunc (le_optab, TFmode, "_q_fle");
13388
13389 set_conv_libfunc (sext_optab, TFmode, SFmode, "_q_stoq");
13390 set_conv_libfunc (sext_optab, TFmode, DFmode, "_q_dtoq");
13391 set_conv_libfunc (trunc_optab, SFmode, TFmode, "_q_qtos");
13392 set_conv_libfunc (trunc_optab, DFmode, TFmode, "_q_qtod");
13393 set_conv_libfunc (sfix_optab, SImode, TFmode, "_q_qtoi");
13394 set_conv_libfunc (ufix_optab, SImode, TFmode, "_q_qtou");
13395 set_conv_libfunc (sfloat_optab, TFmode, SImode, "_q_itoq");
13396 set_conv_libfunc (ufloat_optab, TFmode, SImode, "_q_utoq");
13397 }
13398 }
13399
13400 \f
13401 /* Expand a block clear operation, and return 1 if successful. Return 0
13402 if we should let the compiler generate normal code.
13403
13404 operands[0] is the destination
13405 operands[1] is the length
13406 operands[3] is the alignment */
13407
13408 int
13409 expand_block_clear (rtx operands[])
13410 {
13411 rtx orig_dest = operands[0];
13412 rtx bytes_rtx = operands[1];
13413 rtx align_rtx = operands[3];
13414 bool constp = (GET_CODE (bytes_rtx) == CONST_INT);
13415 HOST_WIDE_INT align;
13416 HOST_WIDE_INT bytes;
13417 int offset;
13418 int clear_bytes;
13419 int clear_step;
13420
13421 /* If this is not a fixed size move, just call memcpy */
13422 if (! constp)
13423 return 0;
13424
13425 /* This must be a fixed size alignment */
13426 gcc_assert (GET_CODE (align_rtx) == CONST_INT);
13427 align = INTVAL (align_rtx) * BITS_PER_UNIT;
13428
13429 /* Anything to clear? */
13430 bytes = INTVAL (bytes_rtx);
13431 if (bytes <= 0)
13432 return 1;
13433
13434 /* Use the builtin memset after a point, to avoid huge code bloat.
13435 When optimize_size, avoid any significant code bloat; calling
13436 memset is about 4 instructions, so allow for one instruction to
13437 load zero and three to do clearing. */
13438 if (TARGET_ALTIVEC && align >= 128)
13439 clear_step = 16;
13440 else if (TARGET_POWERPC64 && align >= 32)
13441 clear_step = 8;
13442 else if (TARGET_SPE && align >= 64)
13443 clear_step = 8;
13444 else
13445 clear_step = 4;
13446
13447 if (optimize_size && bytes > 3 * clear_step)
13448 return 0;
13449 if (! optimize_size && bytes > 8 * clear_step)
13450 return 0;
13451
13452 for (offset = 0; bytes > 0; offset += clear_bytes, bytes -= clear_bytes)
13453 {
13454 enum machine_mode mode = BLKmode;
13455 rtx dest;
13456
13457 if (bytes >= 16 && TARGET_ALTIVEC && align >= 128)
13458 {
13459 clear_bytes = 16;
13460 mode = V4SImode;
13461 }
13462 else if (bytes >= 8 && TARGET_SPE && align >= 64)
13463 {
13464 clear_bytes = 8;
13465 mode = V2SImode;
13466 }
13467 else if (bytes >= 8 && TARGET_POWERPC64
13468 /* 64-bit loads and stores require word-aligned
13469 displacements. */
13470 && (align >= 64 || (!STRICT_ALIGNMENT && align >= 32)))
13471 {
13472 clear_bytes = 8;
13473 mode = DImode;
13474 }
13475 else if (bytes >= 4 && (align >= 32 || !STRICT_ALIGNMENT))
13476 { /* move 4 bytes */
13477 clear_bytes = 4;
13478 mode = SImode;
13479 }
13480 else if (bytes >= 2 && (align >= 16 || !STRICT_ALIGNMENT))
13481 { /* move 2 bytes */
13482 clear_bytes = 2;
13483 mode = HImode;
13484 }
13485 else /* move 1 byte at a time */
13486 {
13487 clear_bytes = 1;
13488 mode = QImode;
13489 }
13490
13491 dest = adjust_address (orig_dest, mode, offset);
13492
13493 emit_move_insn (dest, CONST0_RTX (mode));
13494 }
13495
13496 return 1;
13497 }
13498
13499 \f
13500 /* Expand a block move operation, and return 1 if successful. Return 0
13501 if we should let the compiler generate normal code.
13502
13503 operands[0] is the destination
13504 operands[1] is the source
13505 operands[2] is the length
13506 operands[3] is the alignment */
13507
13508 #define MAX_MOVE_REG 4
13509
13510 int
13511 expand_block_move (rtx operands[])
13512 {
13513 rtx orig_dest = operands[0];
13514 rtx orig_src = operands[1];
13515 rtx bytes_rtx = operands[2];
13516 rtx align_rtx = operands[3];
13517 int constp = (GET_CODE (bytes_rtx) == CONST_INT);
13518 int align;
13519 int bytes;
13520 int offset;
13521 int move_bytes;
13522 rtx stores[MAX_MOVE_REG];
13523 int num_reg = 0;
13524
13525 /* If this is not a fixed size move, just call memcpy */
13526 if (! constp)
13527 return 0;
13528
13529 /* This must be a fixed size alignment */
13530 gcc_assert (GET_CODE (align_rtx) == CONST_INT);
13531 align = INTVAL (align_rtx) * BITS_PER_UNIT;
13532
13533 /* Anything to move? */
13534 bytes = INTVAL (bytes_rtx);
13535 if (bytes <= 0)
13536 return 1;
13537
13538 if (bytes > rs6000_block_move_inline_limit)
13539 return 0;
13540
13541 for (offset = 0; bytes > 0; offset += move_bytes, bytes -= move_bytes)
13542 {
13543 union {
13544 rtx (*movmemsi) (rtx, rtx, rtx, rtx);
13545 rtx (*mov) (rtx, rtx);
13546 } gen_func;
13547 enum machine_mode mode = BLKmode;
13548 rtx src, dest;
13549
13550 /* Altivec first, since it will be faster than a string move
13551 when it applies, and usually not significantly larger. */
13552 if (TARGET_ALTIVEC && bytes >= 16 && align >= 128)
13553 {
13554 move_bytes = 16;
13555 mode = V4SImode;
13556 gen_func.mov = gen_movv4si;
13557 }
13558 else if (TARGET_SPE && bytes >= 8 && align >= 64)
13559 {
13560 move_bytes = 8;
13561 mode = V2SImode;
13562 gen_func.mov = gen_movv2si;
13563 }
13564 else if (TARGET_STRING
13565 && bytes > 24 /* move up to 32 bytes at a time */
13566 && ! fixed_regs[5]
13567 && ! fixed_regs[6]
13568 && ! fixed_regs[7]
13569 && ! fixed_regs[8]
13570 && ! fixed_regs[9]
13571 && ! fixed_regs[10]
13572 && ! fixed_regs[11]
13573 && ! fixed_regs[12])
13574 {
13575 move_bytes = (bytes > 32) ? 32 : bytes;
13576 gen_func.movmemsi = gen_movmemsi_8reg;
13577 }
13578 else if (TARGET_STRING
13579 && bytes > 16 /* move up to 24 bytes at a time */
13580 && ! fixed_regs[5]
13581 && ! fixed_regs[6]
13582 && ! fixed_regs[7]
13583 && ! fixed_regs[8]
13584 && ! fixed_regs[9]
13585 && ! fixed_regs[10])
13586 {
13587 move_bytes = (bytes > 24) ? 24 : bytes;
13588 gen_func.movmemsi = gen_movmemsi_6reg;
13589 }
13590 else if (TARGET_STRING
13591 && bytes > 8 /* move up to 16 bytes at a time */
13592 && ! fixed_regs[5]
13593 && ! fixed_regs[6]
13594 && ! fixed_regs[7]
13595 && ! fixed_regs[8])
13596 {
13597 move_bytes = (bytes > 16) ? 16 : bytes;
13598 gen_func.movmemsi = gen_movmemsi_4reg;
13599 }
13600 else if (bytes >= 8 && TARGET_POWERPC64
13601 /* 64-bit loads and stores require word-aligned
13602 displacements. */
13603 && (align >= 64 || (!STRICT_ALIGNMENT && align >= 32)))
13604 {
13605 move_bytes = 8;
13606 mode = DImode;
13607 gen_func.mov = gen_movdi;
13608 }
13609 else if (TARGET_STRING && bytes > 4 && !TARGET_POWERPC64)
13610 { /* move up to 8 bytes at a time */
13611 move_bytes = (bytes > 8) ? 8 : bytes;
13612 gen_func.movmemsi = gen_movmemsi_2reg;
13613 }
13614 else if (bytes >= 4 && (align >= 32 || !STRICT_ALIGNMENT))
13615 { /* move 4 bytes */
13616 move_bytes = 4;
13617 mode = SImode;
13618 gen_func.mov = gen_movsi;
13619 }
13620 else if (bytes >= 2 && (align >= 16 || !STRICT_ALIGNMENT))
13621 { /* move 2 bytes */
13622 move_bytes = 2;
13623 mode = HImode;
13624 gen_func.mov = gen_movhi;
13625 }
13626 else if (TARGET_STRING && bytes > 1)
13627 { /* move up to 4 bytes at a time */
13628 move_bytes = (bytes > 4) ? 4 : bytes;
13629 gen_func.movmemsi = gen_movmemsi_1reg;
13630 }
13631 else /* move 1 byte at a time */
13632 {
13633 move_bytes = 1;
13634 mode = QImode;
13635 gen_func.mov = gen_movqi;
13636 }
13637
13638 src = adjust_address (orig_src, mode, offset);
13639 dest = adjust_address (orig_dest, mode, offset);
13640
13641 if (mode != BLKmode)
13642 {
13643 rtx tmp_reg = gen_reg_rtx (mode);
13644
13645 emit_insn ((*gen_func.mov) (tmp_reg, src));
13646 stores[num_reg++] = (*gen_func.mov) (dest, tmp_reg);
13647 }
13648
13649 if (mode == BLKmode || num_reg >= MAX_MOVE_REG || bytes == move_bytes)
13650 {
13651 int i;
13652 for (i = 0; i < num_reg; i++)
13653 emit_insn (stores[i]);
13654 num_reg = 0;
13655 }
13656
13657 if (mode == BLKmode)
13658 {
13659 /* Move the address into scratch registers. The movmemsi
13660 patterns require zero offset. */
13661 if (!REG_P (XEXP (src, 0)))
13662 {
13663 rtx src_reg = copy_addr_to_reg (XEXP (src, 0));
13664 src = replace_equiv_address (src, src_reg);
13665 }
13666 set_mem_size (src, GEN_INT (move_bytes));
13667
13668 if (!REG_P (XEXP (dest, 0)))
13669 {
13670 rtx dest_reg = copy_addr_to_reg (XEXP (dest, 0));
13671 dest = replace_equiv_address (dest, dest_reg);
13672 }
13673 set_mem_size (dest, GEN_INT (move_bytes));
13674
13675 emit_insn ((*gen_func.movmemsi) (dest, src,
13676 GEN_INT (move_bytes & 31),
13677 align_rtx));
13678 }
13679 }
13680
13681 return 1;
13682 }
13683
13684 \f
13685 /* Return a string to perform a load_multiple operation.
13686 operands[0] is the vector.
13687 operands[1] is the source address.
13688 operands[2] is the first destination register. */
13689
13690 const char *
13691 rs6000_output_load_multiple (rtx operands[3])
13692 {
13693 /* We have to handle the case where the pseudo used to contain the address
13694 is assigned to one of the output registers. */
13695 int i, j;
13696 int words = XVECLEN (operands[0], 0);
13697 rtx xop[10];
13698
13699 if (XVECLEN (operands[0], 0) == 1)
13700 return "{l|lwz} %2,0(%1)";
13701
13702 for (i = 0; i < words; i++)
13703 if (refers_to_regno_p (REGNO (operands[2]) + i,
13704 REGNO (operands[2]) + i + 1, operands[1], 0))
13705 {
13706 if (i == words-1)
13707 {
13708 xop[0] = GEN_INT (4 * (words-1));
13709 xop[1] = operands[1];
13710 xop[2] = operands[2];
13711 output_asm_insn ("{lsi|lswi} %2,%1,%0\n\t{l|lwz} %1,%0(%1)", xop);
13712 return "";
13713 }
13714 else if (i == 0)
13715 {
13716 xop[0] = GEN_INT (4 * (words-1));
13717 xop[1] = operands[1];
13718 xop[2] = gen_rtx_REG (SImode, REGNO (operands[2]) + 1);
13719 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);
13720 return "";
13721 }
13722 else
13723 {
13724 for (j = 0; j < words; j++)
13725 if (j != i)
13726 {
13727 xop[0] = GEN_INT (j * 4);
13728 xop[1] = operands[1];
13729 xop[2] = gen_rtx_REG (SImode, REGNO (operands[2]) + j);
13730 output_asm_insn ("{l|lwz} %2,%0(%1)", xop);
13731 }
13732 xop[0] = GEN_INT (i * 4);
13733 xop[1] = operands[1];
13734 output_asm_insn ("{l|lwz} %1,%0(%1)", xop);
13735 return "";
13736 }
13737 }
13738
13739 return "{lsi|lswi} %2,%1,%N0";
13740 }
13741
13742 \f
13743 /* A validation routine: say whether CODE, a condition code, and MODE
13744 match. The other alternatives either don't make sense or should
13745 never be generated. */
13746
13747 void
13748 validate_condition_mode (enum rtx_code code, enum machine_mode mode)
13749 {
13750 gcc_assert ((GET_RTX_CLASS (code) == RTX_COMPARE
13751 || GET_RTX_CLASS (code) == RTX_COMM_COMPARE)
13752 && GET_MODE_CLASS (mode) == MODE_CC);
13753
13754 /* These don't make sense. */
13755 gcc_assert ((code != GT && code != LT && code != GE && code != LE)
13756 || mode != CCUNSmode);
13757
13758 gcc_assert ((code != GTU && code != LTU && code != GEU && code != LEU)
13759 || mode == CCUNSmode);
13760
13761 gcc_assert (mode == CCFPmode
13762 || (code != ORDERED && code != UNORDERED
13763 && code != UNEQ && code != LTGT
13764 && code != UNGT && code != UNLT
13765 && code != UNGE && code != UNLE));
13766
13767 /* These should never be generated except for
13768 flag_finite_math_only. */
13769 gcc_assert (mode != CCFPmode
13770 || flag_finite_math_only
13771 || (code != LE && code != GE
13772 && code != UNEQ && code != LTGT
13773 && code != UNGT && code != UNLT));
13774
13775 /* These are invalid; the information is not there. */
13776 gcc_assert (mode != CCEQmode || code == EQ || code == NE);
13777 }
13778
13779 \f
13780 /* Return 1 if ANDOP is a mask that has no bits on that are not in the
13781 mask required to convert the result of a rotate insn into a shift
13782 left insn of SHIFTOP bits. Both are known to be SImode CONST_INT. */
13783
13784 int
13785 includes_lshift_p (rtx shiftop, rtx andop)
13786 {
13787 unsigned HOST_WIDE_INT shift_mask = ~(unsigned HOST_WIDE_INT) 0;
13788
13789 shift_mask <<= INTVAL (shiftop);
13790
13791 return (INTVAL (andop) & 0xffffffff & ~shift_mask) == 0;
13792 }
13793
13794 /* Similar, but for right shift. */
13795
13796 int
13797 includes_rshift_p (rtx shiftop, rtx andop)
13798 {
13799 unsigned HOST_WIDE_INT shift_mask = ~(unsigned HOST_WIDE_INT) 0;
13800
13801 shift_mask >>= INTVAL (shiftop);
13802
13803 return (INTVAL (andop) & 0xffffffff & ~shift_mask) == 0;
13804 }
13805
13806 /* Return 1 if ANDOP is a mask suitable for use with an rldic insn
13807 to perform a left shift. It must have exactly SHIFTOP least
13808 significant 0's, then one or more 1's, then zero or more 0's. */
13809
13810 int
13811 includes_rldic_lshift_p (rtx shiftop, rtx andop)
13812 {
13813 if (GET_CODE (andop) == CONST_INT)
13814 {
13815 HOST_WIDE_INT c, lsb, shift_mask;
13816
13817 c = INTVAL (andop);
13818 if (c == 0 || c == ~0)
13819 return 0;
13820
13821 shift_mask = ~0;
13822 shift_mask <<= INTVAL (shiftop);
13823
13824 /* Find the least significant one bit. */
13825 lsb = c & -c;
13826
13827 /* It must coincide with the LSB of the shift mask. */
13828 if (-lsb != shift_mask)
13829 return 0;
13830
13831 /* Invert to look for the next transition (if any). */
13832 c = ~c;
13833
13834 /* Remove the low group of ones (originally low group of zeros). */
13835 c &= -lsb;
13836
13837 /* Again find the lsb, and check we have all 1's above. */
13838 lsb = c & -c;
13839 return c == -lsb;
13840 }
13841 else if (GET_CODE (andop) == CONST_DOUBLE
13842 && (GET_MODE (andop) == VOIDmode || GET_MODE (andop) == DImode))
13843 {
13844 HOST_WIDE_INT low, high, lsb;
13845 HOST_WIDE_INT shift_mask_low, shift_mask_high;
13846
13847 low = CONST_DOUBLE_LOW (andop);
13848 if (HOST_BITS_PER_WIDE_INT < 64)
13849 high = CONST_DOUBLE_HIGH (andop);
13850
13851 if ((low == 0 && (HOST_BITS_PER_WIDE_INT >= 64 || high == 0))
13852 || (low == ~0 && (HOST_BITS_PER_WIDE_INT >= 64 || high == ~0)))
13853 return 0;
13854
13855 if (HOST_BITS_PER_WIDE_INT < 64 && low == 0)
13856 {
13857 shift_mask_high = ~0;
13858 if (INTVAL (shiftop) > 32)
13859 shift_mask_high <<= INTVAL (shiftop) - 32;
13860
13861 lsb = high & -high;
13862
13863 if (-lsb != shift_mask_high || INTVAL (shiftop) < 32)
13864 return 0;
13865
13866 high = ~high;
13867 high &= -lsb;
13868
13869 lsb = high & -high;
13870 return high == -lsb;
13871 }
13872
13873 shift_mask_low = ~0;
13874 shift_mask_low <<= INTVAL (shiftop);
13875
13876 lsb = low & -low;
13877
13878 if (-lsb != shift_mask_low)
13879 return 0;
13880
13881 if (HOST_BITS_PER_WIDE_INT < 64)
13882 high = ~high;
13883 low = ~low;
13884 low &= -lsb;
13885
13886 if (HOST_BITS_PER_WIDE_INT < 64 && low == 0)
13887 {
13888 lsb = high & -high;
13889 return high == -lsb;
13890 }
13891
13892 lsb = low & -low;
13893 return low == -lsb && (HOST_BITS_PER_WIDE_INT >= 64 || high == ~0);
13894 }
13895 else
13896 return 0;
13897 }
13898
13899 /* Return 1 if ANDOP is a mask suitable for use with an rldicr insn
13900 to perform a left shift. It must have SHIFTOP or more least
13901 significant 0's, with the remainder of the word 1's. */
13902
13903 int
13904 includes_rldicr_lshift_p (rtx shiftop, rtx andop)
13905 {
13906 if (GET_CODE (andop) == CONST_INT)
13907 {
13908 HOST_WIDE_INT c, lsb, shift_mask;
13909
13910 shift_mask = ~0;
13911 shift_mask <<= INTVAL (shiftop);
13912 c = INTVAL (andop);
13913
13914 /* Find the least significant one bit. */
13915 lsb = c & -c;
13916
13917 /* It must be covered by the shift mask.
13918 This test also rejects c == 0. */
13919 if ((lsb & shift_mask) == 0)
13920 return 0;
13921
13922 /* Check we have all 1's above the transition, and reject all 1's. */
13923 return c == -lsb && lsb != 1;
13924 }
13925 else if (GET_CODE (andop) == CONST_DOUBLE
13926 && (GET_MODE (andop) == VOIDmode || GET_MODE (andop) == DImode))
13927 {
13928 HOST_WIDE_INT low, lsb, shift_mask_low;
13929
13930 low = CONST_DOUBLE_LOW (andop);
13931
13932 if (HOST_BITS_PER_WIDE_INT < 64)
13933 {
13934 HOST_WIDE_INT high, shift_mask_high;
13935
13936 high = CONST_DOUBLE_HIGH (andop);
13937
13938 if (low == 0)
13939 {
13940 shift_mask_high = ~0;
13941 if (INTVAL (shiftop) > 32)
13942 shift_mask_high <<= INTVAL (shiftop) - 32;
13943
13944 lsb = high & -high;
13945
13946 if ((lsb & shift_mask_high) == 0)
13947 return 0;
13948
13949 return high == -lsb;
13950 }
13951 if (high != ~0)
13952 return 0;
13953 }
13954
13955 shift_mask_low = ~0;
13956 shift_mask_low <<= INTVAL (shiftop);
13957
13958 lsb = low & -low;
13959
13960 if ((lsb & shift_mask_low) == 0)
13961 return 0;
13962
13963 return low == -lsb && lsb != 1;
13964 }
13965 else
13966 return 0;
13967 }
13968
13969 /* Return 1 if operands will generate a valid arguments to rlwimi
13970 instruction for insert with right shift in 64-bit mode. The mask may
13971 not start on the first bit or stop on the last bit because wrap-around
13972 effects of instruction do not correspond to semantics of RTL insn. */
13973
13974 int
13975 insvdi_rshift_rlwimi_p (rtx sizeop, rtx startop, rtx shiftop)
13976 {
13977 if (INTVAL (startop) > 32
13978 && INTVAL (startop) < 64
13979 && INTVAL (sizeop) > 1
13980 && INTVAL (sizeop) + INTVAL (startop) < 64
13981 && INTVAL (shiftop) > 0
13982 && INTVAL (sizeop) + INTVAL (shiftop) < 32
13983 && (64 - (INTVAL (shiftop) & 63)) >= INTVAL (sizeop))
13984 return 1;
13985
13986 return 0;
13987 }
13988
13989 /* Return 1 if REGNO (reg1) == REGNO (reg2) - 1 making them candidates
13990 for lfq and stfq insns iff the registers are hard registers. */
13991
13992 int
13993 registers_ok_for_quad_peep (rtx reg1, rtx reg2)
13994 {
13995 /* We might have been passed a SUBREG. */
13996 if (GET_CODE (reg1) != REG || GET_CODE (reg2) != REG)
13997 return 0;
13998
13999 /* We might have been passed non floating point registers. */
14000 if (!FP_REGNO_P (REGNO (reg1))
14001 || !FP_REGNO_P (REGNO (reg2)))
14002 return 0;
14003
14004 return (REGNO (reg1) == REGNO (reg2) - 1);
14005 }
14006
14007 /* Return 1 if addr1 and addr2 are suitable for lfq or stfq insn.
14008 addr1 and addr2 must be in consecutive memory locations
14009 (addr2 == addr1 + 8). */
14010
14011 int
14012 mems_ok_for_quad_peep (rtx mem1, rtx mem2)
14013 {
14014 rtx addr1, addr2;
14015 unsigned int reg1, reg2;
14016 int offset1, offset2;
14017
14018 /* The mems cannot be volatile. */
14019 if (MEM_VOLATILE_P (mem1) || MEM_VOLATILE_P (mem2))
14020 return 0;
14021
14022 addr1 = XEXP (mem1, 0);
14023 addr2 = XEXP (mem2, 0);
14024
14025 /* Extract an offset (if used) from the first addr. */
14026 if (GET_CODE (addr1) == PLUS)
14027 {
14028 /* If not a REG, return zero. */
14029 if (GET_CODE (XEXP (addr1, 0)) != REG)
14030 return 0;
14031 else
14032 {
14033 reg1 = REGNO (XEXP (addr1, 0));
14034 /* The offset must be constant! */
14035 if (GET_CODE (XEXP (addr1, 1)) != CONST_INT)
14036 return 0;
14037 offset1 = INTVAL (XEXP (addr1, 1));
14038 }
14039 }
14040 else if (GET_CODE (addr1) != REG)
14041 return 0;
14042 else
14043 {
14044 reg1 = REGNO (addr1);
14045 /* This was a simple (mem (reg)) expression. Offset is 0. */
14046 offset1 = 0;
14047 }
14048
14049 /* And now for the second addr. */
14050 if (GET_CODE (addr2) == PLUS)
14051 {
14052 /* If not a REG, return zero. */
14053 if (GET_CODE (XEXP (addr2, 0)) != REG)
14054 return 0;
14055 else
14056 {
14057 reg2 = REGNO (XEXP (addr2, 0));
14058 /* The offset must be constant. */
14059 if (GET_CODE (XEXP (addr2, 1)) != CONST_INT)
14060 return 0;
14061 offset2 = INTVAL (XEXP (addr2, 1));
14062 }
14063 }
14064 else if (GET_CODE (addr2) != REG)
14065 return 0;
14066 else
14067 {
14068 reg2 = REGNO (addr2);
14069 /* This was a simple (mem (reg)) expression. Offset is 0. */
14070 offset2 = 0;
14071 }
14072
14073 /* Both of these must have the same base register. */
14074 if (reg1 != reg2)
14075 return 0;
14076
14077 /* The offset for the second addr must be 8 more than the first addr. */
14078 if (offset2 != offset1 + 8)
14079 return 0;
14080
14081 /* All the tests passed. addr1 and addr2 are valid for lfq or stfq
14082 instructions. */
14083 return 1;
14084 }
14085 \f
14086
14087 rtx
14088 rs6000_secondary_memory_needed_rtx (enum machine_mode mode)
14089 {
14090 static bool eliminated = false;
14091 rtx ret;
14092
14093 if (mode != SDmode)
14094 ret = assign_stack_local (mode, GET_MODE_SIZE (mode), 0);
14095 else
14096 {
14097 rtx mem = cfun->machine->sdmode_stack_slot;
14098 gcc_assert (mem != NULL_RTX);
14099
14100 if (!eliminated)
14101 {
14102 mem = eliminate_regs (mem, VOIDmode, NULL_RTX);
14103 cfun->machine->sdmode_stack_slot = mem;
14104 eliminated = true;
14105 }
14106 ret = mem;
14107 }
14108
14109 if (TARGET_DEBUG_ADDR)
14110 {
14111 fprintf (stderr, "\nrs6000_secondary_memory_needed_rtx, mode %s, rtx:\n",
14112 GET_MODE_NAME (mode));
14113 if (!ret)
14114 fprintf (stderr, "\tNULL_RTX\n");
14115 else
14116 debug_rtx (ret);
14117 }
14118
14119 return ret;
14120 }
14121
14122 static tree
14123 rs6000_check_sdmode (tree *tp, int *walk_subtrees, void *data ATTRIBUTE_UNUSED)
14124 {
14125 /* Don't walk into types. */
14126 if (*tp == NULL_TREE || *tp == error_mark_node || TYPE_P (*tp))
14127 {
14128 *walk_subtrees = 0;
14129 return NULL_TREE;
14130 }
14131
14132 switch (TREE_CODE (*tp))
14133 {
14134 case VAR_DECL:
14135 case PARM_DECL:
14136 case FIELD_DECL:
14137 case RESULT_DECL:
14138 case SSA_NAME:
14139 case REAL_CST:
14140 case MEM_REF:
14141 case MISALIGNED_INDIRECT_REF:
14142 case VIEW_CONVERT_EXPR:
14143 if (TYPE_MODE (TREE_TYPE (*tp)) == SDmode)
14144 return *tp;
14145 break;
14146 default:
14147 break;
14148 }
14149
14150 return NULL_TREE;
14151 }
14152
14153 enum reload_reg_type {
14154 GPR_REGISTER_TYPE,
14155 VECTOR_REGISTER_TYPE,
14156 OTHER_REGISTER_TYPE
14157 };
14158
14159 static enum reload_reg_type
14160 rs6000_reload_register_type (enum reg_class rclass)
14161 {
14162 switch (rclass)
14163 {
14164 case GENERAL_REGS:
14165 case BASE_REGS:
14166 return GPR_REGISTER_TYPE;
14167
14168 case FLOAT_REGS:
14169 case ALTIVEC_REGS:
14170 case VSX_REGS:
14171 return VECTOR_REGISTER_TYPE;
14172
14173 default:
14174 return OTHER_REGISTER_TYPE;
14175 }
14176 }
14177
14178 /* Inform reload about cases where moving X with a mode MODE to a register in
14179 RCLASS requires an extra scratch or immediate register. Return the class
14180 needed for the immediate register.
14181
14182 For VSX and Altivec, we may need a register to convert sp+offset into
14183 reg+sp. */
14184
14185 static reg_class_t
14186 rs6000_secondary_reload (bool in_p,
14187 rtx x,
14188 reg_class_t rclass_i,
14189 enum machine_mode mode,
14190 secondary_reload_info *sri)
14191 {
14192 enum reg_class rclass = (enum reg_class) rclass_i;
14193 reg_class_t ret = ALL_REGS;
14194 enum insn_code icode;
14195 bool default_p = false;
14196
14197 sri->icode = CODE_FOR_nothing;
14198
14199 /* Convert vector loads and stores into gprs to use an additional base
14200 register. */
14201 icode = rs6000_vector_reload[mode][in_p != false];
14202 if (icode != CODE_FOR_nothing)
14203 {
14204 ret = NO_REGS;
14205 sri->icode = CODE_FOR_nothing;
14206 sri->extra_cost = 0;
14207
14208 if (GET_CODE (x) == MEM)
14209 {
14210 rtx addr = XEXP (x, 0);
14211
14212 /* Loads to and stores from gprs can do reg+offset, and wouldn't need
14213 an extra register in that case, but it would need an extra
14214 register if the addressing is reg+reg or (reg+reg)&(-16). */
14215 if (rclass == GENERAL_REGS || rclass == BASE_REGS)
14216 {
14217 if (!legitimate_indirect_address_p (addr, false)
14218 && !rs6000_legitimate_offset_address_p (TImode, addr, false))
14219 {
14220 sri->icode = icode;
14221 /* account for splitting the loads, and converting the
14222 address from reg+reg to reg. */
14223 sri->extra_cost = (((TARGET_64BIT) ? 3 : 5)
14224 + ((GET_CODE (addr) == AND) ? 1 : 0));
14225 }
14226 }
14227 /* Loads to and stores from vector registers can only do reg+reg
14228 addressing. Altivec registers can also do (reg+reg)&(-16). */
14229 else if (rclass == VSX_REGS || rclass == ALTIVEC_REGS
14230 || rclass == FLOAT_REGS || rclass == NO_REGS)
14231 {
14232 if (!VECTOR_MEM_ALTIVEC_P (mode)
14233 && GET_CODE (addr) == AND
14234 && GET_CODE (XEXP (addr, 1)) == CONST_INT
14235 && INTVAL (XEXP (addr, 1)) == -16
14236 && (legitimate_indirect_address_p (XEXP (addr, 0), false)
14237 || legitimate_indexed_address_p (XEXP (addr, 0), false)))
14238 {
14239 sri->icode = icode;
14240 sri->extra_cost = ((GET_CODE (XEXP (addr, 0)) == PLUS)
14241 ? 2 : 1);
14242 }
14243 else if (!legitimate_indirect_address_p (addr, false)
14244 && (rclass == NO_REGS
14245 || !legitimate_indexed_address_p (addr, false)))
14246 {
14247 sri->icode = icode;
14248 sri->extra_cost = 1;
14249 }
14250 else
14251 icode = CODE_FOR_nothing;
14252 }
14253 /* Any other loads, including to pseudo registers which haven't been
14254 assigned to a register yet, default to require a scratch
14255 register. */
14256 else
14257 {
14258 sri->icode = icode;
14259 sri->extra_cost = 2;
14260 }
14261 }
14262 else if (REG_P (x))
14263 {
14264 int regno = true_regnum (x);
14265
14266 icode = CODE_FOR_nothing;
14267 if (regno < 0 || regno >= FIRST_PSEUDO_REGISTER)
14268 default_p = true;
14269 else
14270 {
14271 enum reg_class xclass = REGNO_REG_CLASS (regno);
14272 enum reload_reg_type rtype1 = rs6000_reload_register_type (rclass);
14273 enum reload_reg_type rtype2 = rs6000_reload_register_type (xclass);
14274
14275 /* If memory is needed, use default_secondary_reload to create the
14276 stack slot. */
14277 if (rtype1 != rtype2 || rtype1 == OTHER_REGISTER_TYPE)
14278 default_p = true;
14279 else
14280 ret = NO_REGS;
14281 }
14282 }
14283 else
14284 default_p = true;
14285 }
14286 else
14287 default_p = true;
14288
14289 if (default_p)
14290 ret = default_secondary_reload (in_p, x, rclass, mode, sri);
14291
14292 gcc_assert (ret != ALL_REGS);
14293
14294 if (TARGET_DEBUG_ADDR)
14295 {
14296 fprintf (stderr,
14297 "\nrs6000_secondary_reload, return %s, in_p = %s, rclass = %s, "
14298 "mode = %s",
14299 reg_class_names[ret],
14300 in_p ? "true" : "false",
14301 reg_class_names[rclass],
14302 GET_MODE_NAME (mode));
14303
14304 if (default_p)
14305 fprintf (stderr, ", default secondary reload");
14306
14307 if (sri->icode != CODE_FOR_nothing)
14308 fprintf (stderr, ", reload func = %s, extra cost = %d\n",
14309 insn_data[sri->icode].name, sri->extra_cost);
14310 else
14311 fprintf (stderr, "\n");
14312
14313 debug_rtx (x);
14314 }
14315
14316 return ret;
14317 }
14318
14319 /* Fixup reload addresses for Altivec or VSX loads/stores to change SP+offset
14320 to SP+reg addressing. */
14321
14322 void
14323 rs6000_secondary_reload_inner (rtx reg, rtx mem, rtx scratch, bool store_p)
14324 {
14325 int regno = true_regnum (reg);
14326 enum machine_mode mode = GET_MODE (reg);
14327 enum reg_class rclass;
14328 rtx addr;
14329 rtx and_op2 = NULL_RTX;
14330 rtx addr_op1;
14331 rtx addr_op2;
14332 rtx scratch_or_premodify = scratch;
14333 rtx and_rtx;
14334 rtx cc_clobber;
14335
14336 if (TARGET_DEBUG_ADDR)
14337 {
14338 fprintf (stderr, "\nrs6000_secondary_reload_inner, type = %s\n",
14339 store_p ? "store" : "load");
14340 fprintf (stderr, "reg:\n");
14341 debug_rtx (reg);
14342 fprintf (stderr, "mem:\n");
14343 debug_rtx (mem);
14344 fprintf (stderr, "scratch:\n");
14345 debug_rtx (scratch);
14346 }
14347
14348 gcc_assert (regno >= 0 && regno < FIRST_PSEUDO_REGISTER);
14349 gcc_assert (GET_CODE (mem) == MEM);
14350 rclass = REGNO_REG_CLASS (regno);
14351 addr = XEXP (mem, 0);
14352
14353 switch (rclass)
14354 {
14355 /* GPRs can handle reg + small constant, all other addresses need to use
14356 the scratch register. */
14357 case GENERAL_REGS:
14358 case BASE_REGS:
14359 if (GET_CODE (addr) == AND)
14360 {
14361 and_op2 = XEXP (addr, 1);
14362 addr = XEXP (addr, 0);
14363 }
14364
14365 if (GET_CODE (addr) == PRE_MODIFY)
14366 {
14367 scratch_or_premodify = XEXP (addr, 0);
14368 gcc_assert (REG_P (scratch_or_premodify));
14369 gcc_assert (GET_CODE (XEXP (addr, 1)) == PLUS);
14370 addr = XEXP (addr, 1);
14371 }
14372
14373 if (GET_CODE (addr) == PLUS
14374 && (!rs6000_legitimate_offset_address_p (TImode, addr, false)
14375 || and_op2 != NULL_RTX))
14376 {
14377 addr_op1 = XEXP (addr, 0);
14378 addr_op2 = XEXP (addr, 1);
14379 gcc_assert (legitimate_indirect_address_p (addr_op1, false));
14380
14381 if (!REG_P (addr_op2)
14382 && (GET_CODE (addr_op2) != CONST_INT
14383 || !satisfies_constraint_I (addr_op2)))
14384 {
14385 if (TARGET_DEBUG_ADDR)
14386 {
14387 fprintf (stderr,
14388 "\nMove plus addr to register %s, mode = %s: ",
14389 rs6000_reg_names[REGNO (scratch)],
14390 GET_MODE_NAME (mode));
14391 debug_rtx (addr_op2);
14392 }
14393 rs6000_emit_move (scratch, addr_op2, Pmode);
14394 addr_op2 = scratch;
14395 }
14396
14397 emit_insn (gen_rtx_SET (VOIDmode,
14398 scratch_or_premodify,
14399 gen_rtx_PLUS (Pmode,
14400 addr_op1,
14401 addr_op2)));
14402
14403 addr = scratch_or_premodify;
14404 scratch_or_premodify = scratch;
14405 }
14406 else if (!legitimate_indirect_address_p (addr, false)
14407 && !rs6000_legitimate_offset_address_p (TImode, addr, false))
14408 {
14409 if (TARGET_DEBUG_ADDR)
14410 {
14411 fprintf (stderr, "\nMove addr to register %s, mode = %s: ",
14412 rs6000_reg_names[REGNO (scratch_or_premodify)],
14413 GET_MODE_NAME (mode));
14414 debug_rtx (addr);
14415 }
14416 rs6000_emit_move (scratch_or_premodify, addr, Pmode);
14417 addr = scratch_or_premodify;
14418 scratch_or_premodify = scratch;
14419 }
14420 break;
14421
14422 /* Float/Altivec registers can only handle reg+reg addressing. Move
14423 other addresses into a scratch register. */
14424 case FLOAT_REGS:
14425 case VSX_REGS:
14426 case ALTIVEC_REGS:
14427
14428 /* With float regs, we need to handle the AND ourselves, since we can't
14429 use the Altivec instruction with an implicit AND -16. Allow scalar
14430 loads to float registers to use reg+offset even if VSX. */
14431 if (GET_CODE (addr) == AND
14432 && (rclass != ALTIVEC_REGS || GET_MODE_SIZE (mode) != 16
14433 || GET_CODE (XEXP (addr, 1)) != CONST_INT
14434 || INTVAL (XEXP (addr, 1)) != -16
14435 || !VECTOR_MEM_ALTIVEC_P (mode)))
14436 {
14437 and_op2 = XEXP (addr, 1);
14438 addr = XEXP (addr, 0);
14439 }
14440
14441 /* If we aren't using a VSX load, save the PRE_MODIFY register and use it
14442 as the address later. */
14443 if (GET_CODE (addr) == PRE_MODIFY
14444 && (!VECTOR_MEM_VSX_P (mode)
14445 || and_op2 != NULL_RTX
14446 || !legitimate_indexed_address_p (XEXP (addr, 1), false)))
14447 {
14448 scratch_or_premodify = XEXP (addr, 0);
14449 gcc_assert (legitimate_indirect_address_p (scratch_or_premodify,
14450 false));
14451 gcc_assert (GET_CODE (XEXP (addr, 1)) == PLUS);
14452 addr = XEXP (addr, 1);
14453 }
14454
14455 if (legitimate_indirect_address_p (addr, false) /* reg */
14456 || legitimate_indexed_address_p (addr, false) /* reg+reg */
14457 || GET_CODE (addr) == PRE_MODIFY /* VSX pre-modify */
14458 || (GET_CODE (addr) == AND /* Altivec memory */
14459 && GET_CODE (XEXP (addr, 1)) == CONST_INT
14460 && INTVAL (XEXP (addr, 1)) == -16
14461 && VECTOR_MEM_ALTIVEC_P (mode))
14462 || (rclass == FLOAT_REGS /* legacy float mem */
14463 && GET_MODE_SIZE (mode) == 8
14464 && and_op2 == NULL_RTX
14465 && scratch_or_premodify == scratch
14466 && rs6000_legitimate_offset_address_p (mode, addr, false)))
14467 ;
14468
14469 else if (GET_CODE (addr) == PLUS)
14470 {
14471 addr_op1 = XEXP (addr, 0);
14472 addr_op2 = XEXP (addr, 1);
14473 gcc_assert (REG_P (addr_op1));
14474
14475 if (TARGET_DEBUG_ADDR)
14476 {
14477 fprintf (stderr, "\nMove plus addr to register %s, mode = %s: ",
14478 rs6000_reg_names[REGNO (scratch)], GET_MODE_NAME (mode));
14479 debug_rtx (addr_op2);
14480 }
14481 rs6000_emit_move (scratch, addr_op2, Pmode);
14482 emit_insn (gen_rtx_SET (VOIDmode,
14483 scratch_or_premodify,
14484 gen_rtx_PLUS (Pmode,
14485 addr_op1,
14486 scratch)));
14487 addr = scratch_or_premodify;
14488 scratch_or_premodify = scratch;
14489 }
14490
14491 else if (GET_CODE (addr) == SYMBOL_REF || GET_CODE (addr) == CONST
14492 || GET_CODE (addr) == CONST_INT || REG_P (addr))
14493 {
14494 if (TARGET_DEBUG_ADDR)
14495 {
14496 fprintf (stderr, "\nMove addr to register %s, mode = %s: ",
14497 rs6000_reg_names[REGNO (scratch_or_premodify)],
14498 GET_MODE_NAME (mode));
14499 debug_rtx (addr);
14500 }
14501
14502 rs6000_emit_move (scratch_or_premodify, addr, Pmode);
14503 addr = scratch_or_premodify;
14504 scratch_or_premodify = scratch;
14505 }
14506
14507 else
14508 gcc_unreachable ();
14509
14510 break;
14511
14512 default:
14513 gcc_unreachable ();
14514 }
14515
14516 /* If the original address involved a pre-modify that we couldn't use the VSX
14517 memory instruction with update, and we haven't taken care of already,
14518 store the address in the pre-modify register and use that as the
14519 address. */
14520 if (scratch_or_premodify != scratch && scratch_or_premodify != addr)
14521 {
14522 emit_insn (gen_rtx_SET (VOIDmode, scratch_or_premodify, addr));
14523 addr = scratch_or_premodify;
14524 }
14525
14526 /* If the original address involved an AND -16 and we couldn't use an ALTIVEC
14527 memory instruction, recreate the AND now, including the clobber which is
14528 generated by the general ANDSI3/ANDDI3 patterns for the
14529 andi. instruction. */
14530 if (and_op2 != NULL_RTX)
14531 {
14532 if (! legitimate_indirect_address_p (addr, false))
14533 {
14534 emit_insn (gen_rtx_SET (VOIDmode, scratch, addr));
14535 addr = scratch;
14536 }
14537
14538 if (TARGET_DEBUG_ADDR)
14539 {
14540 fprintf (stderr, "\nAnd addr to register %s, mode = %s: ",
14541 rs6000_reg_names[REGNO (scratch)], GET_MODE_NAME (mode));
14542 debug_rtx (and_op2);
14543 }
14544
14545 and_rtx = gen_rtx_SET (VOIDmode,
14546 scratch,
14547 gen_rtx_AND (Pmode,
14548 addr,
14549 and_op2));
14550
14551 cc_clobber = gen_rtx_CLOBBER (CCmode, gen_rtx_SCRATCH (CCmode));
14552 emit_insn (gen_rtx_PARALLEL (VOIDmode,
14553 gen_rtvec (2, and_rtx, cc_clobber)));
14554 addr = scratch;
14555 }
14556
14557 /* Adjust the address if it changed. */
14558 if (addr != XEXP (mem, 0))
14559 {
14560 mem = change_address (mem, mode, addr);
14561 if (TARGET_DEBUG_ADDR)
14562 fprintf (stderr, "\nrs6000_secondary_reload_inner, mem adjusted.\n");
14563 }
14564
14565 /* Now create the move. */
14566 if (store_p)
14567 emit_insn (gen_rtx_SET (VOIDmode, mem, reg));
14568 else
14569 emit_insn (gen_rtx_SET (VOIDmode, reg, mem));
14570
14571 return;
14572 }
14573
14574 /* Target hook to return the cover classes for Integrated Register Allocator.
14575 Cover classes is a set of non-intersected register classes covering all hard
14576 registers used for register allocation purpose. Any move between two
14577 registers of a cover class should be cheaper than load or store of the
14578 registers. The value is array of register classes with LIM_REG_CLASSES used
14579 as the end marker.
14580
14581 We need two IRA_COVER_CLASSES, one for pre-VSX, and the other for VSX to
14582 account for the Altivec and Floating registers being subsets of the VSX
14583 register set under VSX, but distinct register sets on pre-VSX machines. */
14584
14585 static const reg_class_t *
14586 rs6000_ira_cover_classes (void)
14587 {
14588 static const reg_class_t cover_pre_vsx[] = IRA_COVER_CLASSES_PRE_VSX;
14589 static const reg_class_t cover_vsx[] = IRA_COVER_CLASSES_VSX;
14590
14591 return (TARGET_VSX) ? cover_vsx : cover_pre_vsx;
14592 }
14593
14594 /* Allocate a 64-bit stack slot to be used for copying SDmode
14595 values through if this function has any SDmode references. */
14596
14597 static void
14598 rs6000_alloc_sdmode_stack_slot (void)
14599 {
14600 tree t;
14601 basic_block bb;
14602 gimple_stmt_iterator gsi;
14603
14604 gcc_assert (cfun->machine->sdmode_stack_slot == NULL_RTX);
14605
14606 FOR_EACH_BB (bb)
14607 for (gsi = gsi_start_bb (bb); !gsi_end_p (gsi); gsi_next (&gsi))
14608 {
14609 tree ret = walk_gimple_op (gsi_stmt (gsi), rs6000_check_sdmode, NULL);
14610 if (ret)
14611 {
14612 rtx stack = assign_stack_local (DDmode, GET_MODE_SIZE (DDmode), 0);
14613 cfun->machine->sdmode_stack_slot = adjust_address_nv (stack,
14614 SDmode, 0);
14615 return;
14616 }
14617 }
14618
14619 /* Check for any SDmode parameters of the function. */
14620 for (t = DECL_ARGUMENTS (cfun->decl); t; t = DECL_CHAIN (t))
14621 {
14622 if (TREE_TYPE (t) == error_mark_node)
14623 continue;
14624
14625 if (TYPE_MODE (TREE_TYPE (t)) == SDmode
14626 || TYPE_MODE (DECL_ARG_TYPE (t)) == SDmode)
14627 {
14628 rtx stack = assign_stack_local (DDmode, GET_MODE_SIZE (DDmode), 0);
14629 cfun->machine->sdmode_stack_slot = adjust_address_nv (stack,
14630 SDmode, 0);
14631 return;
14632 }
14633 }
14634 }
14635
14636 static void
14637 rs6000_instantiate_decls (void)
14638 {
14639 if (cfun->machine->sdmode_stack_slot != NULL_RTX)
14640 instantiate_decl_rtl (cfun->machine->sdmode_stack_slot);
14641 }
14642
14643 /* Given an rtx X being reloaded into a reg required to be
14644 in class CLASS, return the class of reg to actually use.
14645 In general this is just CLASS; but on some machines
14646 in some cases it is preferable to use a more restrictive class.
14647
14648 On the RS/6000, we have to return NO_REGS when we want to reload a
14649 floating-point CONST_DOUBLE to force it to be copied to memory.
14650
14651 We also don't want to reload integer values into floating-point
14652 registers if we can at all help it. In fact, this can
14653 cause reload to die, if it tries to generate a reload of CTR
14654 into a FP register and discovers it doesn't have the memory location
14655 required.
14656
14657 ??? Would it be a good idea to have reload do the converse, that is
14658 try to reload floating modes into FP registers if possible?
14659 */
14660
14661 static enum reg_class
14662 rs6000_preferred_reload_class (rtx x, enum reg_class rclass)
14663 {
14664 enum machine_mode mode = GET_MODE (x);
14665
14666 if (VECTOR_UNIT_VSX_P (mode)
14667 && x == CONST0_RTX (mode) && VSX_REG_CLASS_P (rclass))
14668 return rclass;
14669
14670 if (VECTOR_UNIT_ALTIVEC_OR_VSX_P (mode)
14671 && (rclass == ALTIVEC_REGS || rclass == VSX_REGS)
14672 && easy_vector_constant (x, mode))
14673 return ALTIVEC_REGS;
14674
14675 if (CONSTANT_P (x) && reg_classes_intersect_p (rclass, FLOAT_REGS))
14676 return NO_REGS;
14677
14678 if (GET_MODE_CLASS (mode) == MODE_INT && rclass == NON_SPECIAL_REGS)
14679 return GENERAL_REGS;
14680
14681 /* For VSX, prefer the traditional registers for 64-bit values because we can
14682 use the non-VSX loads. Prefer the Altivec registers if Altivec is
14683 handling the vector operations (i.e. V16QI, V8HI, and V4SI), or if we
14684 prefer Altivec loads.. */
14685 if (rclass == VSX_REGS)
14686 {
14687 if (GET_MODE_SIZE (mode) <= 8)
14688 return FLOAT_REGS;
14689
14690 if (VECTOR_UNIT_ALTIVEC_P (mode) || VECTOR_MEM_ALTIVEC_P (mode))
14691 return ALTIVEC_REGS;
14692
14693 return rclass;
14694 }
14695
14696 return rclass;
14697 }
14698
14699 /* Debug version of rs6000_preferred_reload_class. */
14700 static enum reg_class
14701 rs6000_debug_preferred_reload_class (rtx x, enum reg_class rclass)
14702 {
14703 enum reg_class ret = rs6000_preferred_reload_class (x, rclass);
14704
14705 fprintf (stderr,
14706 "\nrs6000_preferred_reload_class, return %s, rclass = %s, "
14707 "mode = %s, x:\n",
14708 reg_class_names[ret], reg_class_names[rclass],
14709 GET_MODE_NAME (GET_MODE (x)));
14710 debug_rtx (x);
14711
14712 return ret;
14713 }
14714
14715 /* If we are copying between FP or AltiVec registers and anything else, we need
14716 a memory location. The exception is when we are targeting ppc64 and the
14717 move to/from fpr to gpr instructions are available. Also, under VSX, you
14718 can copy vector registers from the FP register set to the Altivec register
14719 set and vice versa. */
14720
14721 static bool
14722 rs6000_secondary_memory_needed (enum reg_class class1,
14723 enum reg_class class2,
14724 enum machine_mode mode)
14725 {
14726 if (class1 == class2)
14727 return false;
14728
14729 /* Under VSX, there are 3 register classes that values could be in (VSX_REGS,
14730 ALTIVEC_REGS, and FLOAT_REGS). We don't need to use memory to copy
14731 between these classes. But we need memory for other things that can go in
14732 FLOAT_REGS like SFmode. */
14733 if (TARGET_VSX
14734 && (VECTOR_MEM_VSX_P (mode) || VECTOR_UNIT_VSX_P (mode))
14735 && (class1 == VSX_REGS || class1 == ALTIVEC_REGS
14736 || class1 == FLOAT_REGS))
14737 return (class2 != VSX_REGS && class2 != ALTIVEC_REGS
14738 && class2 != FLOAT_REGS);
14739
14740 if (class1 == VSX_REGS || class2 == VSX_REGS)
14741 return true;
14742
14743 if (class1 == FLOAT_REGS
14744 && (!TARGET_MFPGPR || !TARGET_POWERPC64
14745 || ((mode != DFmode)
14746 && (mode != DDmode)
14747 && (mode != DImode))))
14748 return true;
14749
14750 if (class2 == FLOAT_REGS
14751 && (!TARGET_MFPGPR || !TARGET_POWERPC64
14752 || ((mode != DFmode)
14753 && (mode != DDmode)
14754 && (mode != DImode))))
14755 return true;
14756
14757 if (class1 == ALTIVEC_REGS || class2 == ALTIVEC_REGS)
14758 return true;
14759
14760 return false;
14761 }
14762
14763 /* Debug version of rs6000_secondary_memory_needed. */
14764 static bool
14765 rs6000_debug_secondary_memory_needed (enum reg_class class1,
14766 enum reg_class class2,
14767 enum machine_mode mode)
14768 {
14769 bool ret = rs6000_secondary_memory_needed (class1, class2, mode);
14770
14771 fprintf (stderr,
14772 "rs6000_secondary_memory_needed, return: %s, class1 = %s, "
14773 "class2 = %s, mode = %s\n",
14774 ret ? "true" : "false", reg_class_names[class1],
14775 reg_class_names[class2], GET_MODE_NAME (mode));
14776
14777 return ret;
14778 }
14779
14780 /* Return the register class of a scratch register needed to copy IN into
14781 or out of a register in RCLASS in MODE. If it can be done directly,
14782 NO_REGS is returned. */
14783
14784 static enum reg_class
14785 rs6000_secondary_reload_class (enum reg_class rclass, enum machine_mode mode,
14786 rtx in)
14787 {
14788 int regno;
14789
14790 if (TARGET_ELF || (DEFAULT_ABI == ABI_DARWIN
14791 #if TARGET_MACHO
14792 && MACHOPIC_INDIRECT
14793 #endif
14794 ))
14795 {
14796 /* We cannot copy a symbolic operand directly into anything
14797 other than BASE_REGS for TARGET_ELF. So indicate that a
14798 register from BASE_REGS is needed as an intermediate
14799 register.
14800
14801 On Darwin, pic addresses require a load from memory, which
14802 needs a base register. */
14803 if (rclass != BASE_REGS
14804 && (GET_CODE (in) == SYMBOL_REF
14805 || GET_CODE (in) == HIGH
14806 || GET_CODE (in) == LABEL_REF
14807 || GET_CODE (in) == CONST))
14808 return BASE_REGS;
14809 }
14810
14811 if (GET_CODE (in) == REG)
14812 {
14813 regno = REGNO (in);
14814 if (regno >= FIRST_PSEUDO_REGISTER)
14815 {
14816 regno = true_regnum (in);
14817 if (regno >= FIRST_PSEUDO_REGISTER)
14818 regno = -1;
14819 }
14820 }
14821 else if (GET_CODE (in) == SUBREG)
14822 {
14823 regno = true_regnum (in);
14824 if (regno >= FIRST_PSEUDO_REGISTER)
14825 regno = -1;
14826 }
14827 else
14828 regno = -1;
14829
14830 /* We can place anything into GENERAL_REGS and can put GENERAL_REGS
14831 into anything. */
14832 if (rclass == GENERAL_REGS || rclass == BASE_REGS
14833 || (regno >= 0 && INT_REGNO_P (regno)))
14834 return NO_REGS;
14835
14836 /* Constants, memory, and FP registers can go into FP registers. */
14837 if ((regno == -1 || FP_REGNO_P (regno))
14838 && (rclass == FLOAT_REGS || rclass == NON_SPECIAL_REGS))
14839 return (mode != SDmode) ? NO_REGS : GENERAL_REGS;
14840
14841 /* Memory, and FP/altivec registers can go into fp/altivec registers under
14842 VSX. */
14843 if (TARGET_VSX
14844 && (regno == -1 || VSX_REGNO_P (regno))
14845 && VSX_REG_CLASS_P (rclass))
14846 return NO_REGS;
14847
14848 /* Memory, and AltiVec registers can go into AltiVec registers. */
14849 if ((regno == -1 || ALTIVEC_REGNO_P (regno))
14850 && rclass == ALTIVEC_REGS)
14851 return NO_REGS;
14852
14853 /* We can copy among the CR registers. */
14854 if ((rclass == CR_REGS || rclass == CR0_REGS)
14855 && regno >= 0 && CR_REGNO_P (regno))
14856 return NO_REGS;
14857
14858 /* Otherwise, we need GENERAL_REGS. */
14859 return GENERAL_REGS;
14860 }
14861
14862 /* Debug version of rs6000_secondary_reload_class. */
14863 static enum reg_class
14864 rs6000_debug_secondary_reload_class (enum reg_class rclass,
14865 enum machine_mode mode, rtx in)
14866 {
14867 enum reg_class ret = rs6000_secondary_reload_class (rclass, mode, in);
14868 fprintf (stderr,
14869 "\nrs6000_secondary_reload_class, return %s, rclass = %s, "
14870 "mode = %s, input rtx:\n",
14871 reg_class_names[ret], reg_class_names[rclass],
14872 GET_MODE_NAME (mode));
14873 debug_rtx (in);
14874
14875 return ret;
14876 }
14877
14878 /* Return nonzero if for CLASS a mode change from FROM to TO is invalid. */
14879
14880 static bool
14881 rs6000_cannot_change_mode_class (enum machine_mode from,
14882 enum machine_mode to,
14883 enum reg_class rclass)
14884 {
14885 unsigned from_size = GET_MODE_SIZE (from);
14886 unsigned to_size = GET_MODE_SIZE (to);
14887
14888 if (from_size != to_size)
14889 {
14890 enum reg_class xclass = (TARGET_VSX) ? VSX_REGS : FLOAT_REGS;
14891 return ((from_size < 8 || to_size < 8 || TARGET_IEEEQUAD)
14892 && reg_classes_intersect_p (xclass, rclass));
14893 }
14894
14895 if (TARGET_E500_DOUBLE
14896 && ((((to) == DFmode) + ((from) == DFmode)) == 1
14897 || (((to) == TFmode) + ((from) == TFmode)) == 1
14898 || (((to) == DDmode) + ((from) == DDmode)) == 1
14899 || (((to) == TDmode) + ((from) == TDmode)) == 1
14900 || (((to) == DImode) + ((from) == DImode)) == 1))
14901 return true;
14902
14903 /* Since the VSX register set includes traditional floating point registers
14904 and altivec registers, just check for the size being different instead of
14905 trying to check whether the modes are vector modes. Otherwise it won't
14906 allow say DF and DI to change classes. */
14907 if (TARGET_VSX && VSX_REG_CLASS_P (rclass))
14908 return (from_size != 8 && from_size != 16);
14909
14910 if (TARGET_ALTIVEC && rclass == ALTIVEC_REGS
14911 && (ALTIVEC_VECTOR_MODE (from) + ALTIVEC_VECTOR_MODE (to)) == 1)
14912 return true;
14913
14914 if (TARGET_SPE && (SPE_VECTOR_MODE (from) + SPE_VECTOR_MODE (to)) == 1
14915 && reg_classes_intersect_p (GENERAL_REGS, rclass))
14916 return true;
14917
14918 return false;
14919 }
14920
14921 /* Debug version of rs6000_cannot_change_mode_class. */
14922 static bool
14923 rs6000_debug_cannot_change_mode_class (enum machine_mode from,
14924 enum machine_mode to,
14925 enum reg_class rclass)
14926 {
14927 bool ret = rs6000_cannot_change_mode_class (from, to, rclass);
14928
14929 fprintf (stderr,
14930 "rs6000_cannot_change_mode_class, return %s, from = %s, "
14931 "to = %s, rclass = %s\n",
14932 ret ? "true" : "false",
14933 GET_MODE_NAME (from), GET_MODE_NAME (to),
14934 reg_class_names[rclass]);
14935
14936 return ret;
14937 }
14938 \f
14939 /* Given a comparison operation, return the bit number in CCR to test. We
14940 know this is a valid comparison.
14941
14942 SCC_P is 1 if this is for an scc. That means that %D will have been
14943 used instead of %C, so the bits will be in different places.
14944
14945 Return -1 if OP isn't a valid comparison for some reason. */
14946
14947 int
14948 ccr_bit (rtx op, int scc_p)
14949 {
14950 enum rtx_code code = GET_CODE (op);
14951 enum machine_mode cc_mode;
14952 int cc_regnum;
14953 int base_bit;
14954 rtx reg;
14955
14956 if (!COMPARISON_P (op))
14957 return -1;
14958
14959 reg = XEXP (op, 0);
14960
14961 gcc_assert (GET_CODE (reg) == REG && CR_REGNO_P (REGNO (reg)));
14962
14963 cc_mode = GET_MODE (reg);
14964 cc_regnum = REGNO (reg);
14965 base_bit = 4 * (cc_regnum - CR0_REGNO);
14966
14967 validate_condition_mode (code, cc_mode);
14968
14969 /* When generating a sCOND operation, only positive conditions are
14970 allowed. */
14971 gcc_assert (!scc_p
14972 || code == EQ || code == GT || code == LT || code == UNORDERED
14973 || code == GTU || code == LTU);
14974
14975 switch (code)
14976 {
14977 case NE:
14978 return scc_p ? base_bit + 3 : base_bit + 2;
14979 case EQ:
14980 return base_bit + 2;
14981 case GT: case GTU: case UNLE:
14982 return base_bit + 1;
14983 case LT: case LTU: case UNGE:
14984 return base_bit;
14985 case ORDERED: case UNORDERED:
14986 return base_bit + 3;
14987
14988 case GE: case GEU:
14989 /* If scc, we will have done a cror to put the bit in the
14990 unordered position. So test that bit. For integer, this is ! LT
14991 unless this is an scc insn. */
14992 return scc_p ? base_bit + 3 : base_bit;
14993
14994 case LE: case LEU:
14995 return scc_p ? base_bit + 3 : base_bit + 1;
14996
14997 default:
14998 gcc_unreachable ();
14999 }
15000 }
15001 \f
15002 /* Return the GOT register. */
15003
15004 rtx
15005 rs6000_got_register (rtx value ATTRIBUTE_UNUSED)
15006 {
15007 /* The second flow pass currently (June 1999) can't update
15008 regs_ever_live without disturbing other parts of the compiler, so
15009 update it here to make the prolog/epilogue code happy. */
15010 if (!can_create_pseudo_p ()
15011 && !df_regs_ever_live_p (RS6000_PIC_OFFSET_TABLE_REGNUM))
15012 df_set_regs_ever_live (RS6000_PIC_OFFSET_TABLE_REGNUM, true);
15013
15014 crtl->uses_pic_offset_table = 1;
15015
15016 return pic_offset_table_rtx;
15017 }
15018 \f
15019 /* Function to init struct machine_function.
15020 This will be called, via a pointer variable,
15021 from push_function_context. */
15022
15023 static struct machine_function *
15024 rs6000_init_machine_status (void)
15025 {
15026 return ggc_alloc_cleared_machine_function ();
15027 }
15028 \f
15029 /* These macros test for integers and extract the low-order bits. */
15030 #define INT_P(X) \
15031 ((GET_CODE (X) == CONST_INT || GET_CODE (X) == CONST_DOUBLE) \
15032 && GET_MODE (X) == VOIDmode)
15033
15034 #define INT_LOWPART(X) \
15035 (GET_CODE (X) == CONST_INT ? INTVAL (X) : CONST_DOUBLE_LOW (X))
15036
15037 int
15038 extract_MB (rtx op)
15039 {
15040 int i;
15041 unsigned long val = INT_LOWPART (op);
15042
15043 /* If the high bit is zero, the value is the first 1 bit we find
15044 from the left. */
15045 if ((val & 0x80000000) == 0)
15046 {
15047 gcc_assert (val & 0xffffffff);
15048
15049 i = 1;
15050 while (((val <<= 1) & 0x80000000) == 0)
15051 ++i;
15052 return i;
15053 }
15054
15055 /* If the high bit is set and the low bit is not, or the mask is all
15056 1's, the value is zero. */
15057 if ((val & 1) == 0 || (val & 0xffffffff) == 0xffffffff)
15058 return 0;
15059
15060 /* Otherwise we have a wrap-around mask. Look for the first 0 bit
15061 from the right. */
15062 i = 31;
15063 while (((val >>= 1) & 1) != 0)
15064 --i;
15065
15066 return i;
15067 }
15068
15069 int
15070 extract_ME (rtx op)
15071 {
15072 int i;
15073 unsigned long val = INT_LOWPART (op);
15074
15075 /* If the low bit is zero, the value is the first 1 bit we find from
15076 the right. */
15077 if ((val & 1) == 0)
15078 {
15079 gcc_assert (val & 0xffffffff);
15080
15081 i = 30;
15082 while (((val >>= 1) & 1) == 0)
15083 --i;
15084
15085 return i;
15086 }
15087
15088 /* If the low bit is set and the high bit is not, or the mask is all
15089 1's, the value is 31. */
15090 if ((val & 0x80000000) == 0 || (val & 0xffffffff) == 0xffffffff)
15091 return 31;
15092
15093 /* Otherwise we have a wrap-around mask. Look for the first 0 bit
15094 from the left. */
15095 i = 0;
15096 while (((val <<= 1) & 0x80000000) != 0)
15097 ++i;
15098
15099 return i;
15100 }
15101
15102 /* Locate some local-dynamic symbol still in use by this function
15103 so that we can print its name in some tls_ld pattern. */
15104
15105 static const char *
15106 rs6000_get_some_local_dynamic_name (void)
15107 {
15108 rtx insn;
15109
15110 if (cfun->machine->some_ld_name)
15111 return cfun->machine->some_ld_name;
15112
15113 for (insn = get_insns (); insn ; insn = NEXT_INSN (insn))
15114 if (INSN_P (insn)
15115 && for_each_rtx (&PATTERN (insn),
15116 rs6000_get_some_local_dynamic_name_1, 0))
15117 return cfun->machine->some_ld_name;
15118
15119 gcc_unreachable ();
15120 }
15121
15122 /* Helper function for rs6000_get_some_local_dynamic_name. */
15123
15124 static int
15125 rs6000_get_some_local_dynamic_name_1 (rtx *px, void *data ATTRIBUTE_UNUSED)
15126 {
15127 rtx x = *px;
15128
15129 if (GET_CODE (x) == SYMBOL_REF)
15130 {
15131 const char *str = XSTR (x, 0);
15132 if (SYMBOL_REF_TLS_MODEL (x) == TLS_MODEL_LOCAL_DYNAMIC)
15133 {
15134 cfun->machine->some_ld_name = str;
15135 return 1;
15136 }
15137 }
15138
15139 return 0;
15140 }
15141
15142 /* Write out a function code label. */
15143
15144 void
15145 rs6000_output_function_entry (FILE *file, const char *fname)
15146 {
15147 if (fname[0] != '.')
15148 {
15149 switch (DEFAULT_ABI)
15150 {
15151 default:
15152 gcc_unreachable ();
15153
15154 case ABI_AIX:
15155 if (DOT_SYMBOLS)
15156 putc ('.', file);
15157 else
15158 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (file, "L.");
15159 break;
15160
15161 case ABI_V4:
15162 case ABI_DARWIN:
15163 break;
15164 }
15165 }
15166
15167 RS6000_OUTPUT_BASENAME (file, fname);
15168 }
15169
15170 /* Print an operand. Recognize special options, documented below. */
15171
15172 #if TARGET_ELF
15173 #define SMALL_DATA_RELOC ((rs6000_sdata == SDATA_EABI) ? "sda21" : "sdarel")
15174 #define SMALL_DATA_REG ((rs6000_sdata == SDATA_EABI) ? 0 : 13)
15175 #else
15176 #define SMALL_DATA_RELOC "sda21"
15177 #define SMALL_DATA_REG 0
15178 #endif
15179
15180 void
15181 print_operand (FILE *file, rtx x, int code)
15182 {
15183 int i;
15184 HOST_WIDE_INT val;
15185 unsigned HOST_WIDE_INT uval;
15186
15187 switch (code)
15188 {
15189 case '.':
15190 /* Write out an instruction after the call which may be replaced
15191 with glue code by the loader. This depends on the AIX version. */
15192 asm_fprintf (file, RS6000_CALL_GLUE);
15193 return;
15194
15195 /* %a is output_address. */
15196
15197 case 'A':
15198 /* If X is a constant integer whose low-order 5 bits are zero,
15199 write 'l'. Otherwise, write 'r'. This is a kludge to fix a bug
15200 in the AIX assembler where "sri" with a zero shift count
15201 writes a trash instruction. */
15202 if (GET_CODE (x) == CONST_INT && (INTVAL (x) & 31) == 0)
15203 putc ('l', file);
15204 else
15205 putc ('r', file);
15206 return;
15207
15208 case 'b':
15209 /* If constant, low-order 16 bits of constant, unsigned.
15210 Otherwise, write normally. */
15211 if (INT_P (x))
15212 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INT_LOWPART (x) & 0xffff);
15213 else
15214 print_operand (file, x, 0);
15215 return;
15216
15217 case 'B':
15218 /* If the low-order bit is zero, write 'r'; otherwise, write 'l'
15219 for 64-bit mask direction. */
15220 putc (((INT_LOWPART (x) & 1) == 0 ? 'r' : 'l'), file);
15221 return;
15222
15223 /* %c is output_addr_const if a CONSTANT_ADDRESS_P, otherwise
15224 output_operand. */
15225
15226 case 'c':
15227 /* X is a CR register. Print the number of the GT bit of the CR. */
15228 if (GET_CODE (x) != REG || ! CR_REGNO_P (REGNO (x)))
15229 output_operand_lossage ("invalid %%c value");
15230 else
15231 fprintf (file, "%d", 4 * (REGNO (x) - CR0_REGNO) + 1);
15232 return;
15233
15234 case 'D':
15235 /* Like 'J' but get to the GT bit only. */
15236 gcc_assert (GET_CODE (x) == REG);
15237
15238 /* Bit 1 is GT bit. */
15239 i = 4 * (REGNO (x) - CR0_REGNO) + 1;
15240
15241 /* Add one for shift count in rlinm for scc. */
15242 fprintf (file, "%d", i + 1);
15243 return;
15244
15245 case 'E':
15246 /* X is a CR register. Print the number of the EQ bit of the CR */
15247 if (GET_CODE (x) != REG || ! CR_REGNO_P (REGNO (x)))
15248 output_operand_lossage ("invalid %%E value");
15249 else
15250 fprintf (file, "%d", 4 * (REGNO (x) - CR0_REGNO) + 2);
15251 return;
15252
15253 case 'f':
15254 /* X is a CR register. Print the shift count needed to move it
15255 to the high-order four bits. */
15256 if (GET_CODE (x) != REG || ! CR_REGNO_P (REGNO (x)))
15257 output_operand_lossage ("invalid %%f value");
15258 else
15259 fprintf (file, "%d", 4 * (REGNO (x) - CR0_REGNO));
15260 return;
15261
15262 case 'F':
15263 /* Similar, but print the count for the rotate in the opposite
15264 direction. */
15265 if (GET_CODE (x) != REG || ! CR_REGNO_P (REGNO (x)))
15266 output_operand_lossage ("invalid %%F value");
15267 else
15268 fprintf (file, "%d", 32 - 4 * (REGNO (x) - CR0_REGNO));
15269 return;
15270
15271 case 'G':
15272 /* X is a constant integer. If it is negative, print "m",
15273 otherwise print "z". This is to make an aze or ame insn. */
15274 if (GET_CODE (x) != CONST_INT)
15275 output_operand_lossage ("invalid %%G value");
15276 else if (INTVAL (x) >= 0)
15277 putc ('z', file);
15278 else
15279 putc ('m', file);
15280 return;
15281
15282 case 'h':
15283 /* If constant, output low-order five bits. Otherwise, write
15284 normally. */
15285 if (INT_P (x))
15286 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INT_LOWPART (x) & 31);
15287 else
15288 print_operand (file, x, 0);
15289 return;
15290
15291 case 'H':
15292 /* If constant, output low-order six bits. Otherwise, write
15293 normally. */
15294 if (INT_P (x))
15295 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INT_LOWPART (x) & 63);
15296 else
15297 print_operand (file, x, 0);
15298 return;
15299
15300 case 'I':
15301 /* Print `i' if this is a constant, else nothing. */
15302 if (INT_P (x))
15303 putc ('i', file);
15304 return;
15305
15306 case 'j':
15307 /* Write the bit number in CCR for jump. */
15308 i = ccr_bit (x, 0);
15309 if (i == -1)
15310 output_operand_lossage ("invalid %%j code");
15311 else
15312 fprintf (file, "%d", i);
15313 return;
15314
15315 case 'J':
15316 /* Similar, but add one for shift count in rlinm for scc and pass
15317 scc flag to `ccr_bit'. */
15318 i = ccr_bit (x, 1);
15319 if (i == -1)
15320 output_operand_lossage ("invalid %%J code");
15321 else
15322 /* If we want bit 31, write a shift count of zero, not 32. */
15323 fprintf (file, "%d", i == 31 ? 0 : i + 1);
15324 return;
15325
15326 case 'k':
15327 /* X must be a constant. Write the 1's complement of the
15328 constant. */
15329 if (! INT_P (x))
15330 output_operand_lossage ("invalid %%k value");
15331 else
15332 fprintf (file, HOST_WIDE_INT_PRINT_DEC, ~ INT_LOWPART (x));
15333 return;
15334
15335 case 'K':
15336 /* X must be a symbolic constant on ELF. Write an
15337 expression suitable for an 'addi' that adds in the low 16
15338 bits of the MEM. */
15339 if (GET_CODE (x) == CONST)
15340 {
15341 if (GET_CODE (XEXP (x, 0)) != PLUS
15342 || (GET_CODE (XEXP (XEXP (x, 0), 0)) != SYMBOL_REF
15343 && GET_CODE (XEXP (XEXP (x, 0), 0)) != LABEL_REF)
15344 || GET_CODE (XEXP (XEXP (x, 0), 1)) != CONST_INT)
15345 output_operand_lossage ("invalid %%K value");
15346 }
15347 print_operand_address (file, x);
15348 fputs ("@l", file);
15349 return;
15350
15351 /* %l is output_asm_label. */
15352
15353 case 'L':
15354 /* Write second word of DImode or DFmode reference. Works on register
15355 or non-indexed memory only. */
15356 if (GET_CODE (x) == REG)
15357 fputs (reg_names[REGNO (x) + 1], file);
15358 else if (GET_CODE (x) == MEM)
15359 {
15360 /* Handle possible auto-increment. Since it is pre-increment and
15361 we have already done it, we can just use an offset of word. */
15362 if (GET_CODE (XEXP (x, 0)) == PRE_INC
15363 || GET_CODE (XEXP (x, 0)) == PRE_DEC)
15364 output_address (plus_constant (XEXP (XEXP (x, 0), 0),
15365 UNITS_PER_WORD));
15366 else if (GET_CODE (XEXP (x, 0)) == PRE_MODIFY)
15367 output_address (plus_constant (XEXP (XEXP (x, 0), 0),
15368 UNITS_PER_WORD));
15369 else
15370 output_address (XEXP (adjust_address_nv (x, SImode,
15371 UNITS_PER_WORD),
15372 0));
15373
15374 if (small_data_operand (x, GET_MODE (x)))
15375 fprintf (file, "@%s(%s)", SMALL_DATA_RELOC,
15376 reg_names[SMALL_DATA_REG]);
15377 }
15378 return;
15379
15380 case 'm':
15381 /* MB value for a mask operand. */
15382 if (! mask_operand (x, SImode))
15383 output_operand_lossage ("invalid %%m value");
15384
15385 fprintf (file, "%d", extract_MB (x));
15386 return;
15387
15388 case 'M':
15389 /* ME value for a mask operand. */
15390 if (! mask_operand (x, SImode))
15391 output_operand_lossage ("invalid %%M value");
15392
15393 fprintf (file, "%d", extract_ME (x));
15394 return;
15395
15396 /* %n outputs the negative of its operand. */
15397
15398 case 'N':
15399 /* Write the number of elements in the vector times 4. */
15400 if (GET_CODE (x) != PARALLEL)
15401 output_operand_lossage ("invalid %%N value");
15402 else
15403 fprintf (file, "%d", XVECLEN (x, 0) * 4);
15404 return;
15405
15406 case 'O':
15407 /* Similar, but subtract 1 first. */
15408 if (GET_CODE (x) != PARALLEL)
15409 output_operand_lossage ("invalid %%O value");
15410 else
15411 fprintf (file, "%d", (XVECLEN (x, 0) - 1) * 4);
15412 return;
15413
15414 case 'p':
15415 /* X is a CONST_INT that is a power of two. Output the logarithm. */
15416 if (! INT_P (x)
15417 || INT_LOWPART (x) < 0
15418 || (i = exact_log2 (INT_LOWPART (x))) < 0)
15419 output_operand_lossage ("invalid %%p value");
15420 else
15421 fprintf (file, "%d", i);
15422 return;
15423
15424 case 'P':
15425 /* The operand must be an indirect memory reference. The result
15426 is the register name. */
15427 if (GET_CODE (x) != MEM || GET_CODE (XEXP (x, 0)) != REG
15428 || REGNO (XEXP (x, 0)) >= 32)
15429 output_operand_lossage ("invalid %%P value");
15430 else
15431 fputs (reg_names[REGNO (XEXP (x, 0))], file);
15432 return;
15433
15434 case 'q':
15435 /* This outputs the logical code corresponding to a boolean
15436 expression. The expression may have one or both operands
15437 negated (if one, only the first one). For condition register
15438 logical operations, it will also treat the negated
15439 CR codes as NOTs, but not handle NOTs of them. */
15440 {
15441 const char *const *t = 0;
15442 const char *s;
15443 enum rtx_code code = GET_CODE (x);
15444 static const char * const tbl[3][3] = {
15445 { "and", "andc", "nor" },
15446 { "or", "orc", "nand" },
15447 { "xor", "eqv", "xor" } };
15448
15449 if (code == AND)
15450 t = tbl[0];
15451 else if (code == IOR)
15452 t = tbl[1];
15453 else if (code == XOR)
15454 t = tbl[2];
15455 else
15456 output_operand_lossage ("invalid %%q value");
15457
15458 if (GET_CODE (XEXP (x, 0)) != NOT)
15459 s = t[0];
15460 else
15461 {
15462 if (GET_CODE (XEXP (x, 1)) == NOT)
15463 s = t[2];
15464 else
15465 s = t[1];
15466 }
15467
15468 fputs (s, file);
15469 }
15470 return;
15471
15472 case 'Q':
15473 if (TARGET_MFCRF)
15474 fputc (',', file);
15475 /* FALLTHRU */
15476 else
15477 return;
15478
15479 case 'R':
15480 /* X is a CR register. Print the mask for `mtcrf'. */
15481 if (GET_CODE (x) != REG || ! CR_REGNO_P (REGNO (x)))
15482 output_operand_lossage ("invalid %%R value");
15483 else
15484 fprintf (file, "%d", 128 >> (REGNO (x) - CR0_REGNO));
15485 return;
15486
15487 case 's':
15488 /* Low 5 bits of 32 - value */
15489 if (! INT_P (x))
15490 output_operand_lossage ("invalid %%s value");
15491 else
15492 fprintf (file, HOST_WIDE_INT_PRINT_DEC, (32 - INT_LOWPART (x)) & 31);
15493 return;
15494
15495 case 'S':
15496 /* PowerPC64 mask position. All 0's is excluded.
15497 CONST_INT 32-bit mask is considered sign-extended so any
15498 transition must occur within the CONST_INT, not on the boundary. */
15499 if (! mask64_operand (x, DImode))
15500 output_operand_lossage ("invalid %%S value");
15501
15502 uval = INT_LOWPART (x);
15503
15504 if (uval & 1) /* Clear Left */
15505 {
15506 #if HOST_BITS_PER_WIDE_INT > 64
15507 uval &= ((unsigned HOST_WIDE_INT) 1 << 64) - 1;
15508 #endif
15509 i = 64;
15510 }
15511 else /* Clear Right */
15512 {
15513 uval = ~uval;
15514 #if HOST_BITS_PER_WIDE_INT > 64
15515 uval &= ((unsigned HOST_WIDE_INT) 1 << 64) - 1;
15516 #endif
15517 i = 63;
15518 }
15519 while (uval != 0)
15520 --i, uval >>= 1;
15521 gcc_assert (i >= 0);
15522 fprintf (file, "%d", i);
15523 return;
15524
15525 case 't':
15526 /* Like 'J' but get to the OVERFLOW/UNORDERED bit. */
15527 gcc_assert (GET_CODE (x) == REG && GET_MODE (x) == CCmode);
15528
15529 /* Bit 3 is OV bit. */
15530 i = 4 * (REGNO (x) - CR0_REGNO) + 3;
15531
15532 /* If we want bit 31, write a shift count of zero, not 32. */
15533 fprintf (file, "%d", i == 31 ? 0 : i + 1);
15534 return;
15535
15536 case 'T':
15537 /* Print the symbolic name of a branch target register. */
15538 if (GET_CODE (x) != REG || (REGNO (x) != LR_REGNO
15539 && REGNO (x) != CTR_REGNO))
15540 output_operand_lossage ("invalid %%T value");
15541 else if (REGNO (x) == LR_REGNO)
15542 fputs (TARGET_NEW_MNEMONICS ? "lr" : "r", file);
15543 else
15544 fputs ("ctr", file);
15545 return;
15546
15547 case 'u':
15548 /* High-order 16 bits of constant for use in unsigned operand. */
15549 if (! INT_P (x))
15550 output_operand_lossage ("invalid %%u value");
15551 else
15552 fprintf (file, HOST_WIDE_INT_PRINT_HEX,
15553 (INT_LOWPART (x) >> 16) & 0xffff);
15554 return;
15555
15556 case 'v':
15557 /* High-order 16 bits of constant for use in signed operand. */
15558 if (! INT_P (x))
15559 output_operand_lossage ("invalid %%v value");
15560 else
15561 fprintf (file, HOST_WIDE_INT_PRINT_HEX,
15562 (INT_LOWPART (x) >> 16) & 0xffff);
15563 return;
15564
15565 case 'U':
15566 /* Print `u' if this has an auto-increment or auto-decrement. */
15567 if (GET_CODE (x) == MEM
15568 && (GET_CODE (XEXP (x, 0)) == PRE_INC
15569 || GET_CODE (XEXP (x, 0)) == PRE_DEC
15570 || GET_CODE (XEXP (x, 0)) == PRE_MODIFY))
15571 putc ('u', file);
15572 return;
15573
15574 case 'V':
15575 /* Print the trap code for this operand. */
15576 switch (GET_CODE (x))
15577 {
15578 case EQ:
15579 fputs ("eq", file); /* 4 */
15580 break;
15581 case NE:
15582 fputs ("ne", file); /* 24 */
15583 break;
15584 case LT:
15585 fputs ("lt", file); /* 16 */
15586 break;
15587 case LE:
15588 fputs ("le", file); /* 20 */
15589 break;
15590 case GT:
15591 fputs ("gt", file); /* 8 */
15592 break;
15593 case GE:
15594 fputs ("ge", file); /* 12 */
15595 break;
15596 case LTU:
15597 fputs ("llt", file); /* 2 */
15598 break;
15599 case LEU:
15600 fputs ("lle", file); /* 6 */
15601 break;
15602 case GTU:
15603 fputs ("lgt", file); /* 1 */
15604 break;
15605 case GEU:
15606 fputs ("lge", file); /* 5 */
15607 break;
15608 default:
15609 gcc_unreachable ();
15610 }
15611 break;
15612
15613 case 'w':
15614 /* If constant, low-order 16 bits of constant, signed. Otherwise, write
15615 normally. */
15616 if (INT_P (x))
15617 fprintf (file, HOST_WIDE_INT_PRINT_DEC,
15618 ((INT_LOWPART (x) & 0xffff) ^ 0x8000) - 0x8000);
15619 else
15620 print_operand (file, x, 0);
15621 return;
15622
15623 case 'W':
15624 /* MB value for a PowerPC64 rldic operand. */
15625 val = (GET_CODE (x) == CONST_INT
15626 ? INTVAL (x) : CONST_DOUBLE_HIGH (x));
15627
15628 if (val < 0)
15629 i = -1;
15630 else
15631 for (i = 0; i < HOST_BITS_PER_WIDE_INT; i++)
15632 if ((val <<= 1) < 0)
15633 break;
15634
15635 #if HOST_BITS_PER_WIDE_INT == 32
15636 if (GET_CODE (x) == CONST_INT && i >= 0)
15637 i += 32; /* zero-extend high-part was all 0's */
15638 else if (GET_CODE (x) == CONST_DOUBLE && i == 32)
15639 {
15640 val = CONST_DOUBLE_LOW (x);
15641
15642 gcc_assert (val);
15643 if (val < 0)
15644 --i;
15645 else
15646 for ( ; i < 64; i++)
15647 if ((val <<= 1) < 0)
15648 break;
15649 }
15650 #endif
15651
15652 fprintf (file, "%d", i + 1);
15653 return;
15654
15655 case 'x':
15656 /* X is a FPR or Altivec register used in a VSX context. */
15657 if (GET_CODE (x) != REG || !VSX_REGNO_P (REGNO (x)))
15658 output_operand_lossage ("invalid %%x value");
15659 else
15660 {
15661 int reg = REGNO (x);
15662 int vsx_reg = (FP_REGNO_P (reg)
15663 ? reg - 32
15664 : reg - FIRST_ALTIVEC_REGNO + 32);
15665
15666 #ifdef TARGET_REGNAMES
15667 if (TARGET_REGNAMES)
15668 fprintf (file, "%%vs%d", vsx_reg);
15669 else
15670 #endif
15671 fprintf (file, "%d", vsx_reg);
15672 }
15673 return;
15674
15675 case 'X':
15676 if (GET_CODE (x) == MEM
15677 && (legitimate_indexed_address_p (XEXP (x, 0), 0)
15678 || (GET_CODE (XEXP (x, 0)) == PRE_MODIFY
15679 && legitimate_indexed_address_p (XEXP (XEXP (x, 0), 1), 0))))
15680 putc ('x', file);
15681 return;
15682
15683 case 'Y':
15684 /* Like 'L', for third word of TImode */
15685 if (GET_CODE (x) == REG)
15686 fputs (reg_names[REGNO (x) + 2], file);
15687 else if (GET_CODE (x) == MEM)
15688 {
15689 if (GET_CODE (XEXP (x, 0)) == PRE_INC
15690 || GET_CODE (XEXP (x, 0)) == PRE_DEC)
15691 output_address (plus_constant (XEXP (XEXP (x, 0), 0), 8));
15692 else if (GET_CODE (XEXP (x, 0)) == PRE_MODIFY)
15693 output_address (plus_constant (XEXP (XEXP (x, 0), 0), 8));
15694 else
15695 output_address (XEXP (adjust_address_nv (x, SImode, 8), 0));
15696 if (small_data_operand (x, GET_MODE (x)))
15697 fprintf (file, "@%s(%s)", SMALL_DATA_RELOC,
15698 reg_names[SMALL_DATA_REG]);
15699 }
15700 return;
15701
15702 case 'z':
15703 /* X is a SYMBOL_REF. Write out the name preceded by a
15704 period and without any trailing data in brackets. Used for function
15705 names. If we are configured for System V (or the embedded ABI) on
15706 the PowerPC, do not emit the period, since those systems do not use
15707 TOCs and the like. */
15708 gcc_assert (GET_CODE (x) == SYMBOL_REF);
15709
15710 /* Mark the decl as referenced so that cgraph will output the
15711 function. */
15712 if (SYMBOL_REF_DECL (x))
15713 mark_decl_referenced (SYMBOL_REF_DECL (x));
15714
15715 /* For macho, check to see if we need a stub. */
15716 if (TARGET_MACHO)
15717 {
15718 const char *name = XSTR (x, 0);
15719 #if TARGET_MACHO
15720 if (darwin_emit_branch_islands
15721 && MACHOPIC_INDIRECT
15722 && machopic_classify_symbol (x) == MACHOPIC_UNDEFINED_FUNCTION)
15723 name = machopic_indirection_name (x, /*stub_p=*/true);
15724 #endif
15725 assemble_name (file, name);
15726 }
15727 else if (!DOT_SYMBOLS)
15728 assemble_name (file, XSTR (x, 0));
15729 else
15730 rs6000_output_function_entry (file, XSTR (x, 0));
15731 return;
15732
15733 case 'Z':
15734 /* Like 'L', for last word of TImode. */
15735 if (GET_CODE (x) == REG)
15736 fputs (reg_names[REGNO (x) + 3], file);
15737 else if (GET_CODE (x) == MEM)
15738 {
15739 if (GET_CODE (XEXP (x, 0)) == PRE_INC
15740 || GET_CODE (XEXP (x, 0)) == PRE_DEC)
15741 output_address (plus_constant (XEXP (XEXP (x, 0), 0), 12));
15742 else if (GET_CODE (XEXP (x, 0)) == PRE_MODIFY)
15743 output_address (plus_constant (XEXP (XEXP (x, 0), 0), 12));
15744 else
15745 output_address (XEXP (adjust_address_nv (x, SImode, 12), 0));
15746 if (small_data_operand (x, GET_MODE (x)))
15747 fprintf (file, "@%s(%s)", SMALL_DATA_RELOC,
15748 reg_names[SMALL_DATA_REG]);
15749 }
15750 return;
15751
15752 /* Print AltiVec or SPE memory operand. */
15753 case 'y':
15754 {
15755 rtx tmp;
15756
15757 gcc_assert (GET_CODE (x) == MEM);
15758
15759 tmp = XEXP (x, 0);
15760
15761 /* Ugly hack because %y is overloaded. */
15762 if ((TARGET_SPE || TARGET_E500_DOUBLE)
15763 && (GET_MODE_SIZE (GET_MODE (x)) == 8
15764 || GET_MODE (x) == TFmode
15765 || GET_MODE (x) == TImode))
15766 {
15767 /* Handle [reg]. */
15768 if (GET_CODE (tmp) == REG)
15769 {
15770 fprintf (file, "0(%s)", reg_names[REGNO (tmp)]);
15771 break;
15772 }
15773 /* Handle [reg+UIMM]. */
15774 else if (GET_CODE (tmp) == PLUS &&
15775 GET_CODE (XEXP (tmp, 1)) == CONST_INT)
15776 {
15777 int x;
15778
15779 gcc_assert (GET_CODE (XEXP (tmp, 0)) == REG);
15780
15781 x = INTVAL (XEXP (tmp, 1));
15782 fprintf (file, "%d(%s)", x, reg_names[REGNO (XEXP (tmp, 0))]);
15783 break;
15784 }
15785
15786 /* Fall through. Must be [reg+reg]. */
15787 }
15788 if (VECTOR_MEM_ALTIVEC_P (GET_MODE (x))
15789 && GET_CODE (tmp) == AND
15790 && GET_CODE (XEXP (tmp, 1)) == CONST_INT
15791 && INTVAL (XEXP (tmp, 1)) == -16)
15792 tmp = XEXP (tmp, 0);
15793 else if (VECTOR_MEM_VSX_P (GET_MODE (x))
15794 && GET_CODE (tmp) == PRE_MODIFY)
15795 tmp = XEXP (tmp, 1);
15796 if (GET_CODE (tmp) == REG)
15797 fprintf (file, "0,%s", reg_names[REGNO (tmp)]);
15798 else
15799 {
15800 if (!GET_CODE (tmp) == PLUS
15801 || !REG_P (XEXP (tmp, 0))
15802 || !REG_P (XEXP (tmp, 1)))
15803 {
15804 output_operand_lossage ("invalid %%y value, try using the 'Z' constraint");
15805 break;
15806 }
15807
15808 if (REGNO (XEXP (tmp, 0)) == 0)
15809 fprintf (file, "%s,%s", reg_names[ REGNO (XEXP (tmp, 1)) ],
15810 reg_names[ REGNO (XEXP (tmp, 0)) ]);
15811 else
15812 fprintf (file, "%s,%s", reg_names[ REGNO (XEXP (tmp, 0)) ],
15813 reg_names[ REGNO (XEXP (tmp, 1)) ]);
15814 }
15815 break;
15816 }
15817
15818 case 0:
15819 if (GET_CODE (x) == REG)
15820 fprintf (file, "%s", reg_names[REGNO (x)]);
15821 else if (GET_CODE (x) == MEM)
15822 {
15823 /* We need to handle PRE_INC and PRE_DEC here, since we need to
15824 know the width from the mode. */
15825 if (GET_CODE (XEXP (x, 0)) == PRE_INC)
15826 fprintf (file, "%d(%s)", GET_MODE_SIZE (GET_MODE (x)),
15827 reg_names[REGNO (XEXP (XEXP (x, 0), 0))]);
15828 else if (GET_CODE (XEXP (x, 0)) == PRE_DEC)
15829 fprintf (file, "%d(%s)", - GET_MODE_SIZE (GET_MODE (x)),
15830 reg_names[REGNO (XEXP (XEXP (x, 0), 0))]);
15831 else if (GET_CODE (XEXP (x, 0)) == PRE_MODIFY)
15832 output_address (XEXP (XEXP (x, 0), 1));
15833 else
15834 output_address (XEXP (x, 0));
15835 }
15836 else
15837 output_addr_const (file, x);
15838 return;
15839
15840 case '&':
15841 assemble_name (file, rs6000_get_some_local_dynamic_name ());
15842 return;
15843
15844 default:
15845 output_operand_lossage ("invalid %%xn code");
15846 }
15847 }
15848 \f
15849 /* Print the address of an operand. */
15850
15851 void
15852 print_operand_address (FILE *file, rtx x)
15853 {
15854 if (GET_CODE (x) == REG)
15855 fprintf (file, "0(%s)", reg_names[ REGNO (x) ]);
15856 else if (GET_CODE (x) == SYMBOL_REF || GET_CODE (x) == CONST
15857 || GET_CODE (x) == LABEL_REF)
15858 {
15859 output_addr_const (file, x);
15860 if (small_data_operand (x, GET_MODE (x)))
15861 fprintf (file, "@%s(%s)", SMALL_DATA_RELOC,
15862 reg_names[SMALL_DATA_REG]);
15863 else
15864 gcc_assert (!TARGET_TOC);
15865 }
15866 else if (GET_CODE (x) == PLUS && GET_CODE (XEXP (x, 1)) == REG)
15867 {
15868 gcc_assert (REG_P (XEXP (x, 0)));
15869 if (REGNO (XEXP (x, 0)) == 0)
15870 fprintf (file, "%s,%s", reg_names[ REGNO (XEXP (x, 1)) ],
15871 reg_names[ REGNO (XEXP (x, 0)) ]);
15872 else
15873 fprintf (file, "%s,%s", reg_names[ REGNO (XEXP (x, 0)) ],
15874 reg_names[ REGNO (XEXP (x, 1)) ]);
15875 }
15876 else if (GET_CODE (x) == PLUS && GET_CODE (XEXP (x, 1)) == CONST_INT)
15877 fprintf (file, HOST_WIDE_INT_PRINT_DEC "(%s)",
15878 INTVAL (XEXP (x, 1)), reg_names[ REGNO (XEXP (x, 0)) ]);
15879 #if TARGET_MACHO
15880 else if (GET_CODE (x) == LO_SUM && GET_CODE (XEXP (x, 0)) == REG
15881 && CONSTANT_P (XEXP (x, 1)))
15882 {
15883 fprintf (file, "lo16(");
15884 output_addr_const (file, XEXP (x, 1));
15885 fprintf (file, ")(%s)", reg_names[ REGNO (XEXP (x, 0)) ]);
15886 }
15887 #endif
15888 else if (legitimate_constant_pool_address_p (x, true))
15889 {
15890 /* This hack along with a corresponding hack in
15891 rs6000_output_addr_const_extra arranges to output addends
15892 where the assembler expects to find them. eg.
15893 (lo_sum (reg 9)
15894 . (const (plus (unspec [symbol_ref ("x") tocrel]) 8)))
15895 without this hack would be output as "x@toc+8@l(9)". We
15896 want "x+8@toc@l(9)". */
15897 output_addr_const (file, tocrel_base);
15898 if (GET_CODE (x) == LO_SUM)
15899 fprintf (file, "@l(%s)", reg_names[ REGNO (XEXP (x, 0)) ]);
15900 else
15901 fprintf (file, "(%s)", reg_names[REGNO (XEXP (x, 0))]);
15902 }
15903 #if TARGET_ELF
15904 else if (GET_CODE (x) == LO_SUM && GET_CODE (XEXP (x, 0)) == REG
15905 && CONSTANT_P (XEXP (x, 1)))
15906 {
15907 output_addr_const (file, XEXP (x, 1));
15908 fprintf (file, "@l(%s)", reg_names[ REGNO (XEXP (x, 0)) ]);
15909 }
15910 #endif
15911 else
15912 gcc_unreachable ();
15913 }
15914 \f
15915 /* Implement OUTPUT_ADDR_CONST_EXTRA for address X. */
15916
15917 bool
15918 rs6000_output_addr_const_extra (FILE *file, rtx x)
15919 {
15920 if (GET_CODE (x) == UNSPEC)
15921 switch (XINT (x, 1))
15922 {
15923 case UNSPEC_TOCREL:
15924 gcc_assert (GET_CODE (XVECEXP (x, 0, 0)) == SYMBOL_REF);
15925 output_addr_const (file, XVECEXP (x, 0, 0));
15926 if (x == tocrel_base && tocrel_offset != const0_rtx)
15927 {
15928 if (INTVAL (tocrel_offset) >= 0)
15929 fprintf (file, "+");
15930 output_addr_const (file, tocrel_offset);
15931 }
15932 if (!TARGET_AIX || (TARGET_ELF && TARGET_MINIMAL_TOC))
15933 {
15934 putc ('-', file);
15935 assemble_name (file, toc_label_name);
15936 }
15937 else if (TARGET_ELF)
15938 fputs ("@toc", file);
15939 return true;
15940
15941 #if TARGET_MACHO
15942 case UNSPEC_MACHOPIC_OFFSET:
15943 output_addr_const (file, XVECEXP (x, 0, 0));
15944 putc ('-', file);
15945 machopic_output_function_base_name (file);
15946 return true;
15947 #endif
15948 }
15949 return false;
15950 }
15951 \f
15952 /* Target hook for assembling integer objects. The PowerPC version has
15953 to handle fixup entries for relocatable code if RELOCATABLE_NEEDS_FIXUP
15954 is defined. It also needs to handle DI-mode objects on 64-bit
15955 targets. */
15956
15957 static bool
15958 rs6000_assemble_integer (rtx x, unsigned int size, int aligned_p)
15959 {
15960 #ifdef RELOCATABLE_NEEDS_FIXUP
15961 /* Special handling for SI values. */
15962 if (RELOCATABLE_NEEDS_FIXUP && size == 4 && aligned_p)
15963 {
15964 static int recurse = 0;
15965
15966 /* For -mrelocatable, we mark all addresses that need to be fixed up
15967 in the .fixup section. */
15968 if (TARGET_RELOCATABLE
15969 && in_section != toc_section
15970 && in_section != text_section
15971 && !unlikely_text_section_p (in_section)
15972 && !recurse
15973 && GET_CODE (x) != CONST_INT
15974 && GET_CODE (x) != CONST_DOUBLE
15975 && CONSTANT_P (x))
15976 {
15977 char buf[256];
15978
15979 recurse = 1;
15980 ASM_GENERATE_INTERNAL_LABEL (buf, "LCP", fixuplabelno);
15981 fixuplabelno++;
15982 ASM_OUTPUT_LABEL (asm_out_file, buf);
15983 fprintf (asm_out_file, "\t.long\t(");
15984 output_addr_const (asm_out_file, x);
15985 fprintf (asm_out_file, ")@fixup\n");
15986 fprintf (asm_out_file, "\t.section\t\".fixup\",\"aw\"\n");
15987 ASM_OUTPUT_ALIGN (asm_out_file, 2);
15988 fprintf (asm_out_file, "\t.long\t");
15989 assemble_name (asm_out_file, buf);
15990 fprintf (asm_out_file, "\n\t.previous\n");
15991 recurse = 0;
15992 return true;
15993 }
15994 /* Remove initial .'s to turn a -mcall-aixdesc function
15995 address into the address of the descriptor, not the function
15996 itself. */
15997 else if (GET_CODE (x) == SYMBOL_REF
15998 && XSTR (x, 0)[0] == '.'
15999 && DEFAULT_ABI == ABI_AIX)
16000 {
16001 const char *name = XSTR (x, 0);
16002 while (*name == '.')
16003 name++;
16004
16005 fprintf (asm_out_file, "\t.long\t%s\n", name);
16006 return true;
16007 }
16008 }
16009 #endif /* RELOCATABLE_NEEDS_FIXUP */
16010 return default_assemble_integer (x, size, aligned_p);
16011 }
16012
16013 #ifdef HAVE_GAS_HIDDEN
16014 /* Emit an assembler directive to set symbol visibility for DECL to
16015 VISIBILITY_TYPE. */
16016
16017 static void
16018 rs6000_assemble_visibility (tree decl, int vis)
16019 {
16020 /* Functions need to have their entry point symbol visibility set as
16021 well as their descriptor symbol visibility. */
16022 if (DEFAULT_ABI == ABI_AIX
16023 && DOT_SYMBOLS
16024 && TREE_CODE (decl) == FUNCTION_DECL)
16025 {
16026 static const char * const visibility_types[] = {
16027 NULL, "internal", "hidden", "protected"
16028 };
16029
16030 const char *name, *type;
16031
16032 name = ((* targetm.strip_name_encoding)
16033 (IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl))));
16034 type = visibility_types[vis];
16035
16036 fprintf (asm_out_file, "\t.%s\t%s\n", type, name);
16037 fprintf (asm_out_file, "\t.%s\t.%s\n", type, name);
16038 }
16039 else
16040 default_assemble_visibility (decl, vis);
16041 }
16042 #endif
16043 \f
16044 enum rtx_code
16045 rs6000_reverse_condition (enum machine_mode mode, enum rtx_code code)
16046 {
16047 /* Reversal of FP compares takes care -- an ordered compare
16048 becomes an unordered compare and vice versa. */
16049 if (mode == CCFPmode
16050 && (!flag_finite_math_only
16051 || code == UNLT || code == UNLE || code == UNGT || code == UNGE
16052 || code == UNEQ || code == LTGT))
16053 return reverse_condition_maybe_unordered (code);
16054 else
16055 return reverse_condition (code);
16056 }
16057
16058 /* Generate a compare for CODE. Return a brand-new rtx that
16059 represents the result of the compare. */
16060
16061 static rtx
16062 rs6000_generate_compare (rtx cmp, enum machine_mode mode)
16063 {
16064 enum machine_mode comp_mode;
16065 rtx compare_result;
16066 enum rtx_code code = GET_CODE (cmp);
16067 rtx op0 = XEXP (cmp, 0);
16068 rtx op1 = XEXP (cmp, 1);
16069
16070 if (FLOAT_MODE_P (mode))
16071 comp_mode = CCFPmode;
16072 else if (code == GTU || code == LTU
16073 || code == GEU || code == LEU)
16074 comp_mode = CCUNSmode;
16075 else if ((code == EQ || code == NE)
16076 && GET_CODE (op0) == SUBREG
16077 && GET_CODE (op1) == SUBREG
16078 && SUBREG_PROMOTED_UNSIGNED_P (op0)
16079 && SUBREG_PROMOTED_UNSIGNED_P (op1))
16080 /* These are unsigned values, perhaps there will be a later
16081 ordering compare that can be shared with this one.
16082 Unfortunately we cannot detect the signedness of the operands
16083 for non-subregs. */
16084 comp_mode = CCUNSmode;
16085 else
16086 comp_mode = CCmode;
16087
16088 /* First, the compare. */
16089 compare_result = gen_reg_rtx (comp_mode);
16090
16091 /* E500 FP compare instructions on the GPRs. Yuck! */
16092 if ((!TARGET_FPRS && TARGET_HARD_FLOAT)
16093 && FLOAT_MODE_P (mode))
16094 {
16095 rtx cmp, or_result, compare_result2;
16096 enum machine_mode op_mode = GET_MODE (op0);
16097
16098 if (op_mode == VOIDmode)
16099 op_mode = GET_MODE (op1);
16100
16101 /* The E500 FP compare instructions toggle the GT bit (CR bit 1) only.
16102 This explains the following mess. */
16103
16104 switch (code)
16105 {
16106 case EQ: case UNEQ: case NE: case LTGT:
16107 switch (op_mode)
16108 {
16109 case SFmode:
16110 cmp = (flag_finite_math_only && !flag_trapping_math)
16111 ? gen_tstsfeq_gpr (compare_result, op0, op1)
16112 : gen_cmpsfeq_gpr (compare_result, op0, op1);
16113 break;
16114
16115 case DFmode:
16116 cmp = (flag_finite_math_only && !flag_trapping_math)
16117 ? gen_tstdfeq_gpr (compare_result, op0, op1)
16118 : gen_cmpdfeq_gpr (compare_result, op0, op1);
16119 break;
16120
16121 case TFmode:
16122 cmp = (flag_finite_math_only && !flag_trapping_math)
16123 ? gen_tsttfeq_gpr (compare_result, op0, op1)
16124 : gen_cmptfeq_gpr (compare_result, op0, op1);
16125 break;
16126
16127 default:
16128 gcc_unreachable ();
16129 }
16130 break;
16131
16132 case GT: case GTU: case UNGT: case UNGE: case GE: case GEU:
16133 switch (op_mode)
16134 {
16135 case SFmode:
16136 cmp = (flag_finite_math_only && !flag_trapping_math)
16137 ? gen_tstsfgt_gpr (compare_result, op0, op1)
16138 : gen_cmpsfgt_gpr (compare_result, op0, op1);
16139 break;
16140
16141 case DFmode:
16142 cmp = (flag_finite_math_only && !flag_trapping_math)
16143 ? gen_tstdfgt_gpr (compare_result, op0, op1)
16144 : gen_cmpdfgt_gpr (compare_result, op0, op1);
16145 break;
16146
16147 case TFmode:
16148 cmp = (flag_finite_math_only && !flag_trapping_math)
16149 ? gen_tsttfgt_gpr (compare_result, op0, op1)
16150 : gen_cmptfgt_gpr (compare_result, op0, op1);
16151 break;
16152
16153 default:
16154 gcc_unreachable ();
16155 }
16156 break;
16157
16158 case LT: case LTU: case UNLT: case UNLE: case LE: case LEU:
16159 switch (op_mode)
16160 {
16161 case SFmode:
16162 cmp = (flag_finite_math_only && !flag_trapping_math)
16163 ? gen_tstsflt_gpr (compare_result, op0, op1)
16164 : gen_cmpsflt_gpr (compare_result, op0, op1);
16165 break;
16166
16167 case DFmode:
16168 cmp = (flag_finite_math_only && !flag_trapping_math)
16169 ? gen_tstdflt_gpr (compare_result, op0, op1)
16170 : gen_cmpdflt_gpr (compare_result, op0, op1);
16171 break;
16172
16173 case TFmode:
16174 cmp = (flag_finite_math_only && !flag_trapping_math)
16175 ? gen_tsttflt_gpr (compare_result, op0, op1)
16176 : gen_cmptflt_gpr (compare_result, op0, op1);
16177 break;
16178
16179 default:
16180 gcc_unreachable ();
16181 }
16182 break;
16183 default:
16184 gcc_unreachable ();
16185 }
16186
16187 /* Synthesize LE and GE from LT/GT || EQ. */
16188 if (code == LE || code == GE || code == LEU || code == GEU)
16189 {
16190 emit_insn (cmp);
16191
16192 switch (code)
16193 {
16194 case LE: code = LT; break;
16195 case GE: code = GT; break;
16196 case LEU: code = LT; break;
16197 case GEU: code = GT; break;
16198 default: gcc_unreachable ();
16199 }
16200
16201 compare_result2 = gen_reg_rtx (CCFPmode);
16202
16203 /* Do the EQ. */
16204 switch (op_mode)
16205 {
16206 case SFmode:
16207 cmp = (flag_finite_math_only && !flag_trapping_math)
16208 ? gen_tstsfeq_gpr (compare_result2, op0, op1)
16209 : gen_cmpsfeq_gpr (compare_result2, op0, op1);
16210 break;
16211
16212 case DFmode:
16213 cmp = (flag_finite_math_only && !flag_trapping_math)
16214 ? gen_tstdfeq_gpr (compare_result2, op0, op1)
16215 : gen_cmpdfeq_gpr (compare_result2, op0, op1);
16216 break;
16217
16218 case TFmode:
16219 cmp = (flag_finite_math_only && !flag_trapping_math)
16220 ? gen_tsttfeq_gpr (compare_result2, op0, op1)
16221 : gen_cmptfeq_gpr (compare_result2, op0, op1);
16222 break;
16223
16224 default:
16225 gcc_unreachable ();
16226 }
16227 emit_insn (cmp);
16228
16229 /* OR them together. */
16230 or_result = gen_reg_rtx (CCFPmode);
16231 cmp = gen_e500_cr_ior_compare (or_result, compare_result,
16232 compare_result2);
16233 compare_result = or_result;
16234 code = EQ;
16235 }
16236 else
16237 {
16238 if (code == NE || code == LTGT)
16239 code = NE;
16240 else
16241 code = EQ;
16242 }
16243
16244 emit_insn (cmp);
16245 }
16246 else
16247 {
16248 /* Generate XLC-compatible TFmode compare as PARALLEL with extra
16249 CLOBBERs to match cmptf_internal2 pattern. */
16250 if (comp_mode == CCFPmode && TARGET_XL_COMPAT
16251 && GET_MODE (op0) == TFmode
16252 && !TARGET_IEEEQUAD
16253 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128)
16254 emit_insn (gen_rtx_PARALLEL (VOIDmode,
16255 gen_rtvec (10,
16256 gen_rtx_SET (VOIDmode,
16257 compare_result,
16258 gen_rtx_COMPARE (comp_mode, op0, op1)),
16259 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
16260 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
16261 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
16262 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
16263 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
16264 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
16265 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
16266 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (DFmode)),
16267 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (Pmode)))));
16268 else if (GET_CODE (op1) == UNSPEC
16269 && XINT (op1, 1) == UNSPEC_SP_TEST)
16270 {
16271 rtx op1b = XVECEXP (op1, 0, 0);
16272 comp_mode = CCEQmode;
16273 compare_result = gen_reg_rtx (CCEQmode);
16274 if (TARGET_64BIT)
16275 emit_insn (gen_stack_protect_testdi (compare_result, op0, op1b));
16276 else
16277 emit_insn (gen_stack_protect_testsi (compare_result, op0, op1b));
16278 }
16279 else
16280 emit_insn (gen_rtx_SET (VOIDmode, compare_result,
16281 gen_rtx_COMPARE (comp_mode, op0, op1)));
16282 }
16283
16284 /* Some kinds of FP comparisons need an OR operation;
16285 under flag_finite_math_only we don't bother. */
16286 if (FLOAT_MODE_P (mode)
16287 && !flag_finite_math_only
16288 && !(TARGET_HARD_FLOAT && !TARGET_FPRS)
16289 && (code == LE || code == GE
16290 || code == UNEQ || code == LTGT
16291 || code == UNGT || code == UNLT))
16292 {
16293 enum rtx_code or1, or2;
16294 rtx or1_rtx, or2_rtx, compare2_rtx;
16295 rtx or_result = gen_reg_rtx (CCEQmode);
16296
16297 switch (code)
16298 {
16299 case LE: or1 = LT; or2 = EQ; break;
16300 case GE: or1 = GT; or2 = EQ; break;
16301 case UNEQ: or1 = UNORDERED; or2 = EQ; break;
16302 case LTGT: or1 = LT; or2 = GT; break;
16303 case UNGT: or1 = UNORDERED; or2 = GT; break;
16304 case UNLT: or1 = UNORDERED; or2 = LT; break;
16305 default: gcc_unreachable ();
16306 }
16307 validate_condition_mode (or1, comp_mode);
16308 validate_condition_mode (or2, comp_mode);
16309 or1_rtx = gen_rtx_fmt_ee (or1, SImode, compare_result, const0_rtx);
16310 or2_rtx = gen_rtx_fmt_ee (or2, SImode, compare_result, const0_rtx);
16311 compare2_rtx = gen_rtx_COMPARE (CCEQmode,
16312 gen_rtx_IOR (SImode, or1_rtx, or2_rtx),
16313 const_true_rtx);
16314 emit_insn (gen_rtx_SET (VOIDmode, or_result, compare2_rtx));
16315
16316 compare_result = or_result;
16317 code = EQ;
16318 }
16319
16320 validate_condition_mode (code, GET_MODE (compare_result));
16321
16322 return gen_rtx_fmt_ee (code, VOIDmode, compare_result, const0_rtx);
16323 }
16324
16325
16326 /* Emit the RTL for an sISEL pattern. */
16327
16328 void
16329 rs6000_emit_sISEL (enum machine_mode mode ATTRIBUTE_UNUSED, rtx operands[])
16330 {
16331 rs6000_emit_int_cmove (operands[0], operands[1], const1_rtx, const0_rtx);
16332 }
16333
16334 void
16335 rs6000_emit_sCOND (enum machine_mode mode, rtx operands[])
16336 {
16337 rtx condition_rtx;
16338 enum machine_mode op_mode;
16339 enum rtx_code cond_code;
16340 rtx result = operands[0];
16341
16342 if (TARGET_ISEL && (mode == SImode || mode == DImode))
16343 {
16344 rs6000_emit_sISEL (mode, operands);
16345 return;
16346 }
16347
16348 condition_rtx = rs6000_generate_compare (operands[1], mode);
16349 cond_code = GET_CODE (condition_rtx);
16350
16351 if (FLOAT_MODE_P (mode)
16352 && !TARGET_FPRS && TARGET_HARD_FLOAT)
16353 {
16354 rtx t;
16355
16356 PUT_MODE (condition_rtx, SImode);
16357 t = XEXP (condition_rtx, 0);
16358
16359 gcc_assert (cond_code == NE || cond_code == EQ);
16360
16361 if (cond_code == NE)
16362 emit_insn (gen_e500_flip_gt_bit (t, t));
16363
16364 emit_insn (gen_move_from_CR_gt_bit (result, t));
16365 return;
16366 }
16367
16368 if (cond_code == NE
16369 || cond_code == GE || cond_code == LE
16370 || cond_code == GEU || cond_code == LEU
16371 || cond_code == ORDERED || cond_code == UNGE || cond_code == UNLE)
16372 {
16373 rtx not_result = gen_reg_rtx (CCEQmode);
16374 rtx not_op, rev_cond_rtx;
16375 enum machine_mode cc_mode;
16376
16377 cc_mode = GET_MODE (XEXP (condition_rtx, 0));
16378
16379 rev_cond_rtx = gen_rtx_fmt_ee (rs6000_reverse_condition (cc_mode, cond_code),
16380 SImode, XEXP (condition_rtx, 0), const0_rtx);
16381 not_op = gen_rtx_COMPARE (CCEQmode, rev_cond_rtx, const0_rtx);
16382 emit_insn (gen_rtx_SET (VOIDmode, not_result, not_op));
16383 condition_rtx = gen_rtx_EQ (VOIDmode, not_result, const0_rtx);
16384 }
16385
16386 op_mode = GET_MODE (XEXP (operands[1], 0));
16387 if (op_mode == VOIDmode)
16388 op_mode = GET_MODE (XEXP (operands[1], 1));
16389
16390 if (TARGET_POWERPC64 && (op_mode == DImode || FLOAT_MODE_P (mode)))
16391 {
16392 PUT_MODE (condition_rtx, DImode);
16393 convert_move (result, condition_rtx, 0);
16394 }
16395 else
16396 {
16397 PUT_MODE (condition_rtx, SImode);
16398 emit_insn (gen_rtx_SET (VOIDmode, result, condition_rtx));
16399 }
16400 }
16401
16402 /* Emit a branch of kind CODE to location LOC. */
16403
16404 void
16405 rs6000_emit_cbranch (enum machine_mode mode, rtx operands[])
16406 {
16407 rtx condition_rtx, loc_ref;
16408
16409 condition_rtx = rs6000_generate_compare (operands[0], mode);
16410 loc_ref = gen_rtx_LABEL_REF (VOIDmode, operands[3]);
16411 emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx,
16412 gen_rtx_IF_THEN_ELSE (VOIDmode, condition_rtx,
16413 loc_ref, pc_rtx)));
16414 }
16415
16416 /* Return the string to output a conditional branch to LABEL, which is
16417 the operand number of the label, or -1 if the branch is really a
16418 conditional return.
16419
16420 OP is the conditional expression. XEXP (OP, 0) is assumed to be a
16421 condition code register and its mode specifies what kind of
16422 comparison we made.
16423
16424 REVERSED is nonzero if we should reverse the sense of the comparison.
16425
16426 INSN is the insn. */
16427
16428 char *
16429 output_cbranch (rtx op, const char *label, int reversed, rtx insn)
16430 {
16431 static char string[64];
16432 enum rtx_code code = GET_CODE (op);
16433 rtx cc_reg = XEXP (op, 0);
16434 enum machine_mode mode = GET_MODE (cc_reg);
16435 int cc_regno = REGNO (cc_reg) - CR0_REGNO;
16436 int need_longbranch = label != NULL && get_attr_length (insn) == 8;
16437 int really_reversed = reversed ^ need_longbranch;
16438 char *s = string;
16439 const char *ccode;
16440 const char *pred;
16441 rtx note;
16442
16443 validate_condition_mode (code, mode);
16444
16445 /* Work out which way this really branches. We could use
16446 reverse_condition_maybe_unordered here always but this
16447 makes the resulting assembler clearer. */
16448 if (really_reversed)
16449 {
16450 /* Reversal of FP compares takes care -- an ordered compare
16451 becomes an unordered compare and vice versa. */
16452 if (mode == CCFPmode)
16453 code = reverse_condition_maybe_unordered (code);
16454 else
16455 code = reverse_condition (code);
16456 }
16457
16458 if ((!TARGET_FPRS && TARGET_HARD_FLOAT) && mode == CCFPmode)
16459 {
16460 /* The efscmp/tst* instructions twiddle bit 2, which maps nicely
16461 to the GT bit. */
16462 switch (code)
16463 {
16464 case EQ:
16465 /* Opposite of GT. */
16466 code = GT;
16467 break;
16468
16469 case NE:
16470 code = UNLE;
16471 break;
16472
16473 default:
16474 gcc_unreachable ();
16475 }
16476 }
16477
16478 switch (code)
16479 {
16480 /* Not all of these are actually distinct opcodes, but
16481 we distinguish them for clarity of the resulting assembler. */
16482 case NE: case LTGT:
16483 ccode = "ne"; break;
16484 case EQ: case UNEQ:
16485 ccode = "eq"; break;
16486 case GE: case GEU:
16487 ccode = "ge"; break;
16488 case GT: case GTU: case UNGT:
16489 ccode = "gt"; break;
16490 case LE: case LEU:
16491 ccode = "le"; break;
16492 case LT: case LTU: case UNLT:
16493 ccode = "lt"; break;
16494 case UNORDERED: ccode = "un"; break;
16495 case ORDERED: ccode = "nu"; break;
16496 case UNGE: ccode = "nl"; break;
16497 case UNLE: ccode = "ng"; break;
16498 default:
16499 gcc_unreachable ();
16500 }
16501
16502 /* Maybe we have a guess as to how likely the branch is.
16503 The old mnemonics don't have a way to specify this information. */
16504 pred = "";
16505 note = find_reg_note (insn, REG_BR_PROB, NULL_RTX);
16506 if (note != NULL_RTX)
16507 {
16508 /* PROB is the difference from 50%. */
16509 int prob = INTVAL (XEXP (note, 0)) - REG_BR_PROB_BASE / 2;
16510
16511 /* Only hint for highly probable/improbable branches on newer
16512 cpus as static prediction overrides processor dynamic
16513 prediction. For older cpus we may as well always hint, but
16514 assume not taken for branches that are very close to 50% as a
16515 mispredicted taken branch is more expensive than a
16516 mispredicted not-taken branch. */
16517 if (rs6000_always_hint
16518 || (abs (prob) > REG_BR_PROB_BASE / 100 * 48
16519 && br_prob_note_reliable_p (note)))
16520 {
16521 if (abs (prob) > REG_BR_PROB_BASE / 20
16522 && ((prob > 0) ^ need_longbranch))
16523 pred = "+";
16524 else
16525 pred = "-";
16526 }
16527 }
16528
16529 if (label == NULL)
16530 s += sprintf (s, "{b%sr|b%slr%s} ", ccode, ccode, pred);
16531 else
16532 s += sprintf (s, "{b%s|b%s%s} ", ccode, ccode, pred);
16533
16534 /* We need to escape any '%' characters in the reg_names string.
16535 Assume they'd only be the first character.... */
16536 if (reg_names[cc_regno + CR0_REGNO][0] == '%')
16537 *s++ = '%';
16538 s += sprintf (s, "%s", reg_names[cc_regno + CR0_REGNO]);
16539
16540 if (label != NULL)
16541 {
16542 /* If the branch distance was too far, we may have to use an
16543 unconditional branch to go the distance. */
16544 if (need_longbranch)
16545 s += sprintf (s, ",$+8\n\tb %s", label);
16546 else
16547 s += sprintf (s, ",%s", label);
16548 }
16549
16550 return string;
16551 }
16552
16553 /* Return the string to flip the GT bit on a CR. */
16554 char *
16555 output_e500_flip_gt_bit (rtx dst, rtx src)
16556 {
16557 static char string[64];
16558 int a, b;
16559
16560 gcc_assert (GET_CODE (dst) == REG && CR_REGNO_P (REGNO (dst))
16561 && GET_CODE (src) == REG && CR_REGNO_P (REGNO (src)));
16562
16563 /* GT bit. */
16564 a = 4 * (REGNO (dst) - CR0_REGNO) + 1;
16565 b = 4 * (REGNO (src) - CR0_REGNO) + 1;
16566
16567 sprintf (string, "crnot %d,%d", a, b);
16568 return string;
16569 }
16570
16571 /* Return insn for VSX or Altivec comparisons. */
16572
16573 static rtx
16574 rs6000_emit_vector_compare_inner (enum rtx_code code, rtx op0, rtx op1)
16575 {
16576 rtx mask;
16577 enum machine_mode mode = GET_MODE (op0);
16578
16579 switch (code)
16580 {
16581 default:
16582 break;
16583
16584 case GE:
16585 if (GET_MODE_CLASS (mode) == MODE_VECTOR_INT)
16586 return NULL_RTX;
16587
16588 case EQ:
16589 case GT:
16590 case GTU:
16591 mask = gen_reg_rtx (mode);
16592 emit_insn (gen_rtx_SET (VOIDmode,
16593 mask,
16594 gen_rtx_fmt_ee (code, mode, op0, op1)));
16595 return mask;
16596 }
16597
16598 return NULL_RTX;
16599 }
16600
16601 /* Emit vector compare for operands OP0 and OP1 using code RCODE.
16602 DMODE is expected destination mode. This is a recursive function. */
16603
16604 static rtx
16605 rs6000_emit_vector_compare (enum rtx_code rcode,
16606 rtx op0, rtx op1,
16607 enum machine_mode dmode)
16608 {
16609 rtx mask;
16610 bool swap_operands = false;
16611 bool try_again = false;
16612
16613 gcc_assert (VECTOR_UNIT_ALTIVEC_OR_VSX_P (dmode));
16614 gcc_assert (GET_MODE (op0) == GET_MODE (op1));
16615
16616 /* See if the comparison works as is. */
16617 mask = rs6000_emit_vector_compare_inner (rcode, op0, op1);
16618 if (mask)
16619 return mask;
16620
16621 switch (rcode)
16622 {
16623 case LT:
16624 rcode = GT;
16625 swap_operands = true;
16626 try_again = true;
16627 break;
16628 case LTU:
16629 rcode = GTU;
16630 swap_operands = true;
16631 try_again = true;
16632 break;
16633 case NE:
16634 case UNLE:
16635 case UNLT:
16636 case UNGE:
16637 case UNGT:
16638 /* Invert condition and try again.
16639 e.g., A != B becomes ~(A==B). */
16640 {
16641 enum rtx_code rev_code;
16642 enum insn_code nor_code;
16643 rtx mask2;
16644
16645 rev_code = reverse_condition_maybe_unordered (rcode);
16646 if (rev_code == UNKNOWN)
16647 return NULL_RTX;
16648
16649 nor_code = optab_handler (one_cmpl_optab, dmode);
16650 if (nor_code == CODE_FOR_nothing)
16651 return NULL_RTX;
16652
16653 mask2 = rs6000_emit_vector_compare (rev_code, op0, op1, dmode);
16654 if (!mask2)
16655 return NULL_RTX;
16656
16657 mask = gen_reg_rtx (dmode);
16658 emit_insn (GEN_FCN (nor_code) (mask, mask2));
16659 return mask;
16660 }
16661 break;
16662 case GE:
16663 case GEU:
16664 case LE:
16665 case LEU:
16666 /* Try GT/GTU/LT/LTU OR EQ */
16667 {
16668 rtx c_rtx, eq_rtx;
16669 enum insn_code ior_code;
16670 enum rtx_code new_code;
16671
16672 switch (rcode)
16673 {
16674 case GE:
16675 new_code = GT;
16676 break;
16677
16678 case GEU:
16679 new_code = GTU;
16680 break;
16681
16682 case LE:
16683 new_code = LT;
16684 break;
16685
16686 case LEU:
16687 new_code = LTU;
16688 break;
16689
16690 default:
16691 gcc_unreachable ();
16692 }
16693
16694 ior_code = optab_handler (ior_optab, dmode);
16695 if (ior_code == CODE_FOR_nothing)
16696 return NULL_RTX;
16697
16698 c_rtx = rs6000_emit_vector_compare (new_code, op0, op1, dmode);
16699 if (!c_rtx)
16700 return NULL_RTX;
16701
16702 eq_rtx = rs6000_emit_vector_compare (EQ, op0, op1, dmode);
16703 if (!eq_rtx)
16704 return NULL_RTX;
16705
16706 mask = gen_reg_rtx (dmode);
16707 emit_insn (GEN_FCN (ior_code) (mask, c_rtx, eq_rtx));
16708 return mask;
16709 }
16710 break;
16711 default:
16712 return NULL_RTX;
16713 }
16714
16715 if (try_again)
16716 {
16717 if (swap_operands)
16718 {
16719 rtx tmp;
16720 tmp = op0;
16721 op0 = op1;
16722 op1 = tmp;
16723 }
16724
16725 mask = rs6000_emit_vector_compare_inner (rcode, op0, op1);
16726 if (mask)
16727 return mask;
16728 }
16729
16730 /* You only get two chances. */
16731 return NULL_RTX;
16732 }
16733
16734 /* Emit vector conditional expression. DEST is destination. OP_TRUE and
16735 OP_FALSE are two VEC_COND_EXPR operands. CC_OP0 and CC_OP1 are the two
16736 operands for the relation operation COND. */
16737
16738 int
16739 rs6000_emit_vector_cond_expr (rtx dest, rtx op_true, rtx op_false,
16740 rtx cond, rtx cc_op0, rtx cc_op1)
16741 {
16742 enum machine_mode dest_mode = GET_MODE (dest);
16743 enum rtx_code rcode = GET_CODE (cond);
16744 enum machine_mode cc_mode = CCmode;
16745 rtx mask;
16746 rtx cond2;
16747 rtx tmp;
16748 bool invert_move = false;
16749
16750 if (VECTOR_UNIT_NONE_P (dest_mode))
16751 return 0;
16752
16753 switch (rcode)
16754 {
16755 /* Swap operands if we can, and fall back to doing the operation as
16756 specified, and doing a NOR to invert the test. */
16757 case NE:
16758 case UNLE:
16759 case UNLT:
16760 case UNGE:
16761 case UNGT:
16762 /* Invert condition and try again.
16763 e.g., A = (B != C) ? D : E becomes A = (B == C) ? E : D. */
16764 invert_move = true;
16765 rcode = reverse_condition_maybe_unordered (rcode);
16766 if (rcode == UNKNOWN)
16767 return 0;
16768 break;
16769
16770 /* Mark unsigned tests with CCUNSmode. */
16771 case GTU:
16772 case GEU:
16773 case LTU:
16774 case LEU:
16775 cc_mode = CCUNSmode;
16776 break;
16777
16778 default:
16779 break;
16780 }
16781
16782 /* Get the vector mask for the given relational operations. */
16783 mask = rs6000_emit_vector_compare (rcode, cc_op0, cc_op1, dest_mode);
16784
16785 if (!mask)
16786 return 0;
16787
16788 if (invert_move)
16789 {
16790 tmp = op_true;
16791 op_true = op_false;
16792 op_false = tmp;
16793 }
16794
16795 cond2 = gen_rtx_fmt_ee (NE, cc_mode, mask, const0_rtx);
16796 emit_insn (gen_rtx_SET (VOIDmode,
16797 dest,
16798 gen_rtx_IF_THEN_ELSE (dest_mode,
16799 cond2,
16800 op_true,
16801 op_false)));
16802 return 1;
16803 }
16804
16805 /* Emit a conditional move: move TRUE_COND to DEST if OP of the
16806 operands of the last comparison is nonzero/true, FALSE_COND if it
16807 is zero/false. Return 0 if the hardware has no such operation. */
16808
16809 int
16810 rs6000_emit_cmove (rtx dest, rtx op, rtx true_cond, rtx false_cond)
16811 {
16812 enum rtx_code code = GET_CODE (op);
16813 rtx op0 = XEXP (op, 0);
16814 rtx op1 = XEXP (op, 1);
16815 REAL_VALUE_TYPE c1;
16816 enum machine_mode compare_mode = GET_MODE (op0);
16817 enum machine_mode result_mode = GET_MODE (dest);
16818 rtx temp;
16819 bool is_against_zero;
16820
16821 /* These modes should always match. */
16822 if (GET_MODE (op1) != compare_mode
16823 /* In the isel case however, we can use a compare immediate, so
16824 op1 may be a small constant. */
16825 && (!TARGET_ISEL || !short_cint_operand (op1, VOIDmode)))
16826 return 0;
16827 if (GET_MODE (true_cond) != result_mode)
16828 return 0;
16829 if (GET_MODE (false_cond) != result_mode)
16830 return 0;
16831
16832 /* First, work out if the hardware can do this at all, or
16833 if it's too slow.... */
16834 if (!FLOAT_MODE_P (compare_mode))
16835 {
16836 if (TARGET_ISEL)
16837 return rs6000_emit_int_cmove (dest, op, true_cond, false_cond);
16838 return 0;
16839 }
16840 else if (TARGET_HARD_FLOAT && !TARGET_FPRS
16841 && SCALAR_FLOAT_MODE_P (compare_mode))
16842 return 0;
16843
16844 is_against_zero = op1 == CONST0_RTX (compare_mode);
16845
16846 /* A floating-point subtract might overflow, underflow, or produce
16847 an inexact result, thus changing the floating-point flags, so it
16848 can't be generated if we care about that. It's safe if one side
16849 of the construct is zero, since then no subtract will be
16850 generated. */
16851 if (SCALAR_FLOAT_MODE_P (compare_mode)
16852 && flag_trapping_math && ! is_against_zero)
16853 return 0;
16854
16855 /* Eliminate half of the comparisons by switching operands, this
16856 makes the remaining code simpler. */
16857 if (code == UNLT || code == UNGT || code == UNORDERED || code == NE
16858 || code == LTGT || code == LT || code == UNLE)
16859 {
16860 code = reverse_condition_maybe_unordered (code);
16861 temp = true_cond;
16862 true_cond = false_cond;
16863 false_cond = temp;
16864 }
16865
16866 /* UNEQ and LTGT take four instructions for a comparison with zero,
16867 it'll probably be faster to use a branch here too. */
16868 if (code == UNEQ && HONOR_NANS (compare_mode))
16869 return 0;
16870
16871 if (GET_CODE (op1) == CONST_DOUBLE)
16872 REAL_VALUE_FROM_CONST_DOUBLE (c1, op1);
16873
16874 /* We're going to try to implement comparisons by performing
16875 a subtract, then comparing against zero. Unfortunately,
16876 Inf - Inf is NaN which is not zero, and so if we don't
16877 know that the operand is finite and the comparison
16878 would treat EQ different to UNORDERED, we can't do it. */
16879 if (HONOR_INFINITIES (compare_mode)
16880 && code != GT && code != UNGE
16881 && (GET_CODE (op1) != CONST_DOUBLE || real_isinf (&c1))
16882 /* Constructs of the form (a OP b ? a : b) are safe. */
16883 && ((! rtx_equal_p (op0, false_cond) && ! rtx_equal_p (op1, false_cond))
16884 || (! rtx_equal_p (op0, true_cond)
16885 && ! rtx_equal_p (op1, true_cond))))
16886 return 0;
16887
16888 /* At this point we know we can use fsel. */
16889
16890 /* Reduce the comparison to a comparison against zero. */
16891 if (! is_against_zero)
16892 {
16893 temp = gen_reg_rtx (compare_mode);
16894 emit_insn (gen_rtx_SET (VOIDmode, temp,
16895 gen_rtx_MINUS (compare_mode, op0, op1)));
16896 op0 = temp;
16897 op1 = CONST0_RTX (compare_mode);
16898 }
16899
16900 /* If we don't care about NaNs we can reduce some of the comparisons
16901 down to faster ones. */
16902 if (! HONOR_NANS (compare_mode))
16903 switch (code)
16904 {
16905 case GT:
16906 code = LE;
16907 temp = true_cond;
16908 true_cond = false_cond;
16909 false_cond = temp;
16910 break;
16911 case UNGE:
16912 code = GE;
16913 break;
16914 case UNEQ:
16915 code = EQ;
16916 break;
16917 default:
16918 break;
16919 }
16920
16921 /* Now, reduce everything down to a GE. */
16922 switch (code)
16923 {
16924 case GE:
16925 break;
16926
16927 case LE:
16928 temp = gen_reg_rtx (compare_mode);
16929 emit_insn (gen_rtx_SET (VOIDmode, temp, gen_rtx_NEG (compare_mode, op0)));
16930 op0 = temp;
16931 break;
16932
16933 case ORDERED:
16934 temp = gen_reg_rtx (compare_mode);
16935 emit_insn (gen_rtx_SET (VOIDmode, temp, gen_rtx_ABS (compare_mode, op0)));
16936 op0 = temp;
16937 break;
16938
16939 case EQ:
16940 temp = gen_reg_rtx (compare_mode);
16941 emit_insn (gen_rtx_SET (VOIDmode, temp,
16942 gen_rtx_NEG (compare_mode,
16943 gen_rtx_ABS (compare_mode, op0))));
16944 op0 = temp;
16945 break;
16946
16947 case UNGE:
16948 /* a UNGE 0 <-> (a GE 0 || -a UNLT 0) */
16949 temp = gen_reg_rtx (result_mode);
16950 emit_insn (gen_rtx_SET (VOIDmode, temp,
16951 gen_rtx_IF_THEN_ELSE (result_mode,
16952 gen_rtx_GE (VOIDmode,
16953 op0, op1),
16954 true_cond, false_cond)));
16955 false_cond = true_cond;
16956 true_cond = temp;
16957
16958 temp = gen_reg_rtx (compare_mode);
16959 emit_insn (gen_rtx_SET (VOIDmode, temp, gen_rtx_NEG (compare_mode, op0)));
16960 op0 = temp;
16961 break;
16962
16963 case GT:
16964 /* a GT 0 <-> (a GE 0 && -a UNLT 0) */
16965 temp = gen_reg_rtx (result_mode);
16966 emit_insn (gen_rtx_SET (VOIDmode, temp,
16967 gen_rtx_IF_THEN_ELSE (result_mode,
16968 gen_rtx_GE (VOIDmode,
16969 op0, op1),
16970 true_cond, false_cond)));
16971 true_cond = false_cond;
16972 false_cond = temp;
16973
16974 temp = gen_reg_rtx (compare_mode);
16975 emit_insn (gen_rtx_SET (VOIDmode, temp, gen_rtx_NEG (compare_mode, op0)));
16976 op0 = temp;
16977 break;
16978
16979 default:
16980 gcc_unreachable ();
16981 }
16982
16983 emit_insn (gen_rtx_SET (VOIDmode, dest,
16984 gen_rtx_IF_THEN_ELSE (result_mode,
16985 gen_rtx_GE (VOIDmode,
16986 op0, op1),
16987 true_cond, false_cond)));
16988 return 1;
16989 }
16990
16991 /* Same as above, but for ints (isel). */
16992
16993 static int
16994 rs6000_emit_int_cmove (rtx dest, rtx op, rtx true_cond, rtx false_cond)
16995 {
16996 rtx condition_rtx, cr;
16997 enum machine_mode mode = GET_MODE (dest);
16998 enum rtx_code cond_code;
16999 rtx (*isel_func) (rtx, rtx, rtx, rtx, rtx);
17000 bool signedp;
17001
17002 if (mode != SImode && (!TARGET_POWERPC64 || mode != DImode))
17003 return 0;
17004
17005 /* We still have to do the compare, because isel doesn't do a
17006 compare, it just looks at the CRx bits set by a previous compare
17007 instruction. */
17008 condition_rtx = rs6000_generate_compare (op, mode);
17009 cond_code = GET_CODE (condition_rtx);
17010 cr = XEXP (condition_rtx, 0);
17011 signedp = GET_MODE (cr) == CCmode;
17012
17013 isel_func = (mode == SImode
17014 ? (signedp ? gen_isel_signed_si : gen_isel_unsigned_si)
17015 : (signedp ? gen_isel_signed_di : gen_isel_unsigned_di));
17016
17017 switch (cond_code)
17018 {
17019 case LT: case GT: case LTU: case GTU: case EQ:
17020 /* isel handles these directly. */
17021 break;
17022
17023 default:
17024 /* We need to swap the sense of the comparison. */
17025 {
17026 rtx t = true_cond;
17027 true_cond = false_cond;
17028 false_cond = t;
17029 PUT_CODE (condition_rtx, reverse_condition (cond_code));
17030 }
17031 break;
17032 }
17033
17034 false_cond = force_reg (mode, false_cond);
17035 if (true_cond != const0_rtx)
17036 true_cond = force_reg (mode, true_cond);
17037
17038 emit_insn (isel_func (dest, condition_rtx, true_cond, false_cond, cr));
17039
17040 return 1;
17041 }
17042
17043 const char *
17044 output_isel (rtx *operands)
17045 {
17046 enum rtx_code code;
17047
17048 code = GET_CODE (operands[1]);
17049
17050 gcc_assert (!(code == GE || code == GEU || code == LE || code == LEU || code == NE));
17051
17052 return "isel %0,%2,%3,%j1";
17053 }
17054
17055 void
17056 rs6000_emit_minmax (rtx dest, enum rtx_code code, rtx op0, rtx op1)
17057 {
17058 enum machine_mode mode = GET_MODE (op0);
17059 enum rtx_code c;
17060 rtx target;
17061
17062 /* VSX/altivec have direct min/max insns. */
17063 if ((code == SMAX || code == SMIN) && VECTOR_UNIT_ALTIVEC_OR_VSX_P (mode))
17064 {
17065 emit_insn (gen_rtx_SET (VOIDmode,
17066 dest,
17067 gen_rtx_fmt_ee (code, mode, op0, op1)));
17068 return;
17069 }
17070
17071 if (code == SMAX || code == SMIN)
17072 c = GE;
17073 else
17074 c = GEU;
17075
17076 if (code == SMAX || code == UMAX)
17077 target = emit_conditional_move (dest, c, op0, op1, mode,
17078 op0, op1, mode, 0);
17079 else
17080 target = emit_conditional_move (dest, c, op0, op1, mode,
17081 op1, op0, mode, 0);
17082 gcc_assert (target);
17083 if (target != dest)
17084 emit_move_insn (dest, target);
17085 }
17086
17087 /* Emit instructions to perform a load-reserved/store-conditional operation.
17088 The operation performed is an atomic
17089 (set M (CODE:MODE M OP))
17090 If not NULL, BEFORE is atomically set to M before the operation, and
17091 AFTER is set to M after the operation (that is, (CODE:MODE M OP)).
17092 If SYNC_P then a memory barrier is emitted before the operation.
17093 Either OP or M may be wrapped in a NOT operation. */
17094
17095 void
17096 rs6000_emit_sync (enum rtx_code code, enum machine_mode mode,
17097 rtx m, rtx op, rtx before_param, rtx after_param,
17098 bool sync_p)
17099 {
17100 enum machine_mode used_mode;
17101 rtx the_op, set_before, set_after, set_atomic, cc_scratch, before, after;
17102 rtx used_m;
17103 rtvec vec;
17104 HOST_WIDE_INT imask = GET_MODE_MASK (mode);
17105 rtx shift = NULL_RTX;
17106
17107 if (sync_p)
17108 emit_insn (gen_lwsync ());
17109
17110 used_m = m;
17111
17112 /* If this is smaller than SImode, we'll have to use SImode with
17113 adjustments. */
17114 if (mode == QImode || mode == HImode)
17115 {
17116 rtx newop, oldop;
17117
17118 if (MEM_ALIGN (used_m) >= 32)
17119 {
17120 int ishift = 0;
17121 if (BYTES_BIG_ENDIAN)
17122 ishift = GET_MODE_BITSIZE (SImode) - GET_MODE_BITSIZE (mode);
17123
17124 shift = GEN_INT (ishift);
17125 used_m = change_address (used_m, SImode, 0);
17126 }
17127 else
17128 {
17129 rtx addrSI, aligned_addr;
17130 int shift_mask = mode == QImode ? 0x18 : 0x10;
17131
17132 addrSI = gen_lowpart_common (SImode,
17133 force_reg (Pmode, XEXP (used_m, 0)));
17134 addrSI = force_reg (SImode, addrSI);
17135 shift = gen_reg_rtx (SImode);
17136
17137 emit_insn (gen_rlwinm (shift, addrSI, GEN_INT (3),
17138 GEN_INT (shift_mask)));
17139 emit_insn (gen_xorsi3 (shift, shift, GEN_INT (shift_mask)));
17140
17141 aligned_addr = expand_binop (Pmode, and_optab,
17142 XEXP (used_m, 0),
17143 GEN_INT (-4), NULL_RTX,
17144 1, OPTAB_LIB_WIDEN);
17145 used_m = change_address (used_m, SImode, aligned_addr);
17146 set_mem_align (used_m, 32);
17147 }
17148 /* It's safe to keep the old alias set of USED_M, because
17149 the operation is atomic and only affects the original
17150 USED_M. */
17151 m = used_m;
17152
17153 if (GET_CODE (op) == NOT)
17154 {
17155 oldop = lowpart_subreg (SImode, XEXP (op, 0), mode);
17156 oldop = gen_rtx_NOT (SImode, oldop);
17157 }
17158 else
17159 oldop = lowpart_subreg (SImode, op, mode);
17160
17161 switch (code)
17162 {
17163 case IOR:
17164 case XOR:
17165 newop = expand_binop (SImode, and_optab,
17166 oldop, GEN_INT (imask), NULL_RTX,
17167 1, OPTAB_LIB_WIDEN);
17168 emit_insn (gen_ashlsi3 (newop, newop, shift));
17169 break;
17170
17171 case NOT: /* NAND */
17172 newop = expand_binop (SImode, ior_optab,
17173 oldop, GEN_INT (~imask), NULL_RTX,
17174 1, OPTAB_LIB_WIDEN);
17175 emit_insn (gen_rotlsi3 (newop, newop, shift));
17176 break;
17177
17178 case AND:
17179 newop = expand_binop (SImode, ior_optab,
17180 oldop, GEN_INT (~imask), NULL_RTX,
17181 1, OPTAB_LIB_WIDEN);
17182 emit_insn (gen_rotlsi3 (newop, newop, shift));
17183 break;
17184
17185 case PLUS:
17186 case MINUS:
17187 {
17188 rtx mask;
17189
17190 newop = expand_binop (SImode, and_optab,
17191 oldop, GEN_INT (imask), NULL_RTX,
17192 1, OPTAB_LIB_WIDEN);
17193 emit_insn (gen_ashlsi3 (newop, newop, shift));
17194
17195 mask = gen_reg_rtx (SImode);
17196 emit_move_insn (mask, GEN_INT (imask));
17197 emit_insn (gen_ashlsi3 (mask, mask, shift));
17198
17199 if (code == PLUS)
17200 newop = gen_rtx_PLUS (SImode, m, newop);
17201 else
17202 newop = gen_rtx_MINUS (SImode, m, newop);
17203 newop = gen_rtx_AND (SImode, newop, mask);
17204 newop = gen_rtx_IOR (SImode, newop,
17205 gen_rtx_AND (SImode,
17206 gen_rtx_NOT (SImode, mask),
17207 m));
17208 break;
17209 }
17210
17211 default:
17212 gcc_unreachable ();
17213 }
17214
17215 op = newop;
17216 used_mode = SImode;
17217 before = gen_reg_rtx (used_mode);
17218 after = gen_reg_rtx (used_mode);
17219 }
17220 else
17221 {
17222 used_mode = mode;
17223 before = before_param;
17224 after = after_param;
17225
17226 if (before == NULL_RTX)
17227 before = gen_reg_rtx (used_mode);
17228 if (after == NULL_RTX)
17229 after = gen_reg_rtx (used_mode);
17230 }
17231
17232 if ((code == PLUS || code == MINUS)
17233 && used_mode != mode)
17234 the_op = op; /* Computed above. */
17235 else if (GET_CODE (op) == NOT && GET_CODE (m) != NOT)
17236 the_op = gen_rtx_fmt_ee (code, used_mode, op, m);
17237 else if (code == NOT)
17238 the_op = gen_rtx_fmt_ee (IOR, used_mode,
17239 gen_rtx_NOT (used_mode, m),
17240 gen_rtx_NOT (used_mode, op));
17241 else
17242 the_op = gen_rtx_fmt_ee (code, used_mode, m, op);
17243
17244 set_after = gen_rtx_SET (VOIDmode, after, the_op);
17245 set_before = gen_rtx_SET (VOIDmode, before, used_m);
17246 set_atomic = gen_rtx_SET (VOIDmode, used_m,
17247 gen_rtx_UNSPEC (used_mode,
17248 gen_rtvec (1, the_op),
17249 UNSPEC_SYNC_OP));
17250 cc_scratch = gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (CCmode));
17251
17252 if ((code == PLUS || code == MINUS) && used_mode != mode)
17253 vec = gen_rtvec (5, set_after, set_before, set_atomic, cc_scratch,
17254 gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (SImode)));
17255 else
17256 vec = gen_rtvec (4, set_after, set_before, set_atomic, cc_scratch);
17257 emit_insn (gen_rtx_PARALLEL (VOIDmode, vec));
17258
17259 /* Shift and mask the return values properly. */
17260 if (used_mode != mode && before_param)
17261 {
17262 emit_insn (gen_lshrsi3 (before, before, shift));
17263 convert_move (before_param, before, 1);
17264 }
17265
17266 if (used_mode != mode && after_param)
17267 {
17268 emit_insn (gen_lshrsi3 (after, after, shift));
17269 convert_move (after_param, after, 1);
17270 }
17271
17272 /* The previous sequence will end with a branch that's dependent on
17273 the conditional store, so placing an isync will ensure that no
17274 other instructions (especially, no load or store instructions)
17275 can start before the atomic operation completes. */
17276 if (sync_p)
17277 emit_insn (gen_isync ());
17278 }
17279
17280 /* A subroutine of the atomic operation splitters. Jump to LABEL if
17281 COND is true. Mark the jump as unlikely to be taken. */
17282
17283 static void
17284 emit_unlikely_jump (rtx cond, rtx label)
17285 {
17286 rtx very_unlikely = GEN_INT (REG_BR_PROB_BASE / 100 - 1);
17287 rtx x;
17288
17289 x = gen_rtx_IF_THEN_ELSE (VOIDmode, cond, label, pc_rtx);
17290 x = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, x));
17291 add_reg_note (x, REG_BR_PROB, very_unlikely);
17292 }
17293
17294 /* A subroutine of the atomic operation splitters. Emit a load-locked
17295 instruction in MODE. */
17296
17297 static void
17298 emit_load_locked (enum machine_mode mode, rtx reg, rtx mem)
17299 {
17300 rtx (*fn) (rtx, rtx) = NULL;
17301 if (mode == SImode)
17302 fn = gen_load_locked_si;
17303 else if (mode == DImode)
17304 fn = gen_load_locked_di;
17305 emit_insn (fn (reg, mem));
17306 }
17307
17308 /* A subroutine of the atomic operation splitters. Emit a store-conditional
17309 instruction in MODE. */
17310
17311 static void
17312 emit_store_conditional (enum machine_mode mode, rtx res, rtx mem, rtx val)
17313 {
17314 rtx (*fn) (rtx, rtx, rtx) = NULL;
17315 if (mode == SImode)
17316 fn = gen_store_conditional_si;
17317 else if (mode == DImode)
17318 fn = gen_store_conditional_di;
17319
17320 /* Emit sync before stwcx. to address PPC405 Erratum. */
17321 if (PPC405_ERRATUM77)
17322 emit_insn (gen_memory_barrier ());
17323
17324 emit_insn (fn (res, mem, val));
17325 }
17326
17327 /* Expand an atomic fetch-and-operate pattern. CODE is the binary operation
17328 to perform. MEM is the memory on which to operate. VAL is the second
17329 operand of the binary operator. BEFORE and AFTER are optional locations to
17330 return the value of MEM either before of after the operation. SCRATCH is
17331 a scratch register. */
17332
17333 void
17334 rs6000_split_atomic_op (enum rtx_code code, rtx mem, rtx val,
17335 rtx before, rtx after, rtx scratch)
17336 {
17337 enum machine_mode mode = GET_MODE (mem);
17338 rtx label, x, cond = gen_rtx_REG (CCmode, CR0_REGNO);
17339
17340 emit_insn (gen_lwsync ());
17341
17342 label = gen_label_rtx ();
17343 emit_label (label);
17344 label = gen_rtx_LABEL_REF (VOIDmode, label);
17345
17346 if (before == NULL_RTX)
17347 before = scratch;
17348 emit_load_locked (mode, before, mem);
17349
17350 if (code == NOT)
17351 x = gen_rtx_IOR (mode,
17352 gen_rtx_NOT (mode, before),
17353 gen_rtx_NOT (mode, val));
17354 else if (code == AND)
17355 x = gen_rtx_UNSPEC (mode, gen_rtvec (2, before, val), UNSPEC_AND);
17356 else
17357 x = gen_rtx_fmt_ee (code, mode, before, val);
17358
17359 if (after != NULL_RTX)
17360 emit_insn (gen_rtx_SET (VOIDmode, after, copy_rtx (x)));
17361 emit_insn (gen_rtx_SET (VOIDmode, scratch, x));
17362
17363 emit_store_conditional (mode, cond, mem, scratch);
17364
17365 x = gen_rtx_NE (VOIDmode, cond, const0_rtx);
17366 emit_unlikely_jump (x, label);
17367
17368 emit_insn (gen_isync ());
17369 }
17370
17371 /* Expand an atomic compare and swap operation. MEM is the memory on which
17372 to operate. OLDVAL is the old value to be compared. NEWVAL is the new
17373 value to be stored. SCRATCH is a scratch GPR. */
17374
17375 void
17376 rs6000_split_compare_and_swap (rtx retval, rtx mem, rtx oldval, rtx newval,
17377 rtx scratch)
17378 {
17379 enum machine_mode mode = GET_MODE (mem);
17380 rtx label1, label2, x, cond = gen_rtx_REG (CCmode, CR0_REGNO);
17381
17382 emit_insn (gen_lwsync ());
17383
17384 label1 = gen_rtx_LABEL_REF (VOIDmode, gen_label_rtx ());
17385 label2 = gen_rtx_LABEL_REF (VOIDmode, gen_label_rtx ());
17386 emit_label (XEXP (label1, 0));
17387
17388 emit_load_locked (mode, retval, mem);
17389
17390 x = gen_rtx_COMPARE (CCmode, retval, oldval);
17391 emit_insn (gen_rtx_SET (VOIDmode, cond, x));
17392
17393 x = gen_rtx_NE (VOIDmode, cond, const0_rtx);
17394 emit_unlikely_jump (x, label2);
17395
17396 emit_move_insn (scratch, newval);
17397 emit_store_conditional (mode, cond, mem, scratch);
17398
17399 x = gen_rtx_NE (VOIDmode, cond, const0_rtx);
17400 emit_unlikely_jump (x, label1);
17401
17402 emit_insn (gen_isync ());
17403 emit_label (XEXP (label2, 0));
17404 }
17405
17406 /* Expand an atomic test and set operation. MEM is the memory on which
17407 to operate. VAL is the value set. SCRATCH is a scratch GPR. */
17408
17409 void
17410 rs6000_split_lock_test_and_set (rtx retval, rtx mem, rtx val, rtx scratch)
17411 {
17412 enum machine_mode mode = GET_MODE (mem);
17413 rtx label, x, cond = gen_rtx_REG (CCmode, CR0_REGNO);
17414
17415 label = gen_rtx_LABEL_REF (VOIDmode, gen_label_rtx ());
17416 emit_label (XEXP (label, 0));
17417
17418 emit_load_locked (mode, retval, mem);
17419 emit_move_insn (scratch, val);
17420 emit_store_conditional (mode, cond, mem, scratch);
17421
17422 x = gen_rtx_NE (VOIDmode, cond, const0_rtx);
17423 emit_unlikely_jump (x, label);
17424
17425 emit_insn (gen_isync ());
17426 }
17427
17428 void
17429 rs6000_expand_compare_and_swapqhi (rtx dst, rtx mem, rtx oldval, rtx newval)
17430 {
17431 enum machine_mode mode = GET_MODE (mem);
17432 rtx addrSI, align, wdst, shift, mask;
17433 HOST_WIDE_INT shift_mask = mode == QImode ? 0x18 : 0x10;
17434 HOST_WIDE_INT imask = GET_MODE_MASK (mode);
17435
17436 /* Shift amount for subword relative to aligned word. */
17437 addrSI = force_reg (GET_MODE (XEXP (mem, 0)), XEXP (mem, 0));
17438 addrSI = force_reg (SImode, gen_lowpart_common (SImode, addrSI));
17439 shift = gen_reg_rtx (SImode);
17440 emit_insn (gen_rlwinm (shift, addrSI, GEN_INT (3),
17441 GEN_INT (shift_mask)));
17442 emit_insn (gen_xorsi3 (shift, shift, GEN_INT (shift_mask)));
17443
17444 /* Shift and mask old value into position within word. */
17445 oldval = convert_modes (SImode, mode, oldval, 1);
17446 oldval = expand_binop (SImode, and_optab,
17447 oldval, GEN_INT (imask), NULL_RTX,
17448 1, OPTAB_LIB_WIDEN);
17449 emit_insn (gen_ashlsi3 (oldval, oldval, shift));
17450
17451 /* Shift and mask new value into position within word. */
17452 newval = convert_modes (SImode, mode, newval, 1);
17453 newval = expand_binop (SImode, and_optab,
17454 newval, GEN_INT (imask), NULL_RTX,
17455 1, OPTAB_LIB_WIDEN);
17456 emit_insn (gen_ashlsi3 (newval, newval, shift));
17457
17458 /* Mask for insertion. */
17459 mask = gen_reg_rtx (SImode);
17460 emit_move_insn (mask, GEN_INT (imask));
17461 emit_insn (gen_ashlsi3 (mask, mask, shift));
17462
17463 /* Address of aligned word containing subword. */
17464 align = expand_binop (Pmode, and_optab, XEXP (mem, 0), GEN_INT (-4),
17465 NULL_RTX, 1, OPTAB_LIB_WIDEN);
17466 mem = change_address (mem, SImode, align);
17467 set_mem_align (mem, 32);
17468 MEM_VOLATILE_P (mem) = 1;
17469
17470 wdst = gen_reg_rtx (SImode);
17471 emit_insn (gen_sync_compare_and_swapqhi_internal (wdst, mask,
17472 oldval, newval, mem));
17473
17474 /* Shift the result back. */
17475 emit_insn (gen_lshrsi3 (wdst, wdst, shift));
17476
17477 emit_move_insn (dst, gen_lowpart (mode, wdst));
17478 }
17479
17480 void
17481 rs6000_split_compare_and_swapqhi (rtx dest, rtx mask,
17482 rtx oldval, rtx newval, rtx mem,
17483 rtx scratch)
17484 {
17485 rtx label1, label2, x, cond = gen_rtx_REG (CCmode, CR0_REGNO);
17486
17487 emit_insn (gen_lwsync ());
17488 label1 = gen_rtx_LABEL_REF (VOIDmode, gen_label_rtx ());
17489 label2 = gen_rtx_LABEL_REF (VOIDmode, gen_label_rtx ());
17490 emit_label (XEXP (label1, 0));
17491
17492 emit_load_locked (SImode, scratch, mem);
17493
17494 /* Mask subword within loaded value for comparison with oldval.
17495 Use UNSPEC_AND to avoid clobber.*/
17496 emit_insn (gen_rtx_SET (SImode, dest,
17497 gen_rtx_UNSPEC (SImode,
17498 gen_rtvec (2, scratch, mask),
17499 UNSPEC_AND)));
17500
17501 x = gen_rtx_COMPARE (CCmode, dest, oldval);
17502 emit_insn (gen_rtx_SET (VOIDmode, cond, x));
17503
17504 x = gen_rtx_NE (VOIDmode, cond, const0_rtx);
17505 emit_unlikely_jump (x, label2);
17506
17507 /* Clear subword within loaded value for insertion of new value. */
17508 emit_insn (gen_rtx_SET (SImode, scratch,
17509 gen_rtx_AND (SImode,
17510 gen_rtx_NOT (SImode, mask), scratch)));
17511 emit_insn (gen_iorsi3 (scratch, scratch, newval));
17512 emit_store_conditional (SImode, cond, mem, scratch);
17513
17514 x = gen_rtx_NE (VOIDmode, cond, const0_rtx);
17515 emit_unlikely_jump (x, label1);
17516
17517 emit_insn (gen_isync ());
17518 emit_label (XEXP (label2, 0));
17519 }
17520
17521
17522 /* Emit instructions to move SRC to DST. Called by splitters for
17523 multi-register moves. It will emit at most one instruction for
17524 each register that is accessed; that is, it won't emit li/lis pairs
17525 (or equivalent for 64-bit code). One of SRC or DST must be a hard
17526 register. */
17527
17528 void
17529 rs6000_split_multireg_move (rtx dst, rtx src)
17530 {
17531 /* The register number of the first register being moved. */
17532 int reg;
17533 /* The mode that is to be moved. */
17534 enum machine_mode mode;
17535 /* The mode that the move is being done in, and its size. */
17536 enum machine_mode reg_mode;
17537 int reg_mode_size;
17538 /* The number of registers that will be moved. */
17539 int nregs;
17540
17541 reg = REG_P (dst) ? REGNO (dst) : REGNO (src);
17542 mode = GET_MODE (dst);
17543 nregs = hard_regno_nregs[reg][mode];
17544 if (FP_REGNO_P (reg))
17545 reg_mode = DECIMAL_FLOAT_MODE_P (mode) ? DDmode :
17546 ((TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT) ? DFmode : SFmode);
17547 else if (ALTIVEC_REGNO_P (reg))
17548 reg_mode = V16QImode;
17549 else if (TARGET_E500_DOUBLE && mode == TFmode)
17550 reg_mode = DFmode;
17551 else
17552 reg_mode = word_mode;
17553 reg_mode_size = GET_MODE_SIZE (reg_mode);
17554
17555 gcc_assert (reg_mode_size * nregs == GET_MODE_SIZE (mode));
17556
17557 if (REG_P (src) && REG_P (dst) && (REGNO (src) < REGNO (dst)))
17558 {
17559 /* Move register range backwards, if we might have destructive
17560 overlap. */
17561 int i;
17562 for (i = nregs - 1; i >= 0; i--)
17563 emit_insn (gen_rtx_SET (VOIDmode,
17564 simplify_gen_subreg (reg_mode, dst, mode,
17565 i * reg_mode_size),
17566 simplify_gen_subreg (reg_mode, src, mode,
17567 i * reg_mode_size)));
17568 }
17569 else
17570 {
17571 int i;
17572 int j = -1;
17573 bool used_update = false;
17574 rtx restore_basereg = NULL_RTX;
17575
17576 if (MEM_P (src) && INT_REGNO_P (reg))
17577 {
17578 rtx breg;
17579
17580 if (GET_CODE (XEXP (src, 0)) == PRE_INC
17581 || GET_CODE (XEXP (src, 0)) == PRE_DEC)
17582 {
17583 rtx delta_rtx;
17584 breg = XEXP (XEXP (src, 0), 0);
17585 delta_rtx = (GET_CODE (XEXP (src, 0)) == PRE_INC
17586 ? GEN_INT (GET_MODE_SIZE (GET_MODE (src)))
17587 : GEN_INT (-GET_MODE_SIZE (GET_MODE (src))));
17588 emit_insn (gen_add3_insn (breg, breg, delta_rtx));
17589 src = replace_equiv_address (src, breg);
17590 }
17591 else if (! rs6000_offsettable_memref_p (src))
17592 {
17593 if (GET_CODE (XEXP (src, 0)) == PRE_MODIFY)
17594 {
17595 rtx basereg = XEXP (XEXP (src, 0), 0);
17596 if (TARGET_UPDATE)
17597 {
17598 rtx ndst = simplify_gen_subreg (reg_mode, dst, mode, 0);
17599 emit_insn (gen_rtx_SET (VOIDmode, ndst,
17600 gen_rtx_MEM (reg_mode, XEXP (src, 0))));
17601 used_update = true;
17602 }
17603 else
17604 emit_insn (gen_rtx_SET (VOIDmode, basereg,
17605 XEXP (XEXP (src, 0), 1)));
17606 src = replace_equiv_address (src, basereg);
17607 }
17608 else
17609 {
17610 rtx basereg = gen_rtx_REG (Pmode, reg);
17611 emit_insn (gen_rtx_SET (VOIDmode, basereg, XEXP (src, 0)));
17612 src = replace_equiv_address (src, basereg);
17613 }
17614 }
17615
17616 breg = XEXP (src, 0);
17617 if (GET_CODE (breg) == PLUS || GET_CODE (breg) == LO_SUM)
17618 breg = XEXP (breg, 0);
17619
17620 /* If the base register we are using to address memory is
17621 also a destination reg, then change that register last. */
17622 if (REG_P (breg)
17623 && REGNO (breg) >= REGNO (dst)
17624 && REGNO (breg) < REGNO (dst) + nregs)
17625 j = REGNO (breg) - REGNO (dst);
17626 }
17627 else if (MEM_P (dst) && INT_REGNO_P (reg))
17628 {
17629 rtx breg;
17630
17631 if (GET_CODE (XEXP (dst, 0)) == PRE_INC
17632 || GET_CODE (XEXP (dst, 0)) == PRE_DEC)
17633 {
17634 rtx delta_rtx;
17635 breg = XEXP (XEXP (dst, 0), 0);
17636 delta_rtx = (GET_CODE (XEXP (dst, 0)) == PRE_INC
17637 ? GEN_INT (GET_MODE_SIZE (GET_MODE (dst)))
17638 : GEN_INT (-GET_MODE_SIZE (GET_MODE (dst))));
17639
17640 /* We have to update the breg before doing the store.
17641 Use store with update, if available. */
17642
17643 if (TARGET_UPDATE)
17644 {
17645 rtx nsrc = simplify_gen_subreg (reg_mode, src, mode, 0);
17646 emit_insn (TARGET_32BIT
17647 ? (TARGET_POWERPC64
17648 ? gen_movdi_si_update (breg, breg, delta_rtx, nsrc)
17649 : gen_movsi_update (breg, breg, delta_rtx, nsrc))
17650 : gen_movdi_di_update (breg, breg, delta_rtx, nsrc));
17651 used_update = true;
17652 }
17653 else
17654 emit_insn (gen_add3_insn (breg, breg, delta_rtx));
17655 dst = replace_equiv_address (dst, breg);
17656 }
17657 else if (!rs6000_offsettable_memref_p (dst)
17658 && GET_CODE (XEXP (dst, 0)) != LO_SUM)
17659 {
17660 if (GET_CODE (XEXP (dst, 0)) == PRE_MODIFY)
17661 {
17662 rtx basereg = XEXP (XEXP (dst, 0), 0);
17663 if (TARGET_UPDATE)
17664 {
17665 rtx nsrc = simplify_gen_subreg (reg_mode, src, mode, 0);
17666 emit_insn (gen_rtx_SET (VOIDmode,
17667 gen_rtx_MEM (reg_mode, XEXP (dst, 0)), nsrc));
17668 used_update = true;
17669 }
17670 else
17671 emit_insn (gen_rtx_SET (VOIDmode, basereg,
17672 XEXP (XEXP (dst, 0), 1)));
17673 dst = replace_equiv_address (dst, basereg);
17674 }
17675 else
17676 {
17677 rtx basereg = XEXP (XEXP (dst, 0), 0);
17678 rtx offsetreg = XEXP (XEXP (dst, 0), 1);
17679 gcc_assert (GET_CODE (XEXP (dst, 0)) == PLUS
17680 && REG_P (basereg)
17681 && REG_P (offsetreg)
17682 && REGNO (basereg) != REGNO (offsetreg));
17683 if (REGNO (basereg) == 0)
17684 {
17685 rtx tmp = offsetreg;
17686 offsetreg = basereg;
17687 basereg = tmp;
17688 }
17689 emit_insn (gen_add3_insn (basereg, basereg, offsetreg));
17690 restore_basereg = gen_sub3_insn (basereg, basereg, offsetreg);
17691 dst = replace_equiv_address (dst, basereg);
17692 }
17693 }
17694 else if (GET_CODE (XEXP (dst, 0)) != LO_SUM)
17695 gcc_assert (rs6000_offsettable_memref_p (dst));
17696 }
17697
17698 for (i = 0; i < nregs; i++)
17699 {
17700 /* Calculate index to next subword. */
17701 ++j;
17702 if (j == nregs)
17703 j = 0;
17704
17705 /* If compiler already emitted move of first word by
17706 store with update, no need to do anything. */
17707 if (j == 0 && used_update)
17708 continue;
17709
17710 emit_insn (gen_rtx_SET (VOIDmode,
17711 simplify_gen_subreg (reg_mode, dst, mode,
17712 j * reg_mode_size),
17713 simplify_gen_subreg (reg_mode, src, mode,
17714 j * reg_mode_size)));
17715 }
17716 if (restore_basereg != NULL_RTX)
17717 emit_insn (restore_basereg);
17718 }
17719 }
17720
17721 \f
17722 /* This page contains routines that are used to determine what the
17723 function prologue and epilogue code will do and write them out. */
17724
17725 /* Return the first fixed-point register that is required to be
17726 saved. 32 if none. */
17727
17728 int
17729 first_reg_to_save (void)
17730 {
17731 int first_reg;
17732
17733 /* Find lowest numbered live register. */
17734 for (first_reg = 13; first_reg <= 31; first_reg++)
17735 if (df_regs_ever_live_p (first_reg)
17736 && (! call_used_regs[first_reg]
17737 || (first_reg == RS6000_PIC_OFFSET_TABLE_REGNUM
17738 && ((DEFAULT_ABI == ABI_V4 && flag_pic != 0)
17739 || (DEFAULT_ABI == ABI_DARWIN && flag_pic)
17740 || (TARGET_TOC && TARGET_MINIMAL_TOC)))))
17741 break;
17742
17743 #if TARGET_MACHO
17744 if (flag_pic
17745 && crtl->uses_pic_offset_table
17746 && first_reg > RS6000_PIC_OFFSET_TABLE_REGNUM)
17747 return RS6000_PIC_OFFSET_TABLE_REGNUM;
17748 #endif
17749
17750 return first_reg;
17751 }
17752
17753 /* Similar, for FP regs. */
17754
17755 int
17756 first_fp_reg_to_save (void)
17757 {
17758 int first_reg;
17759
17760 /* Find lowest numbered live register. */
17761 for (first_reg = 14 + 32; first_reg <= 63; first_reg++)
17762 if (df_regs_ever_live_p (first_reg))
17763 break;
17764
17765 return first_reg;
17766 }
17767
17768 /* Similar, for AltiVec regs. */
17769
17770 static int
17771 first_altivec_reg_to_save (void)
17772 {
17773 int i;
17774
17775 /* Stack frame remains as is unless we are in AltiVec ABI. */
17776 if (! TARGET_ALTIVEC_ABI)
17777 return LAST_ALTIVEC_REGNO + 1;
17778
17779 /* On Darwin, the unwind routines are compiled without
17780 TARGET_ALTIVEC, and use save_world to save/restore the
17781 altivec registers when necessary. */
17782 if (DEFAULT_ABI == ABI_DARWIN && crtl->calls_eh_return
17783 && ! TARGET_ALTIVEC)
17784 return FIRST_ALTIVEC_REGNO + 20;
17785
17786 /* Find lowest numbered live register. */
17787 for (i = FIRST_ALTIVEC_REGNO + 20; i <= LAST_ALTIVEC_REGNO; ++i)
17788 if (df_regs_ever_live_p (i))
17789 break;
17790
17791 return i;
17792 }
17793
17794 /* Return a 32-bit mask of the AltiVec registers we need to set in
17795 VRSAVE. Bit n of the return value is 1 if Vn is live. The MSB in
17796 the 32-bit word is 0. */
17797
17798 static unsigned int
17799 compute_vrsave_mask (void)
17800 {
17801 unsigned int i, mask = 0;
17802
17803 /* On Darwin, the unwind routines are compiled without
17804 TARGET_ALTIVEC, and use save_world to save/restore the
17805 call-saved altivec registers when necessary. */
17806 if (DEFAULT_ABI == ABI_DARWIN && crtl->calls_eh_return
17807 && ! TARGET_ALTIVEC)
17808 mask |= 0xFFF;
17809
17810 /* First, find out if we use _any_ altivec registers. */
17811 for (i = FIRST_ALTIVEC_REGNO; i <= LAST_ALTIVEC_REGNO; ++i)
17812 if (df_regs_ever_live_p (i))
17813 mask |= ALTIVEC_REG_BIT (i);
17814
17815 if (mask == 0)
17816 return mask;
17817
17818 /* Next, remove the argument registers from the set. These must
17819 be in the VRSAVE mask set by the caller, so we don't need to add
17820 them in again. More importantly, the mask we compute here is
17821 used to generate CLOBBERs in the set_vrsave insn, and we do not
17822 wish the argument registers to die. */
17823 for (i = crtl->args.info.vregno - 1; i >= ALTIVEC_ARG_MIN_REG; --i)
17824 mask &= ~ALTIVEC_REG_BIT (i);
17825
17826 /* Similarly, remove the return value from the set. */
17827 {
17828 bool yes = false;
17829 diddle_return_value (is_altivec_return_reg, &yes);
17830 if (yes)
17831 mask &= ~ALTIVEC_REG_BIT (ALTIVEC_ARG_RETURN);
17832 }
17833
17834 return mask;
17835 }
17836
17837 /* For a very restricted set of circumstances, we can cut down the
17838 size of prologues/epilogues by calling our own save/restore-the-world
17839 routines. */
17840
17841 static void
17842 compute_save_world_info (rs6000_stack_t *info_ptr)
17843 {
17844 info_ptr->world_save_p = 1;
17845 info_ptr->world_save_p
17846 = (WORLD_SAVE_P (info_ptr)
17847 && DEFAULT_ABI == ABI_DARWIN
17848 && ! (cfun->calls_setjmp && flag_exceptions)
17849 && info_ptr->first_fp_reg_save == FIRST_SAVED_FP_REGNO
17850 && info_ptr->first_gp_reg_save == FIRST_SAVED_GP_REGNO
17851 && info_ptr->first_altivec_reg_save == FIRST_SAVED_ALTIVEC_REGNO
17852 && info_ptr->cr_save_p);
17853
17854 /* This will not work in conjunction with sibcalls. Make sure there
17855 are none. (This check is expensive, but seldom executed.) */
17856 if (WORLD_SAVE_P (info_ptr))
17857 {
17858 rtx insn;
17859 for ( insn = get_last_insn_anywhere (); insn; insn = PREV_INSN (insn))
17860 if ( GET_CODE (insn) == CALL_INSN
17861 && SIBLING_CALL_P (insn))
17862 {
17863 info_ptr->world_save_p = 0;
17864 break;
17865 }
17866 }
17867
17868 if (WORLD_SAVE_P (info_ptr))
17869 {
17870 /* Even if we're not touching VRsave, make sure there's room on the
17871 stack for it, if it looks like we're calling SAVE_WORLD, which
17872 will attempt to save it. */
17873 info_ptr->vrsave_size = 4;
17874
17875 /* If we are going to save the world, we need to save the link register too. */
17876 info_ptr->lr_save_p = 1;
17877
17878 /* "Save" the VRsave register too if we're saving the world. */
17879 if (info_ptr->vrsave_mask == 0)
17880 info_ptr->vrsave_mask = compute_vrsave_mask ();
17881
17882 /* Because the Darwin register save/restore routines only handle
17883 F14 .. F31 and V20 .. V31 as per the ABI, perform a consistency
17884 check. */
17885 gcc_assert (info_ptr->first_fp_reg_save >= FIRST_SAVED_FP_REGNO
17886 && (info_ptr->first_altivec_reg_save
17887 >= FIRST_SAVED_ALTIVEC_REGNO));
17888 }
17889 return;
17890 }
17891
17892
17893 static void
17894 is_altivec_return_reg (rtx reg, void *xyes)
17895 {
17896 bool *yes = (bool *) xyes;
17897 if (REGNO (reg) == ALTIVEC_ARG_RETURN)
17898 *yes = true;
17899 }
17900
17901 \f
17902 /* Calculate the stack information for the current function. This is
17903 complicated by having two separate calling sequences, the AIX calling
17904 sequence and the V.4 calling sequence.
17905
17906 AIX (and Darwin/Mac OS X) stack frames look like:
17907 32-bit 64-bit
17908 SP----> +---------------------------------------+
17909 | back chain to caller | 0 0
17910 +---------------------------------------+
17911 | saved CR | 4 8 (8-11)
17912 +---------------------------------------+
17913 | saved LR | 8 16
17914 +---------------------------------------+
17915 | reserved for compilers | 12 24
17916 +---------------------------------------+
17917 | reserved for binders | 16 32
17918 +---------------------------------------+
17919 | saved TOC pointer | 20 40
17920 +---------------------------------------+
17921 | Parameter save area (P) | 24 48
17922 +---------------------------------------+
17923 | Alloca space (A) | 24+P etc.
17924 +---------------------------------------+
17925 | Local variable space (L) | 24+P+A
17926 +---------------------------------------+
17927 | Float/int conversion temporary (X) | 24+P+A+L
17928 +---------------------------------------+
17929 | Save area for AltiVec registers (W) | 24+P+A+L+X
17930 +---------------------------------------+
17931 | AltiVec alignment padding (Y) | 24+P+A+L+X+W
17932 +---------------------------------------+
17933 | Save area for VRSAVE register (Z) | 24+P+A+L+X+W+Y
17934 +---------------------------------------+
17935 | Save area for GP registers (G) | 24+P+A+X+L+X+W+Y+Z
17936 +---------------------------------------+
17937 | Save area for FP registers (F) | 24+P+A+X+L+X+W+Y+Z+G
17938 +---------------------------------------+
17939 old SP->| back chain to caller's caller |
17940 +---------------------------------------+
17941
17942 The required alignment for AIX configurations is two words (i.e., 8
17943 or 16 bytes).
17944
17945
17946 V.4 stack frames look like:
17947
17948 SP----> +---------------------------------------+
17949 | back chain to caller | 0
17950 +---------------------------------------+
17951 | caller's saved LR | 4
17952 +---------------------------------------+
17953 | Parameter save area (P) | 8
17954 +---------------------------------------+
17955 | Alloca space (A) | 8+P
17956 +---------------------------------------+
17957 | Varargs save area (V) | 8+P+A
17958 +---------------------------------------+
17959 | Local variable space (L) | 8+P+A+V
17960 +---------------------------------------+
17961 | Float/int conversion temporary (X) | 8+P+A+V+L
17962 +---------------------------------------+
17963 | Save area for AltiVec registers (W) | 8+P+A+V+L+X
17964 +---------------------------------------+
17965 | AltiVec alignment padding (Y) | 8+P+A+V+L+X+W
17966 +---------------------------------------+
17967 | Save area for VRSAVE register (Z) | 8+P+A+V+L+X+W+Y
17968 +---------------------------------------+
17969 | SPE: area for 64-bit GP registers |
17970 +---------------------------------------+
17971 | SPE alignment padding |
17972 +---------------------------------------+
17973 | saved CR (C) | 8+P+A+V+L+X+W+Y+Z
17974 +---------------------------------------+
17975 | Save area for GP registers (G) | 8+P+A+V+L+X+W+Y+Z+C
17976 +---------------------------------------+
17977 | Save area for FP registers (F) | 8+P+A+V+L+X+W+Y+Z+C+G
17978 +---------------------------------------+
17979 old SP->| back chain to caller's caller |
17980 +---------------------------------------+
17981
17982 The required alignment for V.4 is 16 bytes, or 8 bytes if -meabi is
17983 given. (But note below and in sysv4.h that we require only 8 and
17984 may round up the size of our stack frame anyways. The historical
17985 reason is early versions of powerpc-linux which didn't properly
17986 align the stack at program startup. A happy side-effect is that
17987 -mno-eabi libraries can be used with -meabi programs.)
17988
17989 The EABI configuration defaults to the V.4 layout. However,
17990 the stack alignment requirements may differ. If -mno-eabi is not
17991 given, the required stack alignment is 8 bytes; if -mno-eabi is
17992 given, the required alignment is 16 bytes. (But see V.4 comment
17993 above.) */
17994
17995 #ifndef ABI_STACK_BOUNDARY
17996 #define ABI_STACK_BOUNDARY STACK_BOUNDARY
17997 #endif
17998
17999 static rs6000_stack_t *
18000 rs6000_stack_info (void)
18001 {
18002 static rs6000_stack_t info;
18003 rs6000_stack_t *info_ptr = &info;
18004 int reg_size = TARGET_32BIT ? 4 : 8;
18005 int ehrd_size;
18006 int save_align;
18007 int first_gp;
18008 HOST_WIDE_INT non_fixed_size;
18009
18010 memset (&info, 0, sizeof (info));
18011
18012 if (TARGET_SPE)
18013 {
18014 /* Cache value so we don't rescan instruction chain over and over. */
18015 if (cfun->machine->insn_chain_scanned_p == 0)
18016 cfun->machine->insn_chain_scanned_p
18017 = spe_func_has_64bit_regs_p () + 1;
18018 info_ptr->spe_64bit_regs_used = cfun->machine->insn_chain_scanned_p - 1;
18019 }
18020
18021 /* Select which calling sequence. */
18022 info_ptr->abi = DEFAULT_ABI;
18023
18024 /* Calculate which registers need to be saved & save area size. */
18025 info_ptr->first_gp_reg_save = first_reg_to_save ();
18026 /* Assume that we will have to save RS6000_PIC_OFFSET_TABLE_REGNUM,
18027 even if it currently looks like we won't. Reload may need it to
18028 get at a constant; if so, it will have already created a constant
18029 pool entry for it. */
18030 if (((TARGET_TOC && TARGET_MINIMAL_TOC)
18031 || (flag_pic == 1 && DEFAULT_ABI == ABI_V4)
18032 || (flag_pic && DEFAULT_ABI == ABI_DARWIN))
18033 && crtl->uses_const_pool
18034 && info_ptr->first_gp_reg_save > RS6000_PIC_OFFSET_TABLE_REGNUM)
18035 first_gp = RS6000_PIC_OFFSET_TABLE_REGNUM;
18036 else
18037 first_gp = info_ptr->first_gp_reg_save;
18038
18039 info_ptr->gp_size = reg_size * (32 - first_gp);
18040
18041 /* For the SPE, we have an additional upper 32-bits on each GPR.
18042 Ideally we should save the entire 64-bits only when the upper
18043 half is used in SIMD instructions. Since we only record
18044 registers live (not the size they are used in), this proves
18045 difficult because we'd have to traverse the instruction chain at
18046 the right time, taking reload into account. This is a real pain,
18047 so we opt to save the GPRs in 64-bits always if but one register
18048 gets used in 64-bits. Otherwise, all the registers in the frame
18049 get saved in 32-bits.
18050
18051 So... since when we save all GPRs (except the SP) in 64-bits, the
18052 traditional GP save area will be empty. */
18053 if (TARGET_SPE_ABI && info_ptr->spe_64bit_regs_used != 0)
18054 info_ptr->gp_size = 0;
18055
18056 info_ptr->first_fp_reg_save = first_fp_reg_to_save ();
18057 info_ptr->fp_size = 8 * (64 - info_ptr->first_fp_reg_save);
18058
18059 info_ptr->first_altivec_reg_save = first_altivec_reg_to_save ();
18060 info_ptr->altivec_size = 16 * (LAST_ALTIVEC_REGNO + 1
18061 - info_ptr->first_altivec_reg_save);
18062
18063 /* Does this function call anything? */
18064 info_ptr->calls_p = (! current_function_is_leaf
18065 || cfun->machine->ra_needs_full_frame);
18066
18067 /* Determine if we need to save the link register. */
18068 if ((DEFAULT_ABI == ABI_AIX
18069 && crtl->profile
18070 && !TARGET_PROFILE_KERNEL)
18071 #ifdef TARGET_RELOCATABLE
18072 || (TARGET_RELOCATABLE && (get_pool_size () != 0))
18073 #endif
18074 || (info_ptr->first_fp_reg_save != 64
18075 && !FP_SAVE_INLINE (info_ptr->first_fp_reg_save))
18076 || (DEFAULT_ABI == ABI_V4 && cfun->calls_alloca)
18077 || info_ptr->calls_p
18078 || rs6000_ra_ever_killed ())
18079 {
18080 info_ptr->lr_save_p = 1;
18081 df_set_regs_ever_live (LR_REGNO, true);
18082 }
18083
18084 /* Determine if we need to save the condition code registers. */
18085 if (df_regs_ever_live_p (CR2_REGNO)
18086 || df_regs_ever_live_p (CR3_REGNO)
18087 || df_regs_ever_live_p (CR4_REGNO))
18088 {
18089 info_ptr->cr_save_p = 1;
18090 if (DEFAULT_ABI == ABI_V4)
18091 info_ptr->cr_size = reg_size;
18092 }
18093
18094 /* If the current function calls __builtin_eh_return, then we need
18095 to allocate stack space for registers that will hold data for
18096 the exception handler. */
18097 if (crtl->calls_eh_return)
18098 {
18099 unsigned int i;
18100 for (i = 0; EH_RETURN_DATA_REGNO (i) != INVALID_REGNUM; ++i)
18101 continue;
18102
18103 /* SPE saves EH registers in 64-bits. */
18104 ehrd_size = i * (TARGET_SPE_ABI
18105 && info_ptr->spe_64bit_regs_used != 0
18106 ? UNITS_PER_SPE_WORD : UNITS_PER_WORD);
18107 }
18108 else
18109 ehrd_size = 0;
18110
18111 /* Determine various sizes. */
18112 info_ptr->reg_size = reg_size;
18113 info_ptr->fixed_size = RS6000_SAVE_AREA;
18114 info_ptr->vars_size = RS6000_ALIGN (get_frame_size (), 8);
18115 info_ptr->parm_size = RS6000_ALIGN (crtl->outgoing_args_size,
18116 TARGET_ALTIVEC ? 16 : 8);
18117 if (FRAME_GROWS_DOWNWARD)
18118 info_ptr->vars_size
18119 += RS6000_ALIGN (info_ptr->fixed_size + info_ptr->vars_size
18120 + info_ptr->parm_size,
18121 ABI_STACK_BOUNDARY / BITS_PER_UNIT)
18122 - (info_ptr->fixed_size + info_ptr->vars_size
18123 + info_ptr->parm_size);
18124
18125 if (TARGET_SPE_ABI && info_ptr->spe_64bit_regs_used != 0)
18126 info_ptr->spe_gp_size = 8 * (32 - first_gp);
18127 else
18128 info_ptr->spe_gp_size = 0;
18129
18130 if (TARGET_ALTIVEC_ABI)
18131 info_ptr->vrsave_mask = compute_vrsave_mask ();
18132 else
18133 info_ptr->vrsave_mask = 0;
18134
18135 if (TARGET_ALTIVEC_VRSAVE && info_ptr->vrsave_mask)
18136 info_ptr->vrsave_size = 4;
18137 else
18138 info_ptr->vrsave_size = 0;
18139
18140 compute_save_world_info (info_ptr);
18141
18142 /* Calculate the offsets. */
18143 switch (DEFAULT_ABI)
18144 {
18145 case ABI_NONE:
18146 default:
18147 gcc_unreachable ();
18148
18149 case ABI_AIX:
18150 case ABI_DARWIN:
18151 info_ptr->fp_save_offset = - info_ptr->fp_size;
18152 info_ptr->gp_save_offset = info_ptr->fp_save_offset - info_ptr->gp_size;
18153
18154 if (TARGET_ALTIVEC_ABI)
18155 {
18156 info_ptr->vrsave_save_offset
18157 = info_ptr->gp_save_offset - info_ptr->vrsave_size;
18158
18159 /* Align stack so vector save area is on a quadword boundary.
18160 The padding goes above the vectors. */
18161 if (info_ptr->altivec_size != 0)
18162 info_ptr->altivec_padding_size
18163 = info_ptr->vrsave_save_offset & 0xF;
18164 else
18165 info_ptr->altivec_padding_size = 0;
18166
18167 info_ptr->altivec_save_offset
18168 = info_ptr->vrsave_save_offset
18169 - info_ptr->altivec_padding_size
18170 - info_ptr->altivec_size;
18171 gcc_assert (info_ptr->altivec_size == 0
18172 || info_ptr->altivec_save_offset % 16 == 0);
18173
18174 /* Adjust for AltiVec case. */
18175 info_ptr->ehrd_offset = info_ptr->altivec_save_offset - ehrd_size;
18176 }
18177 else
18178 info_ptr->ehrd_offset = info_ptr->gp_save_offset - ehrd_size;
18179 info_ptr->cr_save_offset = reg_size; /* first word when 64-bit. */
18180 info_ptr->lr_save_offset = 2*reg_size;
18181 break;
18182
18183 case ABI_V4:
18184 info_ptr->fp_save_offset = - info_ptr->fp_size;
18185 info_ptr->gp_save_offset = info_ptr->fp_save_offset - info_ptr->gp_size;
18186 info_ptr->cr_save_offset = info_ptr->gp_save_offset - info_ptr->cr_size;
18187
18188 if (TARGET_SPE_ABI && info_ptr->spe_64bit_regs_used != 0)
18189 {
18190 /* Align stack so SPE GPR save area is aligned on a
18191 double-word boundary. */
18192 if (info_ptr->spe_gp_size != 0 && info_ptr->cr_save_offset != 0)
18193 info_ptr->spe_padding_size
18194 = 8 - (-info_ptr->cr_save_offset % 8);
18195 else
18196 info_ptr->spe_padding_size = 0;
18197
18198 info_ptr->spe_gp_save_offset
18199 = info_ptr->cr_save_offset
18200 - info_ptr->spe_padding_size
18201 - info_ptr->spe_gp_size;
18202
18203 /* Adjust for SPE case. */
18204 info_ptr->ehrd_offset = info_ptr->spe_gp_save_offset;
18205 }
18206 else if (TARGET_ALTIVEC_ABI)
18207 {
18208 info_ptr->vrsave_save_offset
18209 = info_ptr->cr_save_offset - info_ptr->vrsave_size;
18210
18211 /* Align stack so vector save area is on a quadword boundary. */
18212 if (info_ptr->altivec_size != 0)
18213 info_ptr->altivec_padding_size
18214 = 16 - (-info_ptr->vrsave_save_offset % 16);
18215 else
18216 info_ptr->altivec_padding_size = 0;
18217
18218 info_ptr->altivec_save_offset
18219 = info_ptr->vrsave_save_offset
18220 - info_ptr->altivec_padding_size
18221 - info_ptr->altivec_size;
18222
18223 /* Adjust for AltiVec case. */
18224 info_ptr->ehrd_offset = info_ptr->altivec_save_offset;
18225 }
18226 else
18227 info_ptr->ehrd_offset = info_ptr->cr_save_offset;
18228 info_ptr->ehrd_offset -= ehrd_size;
18229 info_ptr->lr_save_offset = reg_size;
18230 break;
18231 }
18232
18233 save_align = (TARGET_ALTIVEC_ABI || DEFAULT_ABI == ABI_DARWIN) ? 16 : 8;
18234 info_ptr->save_size = RS6000_ALIGN (info_ptr->fp_size
18235 + info_ptr->gp_size
18236 + info_ptr->altivec_size
18237 + info_ptr->altivec_padding_size
18238 + info_ptr->spe_gp_size
18239 + info_ptr->spe_padding_size
18240 + ehrd_size
18241 + info_ptr->cr_size
18242 + info_ptr->vrsave_size,
18243 save_align);
18244
18245 non_fixed_size = (info_ptr->vars_size
18246 + info_ptr->parm_size
18247 + info_ptr->save_size);
18248
18249 info_ptr->total_size = RS6000_ALIGN (non_fixed_size + info_ptr->fixed_size,
18250 ABI_STACK_BOUNDARY / BITS_PER_UNIT);
18251
18252 /* Determine if we need to allocate any stack frame:
18253
18254 For AIX we need to push the stack if a frame pointer is needed
18255 (because the stack might be dynamically adjusted), if we are
18256 debugging, if we make calls, or if the sum of fp_save, gp_save,
18257 and local variables are more than the space needed to save all
18258 non-volatile registers: 32-bit: 18*8 + 19*4 = 220 or 64-bit: 18*8
18259 + 18*8 = 288 (GPR13 reserved).
18260
18261 For V.4 we don't have the stack cushion that AIX uses, but assume
18262 that the debugger can handle stackless frames. */
18263
18264 if (info_ptr->calls_p)
18265 info_ptr->push_p = 1;
18266
18267 else if (DEFAULT_ABI == ABI_V4)
18268 info_ptr->push_p = non_fixed_size != 0;
18269
18270 else if (frame_pointer_needed)
18271 info_ptr->push_p = 1;
18272
18273 else if (TARGET_XCOFF && write_symbols != NO_DEBUG)
18274 info_ptr->push_p = 1;
18275
18276 else
18277 info_ptr->push_p = non_fixed_size > (TARGET_32BIT ? 220 : 288);
18278
18279 /* Zero offsets if we're not saving those registers. */
18280 if (info_ptr->fp_size == 0)
18281 info_ptr->fp_save_offset = 0;
18282
18283 if (info_ptr->gp_size == 0)
18284 info_ptr->gp_save_offset = 0;
18285
18286 if (! TARGET_ALTIVEC_ABI || info_ptr->altivec_size == 0)
18287 info_ptr->altivec_save_offset = 0;
18288
18289 if (! TARGET_ALTIVEC_ABI || info_ptr->vrsave_mask == 0)
18290 info_ptr->vrsave_save_offset = 0;
18291
18292 if (! TARGET_SPE_ABI
18293 || info_ptr->spe_64bit_regs_used == 0
18294 || info_ptr->spe_gp_size == 0)
18295 info_ptr->spe_gp_save_offset = 0;
18296
18297 if (! info_ptr->lr_save_p)
18298 info_ptr->lr_save_offset = 0;
18299
18300 if (! info_ptr->cr_save_p)
18301 info_ptr->cr_save_offset = 0;
18302
18303 return info_ptr;
18304 }
18305
18306 /* Return true if the current function uses any GPRs in 64-bit SIMD
18307 mode. */
18308
18309 static bool
18310 spe_func_has_64bit_regs_p (void)
18311 {
18312 rtx insns, insn;
18313
18314 /* Functions that save and restore all the call-saved registers will
18315 need to save/restore the registers in 64-bits. */
18316 if (crtl->calls_eh_return
18317 || cfun->calls_setjmp
18318 || crtl->has_nonlocal_goto)
18319 return true;
18320
18321 insns = get_insns ();
18322
18323 for (insn = NEXT_INSN (insns); insn != NULL_RTX; insn = NEXT_INSN (insn))
18324 {
18325 if (INSN_P (insn))
18326 {
18327 rtx i;
18328
18329 /* FIXME: This should be implemented with attributes...
18330
18331 (set_attr "spe64" "true")....then,
18332 if (get_spe64(insn)) return true;
18333
18334 It's the only reliable way to do the stuff below. */
18335
18336 i = PATTERN (insn);
18337 if (GET_CODE (i) == SET)
18338 {
18339 enum machine_mode mode = GET_MODE (SET_SRC (i));
18340
18341 if (SPE_VECTOR_MODE (mode))
18342 return true;
18343 if (TARGET_E500_DOUBLE && (mode == DFmode || mode == TFmode))
18344 return true;
18345 }
18346 }
18347 }
18348
18349 return false;
18350 }
18351
18352 static void
18353 debug_stack_info (rs6000_stack_t *info)
18354 {
18355 const char *abi_string;
18356
18357 if (! info)
18358 info = rs6000_stack_info ();
18359
18360 fprintf (stderr, "\nStack information for function %s:\n",
18361 ((current_function_decl && DECL_NAME (current_function_decl))
18362 ? IDENTIFIER_POINTER (DECL_NAME (current_function_decl))
18363 : "<unknown>"));
18364
18365 switch (info->abi)
18366 {
18367 default: abi_string = "Unknown"; break;
18368 case ABI_NONE: abi_string = "NONE"; break;
18369 case ABI_AIX: abi_string = "AIX"; break;
18370 case ABI_DARWIN: abi_string = "Darwin"; break;
18371 case ABI_V4: abi_string = "V.4"; break;
18372 }
18373
18374 fprintf (stderr, "\tABI = %5s\n", abi_string);
18375
18376 if (TARGET_ALTIVEC_ABI)
18377 fprintf (stderr, "\tALTIVEC ABI extensions enabled.\n");
18378
18379 if (TARGET_SPE_ABI)
18380 fprintf (stderr, "\tSPE ABI extensions enabled.\n");
18381
18382 if (info->first_gp_reg_save != 32)
18383 fprintf (stderr, "\tfirst_gp_reg_save = %5d\n", info->first_gp_reg_save);
18384
18385 if (info->first_fp_reg_save != 64)
18386 fprintf (stderr, "\tfirst_fp_reg_save = %5d\n", info->first_fp_reg_save);
18387
18388 if (info->first_altivec_reg_save <= LAST_ALTIVEC_REGNO)
18389 fprintf (stderr, "\tfirst_altivec_reg_save = %5d\n",
18390 info->first_altivec_reg_save);
18391
18392 if (info->lr_save_p)
18393 fprintf (stderr, "\tlr_save_p = %5d\n", info->lr_save_p);
18394
18395 if (info->cr_save_p)
18396 fprintf (stderr, "\tcr_save_p = %5d\n", info->cr_save_p);
18397
18398 if (info->vrsave_mask)
18399 fprintf (stderr, "\tvrsave_mask = 0x%x\n", info->vrsave_mask);
18400
18401 if (info->push_p)
18402 fprintf (stderr, "\tpush_p = %5d\n", info->push_p);
18403
18404 if (info->calls_p)
18405 fprintf (stderr, "\tcalls_p = %5d\n", info->calls_p);
18406
18407 if (info->gp_save_offset)
18408 fprintf (stderr, "\tgp_save_offset = %5d\n", info->gp_save_offset);
18409
18410 if (info->fp_save_offset)
18411 fprintf (stderr, "\tfp_save_offset = %5d\n", info->fp_save_offset);
18412
18413 if (info->altivec_save_offset)
18414 fprintf (stderr, "\taltivec_save_offset = %5d\n",
18415 info->altivec_save_offset);
18416
18417 if (info->spe_gp_save_offset)
18418 fprintf (stderr, "\tspe_gp_save_offset = %5d\n",
18419 info->spe_gp_save_offset);
18420
18421 if (info->vrsave_save_offset)
18422 fprintf (stderr, "\tvrsave_save_offset = %5d\n",
18423 info->vrsave_save_offset);
18424
18425 if (info->lr_save_offset)
18426 fprintf (stderr, "\tlr_save_offset = %5d\n", info->lr_save_offset);
18427
18428 if (info->cr_save_offset)
18429 fprintf (stderr, "\tcr_save_offset = %5d\n", info->cr_save_offset);
18430
18431 if (info->varargs_save_offset)
18432 fprintf (stderr, "\tvarargs_save_offset = %5d\n", info->varargs_save_offset);
18433
18434 if (info->total_size)
18435 fprintf (stderr, "\ttotal_size = "HOST_WIDE_INT_PRINT_DEC"\n",
18436 info->total_size);
18437
18438 if (info->vars_size)
18439 fprintf (stderr, "\tvars_size = "HOST_WIDE_INT_PRINT_DEC"\n",
18440 info->vars_size);
18441
18442 if (info->parm_size)
18443 fprintf (stderr, "\tparm_size = %5d\n", info->parm_size);
18444
18445 if (info->fixed_size)
18446 fprintf (stderr, "\tfixed_size = %5d\n", info->fixed_size);
18447
18448 if (info->gp_size)
18449 fprintf (stderr, "\tgp_size = %5d\n", info->gp_size);
18450
18451 if (info->spe_gp_size)
18452 fprintf (stderr, "\tspe_gp_size = %5d\n", info->spe_gp_size);
18453
18454 if (info->fp_size)
18455 fprintf (stderr, "\tfp_size = %5d\n", info->fp_size);
18456
18457 if (info->altivec_size)
18458 fprintf (stderr, "\taltivec_size = %5d\n", info->altivec_size);
18459
18460 if (info->vrsave_size)
18461 fprintf (stderr, "\tvrsave_size = %5d\n", info->vrsave_size);
18462
18463 if (info->altivec_padding_size)
18464 fprintf (stderr, "\taltivec_padding_size= %5d\n",
18465 info->altivec_padding_size);
18466
18467 if (info->spe_padding_size)
18468 fprintf (stderr, "\tspe_padding_size = %5d\n",
18469 info->spe_padding_size);
18470
18471 if (info->cr_size)
18472 fprintf (stderr, "\tcr_size = %5d\n", info->cr_size);
18473
18474 if (info->save_size)
18475 fprintf (stderr, "\tsave_size = %5d\n", info->save_size);
18476
18477 if (info->reg_size != 4)
18478 fprintf (stderr, "\treg_size = %5d\n", info->reg_size);
18479
18480 fprintf (stderr, "\n");
18481 }
18482
18483 rtx
18484 rs6000_return_addr (int count, rtx frame)
18485 {
18486 /* Currently we don't optimize very well between prolog and body
18487 code and for PIC code the code can be actually quite bad, so
18488 don't try to be too clever here. */
18489 if (count != 0 || (DEFAULT_ABI != ABI_AIX && flag_pic))
18490 {
18491 cfun->machine->ra_needs_full_frame = 1;
18492
18493 return
18494 gen_rtx_MEM
18495 (Pmode,
18496 memory_address
18497 (Pmode,
18498 plus_constant (copy_to_reg
18499 (gen_rtx_MEM (Pmode,
18500 memory_address (Pmode, frame))),
18501 RETURN_ADDRESS_OFFSET)));
18502 }
18503
18504 cfun->machine->ra_need_lr = 1;
18505 return get_hard_reg_initial_val (Pmode, LR_REGNO);
18506 }
18507
18508 /* Say whether a function is a candidate for sibcall handling or not.
18509 We do not allow indirect calls to be optimized into sibling calls.
18510 Also, we can't do it if there are any vector parameters; there's
18511 nowhere to put the VRsave code so it works; note that functions with
18512 vector parameters are required to have a prototype, so the argument
18513 type info must be available here. (The tail recursion case can work
18514 with vector parameters, but there's no way to distinguish here.) */
18515 static bool
18516 rs6000_function_ok_for_sibcall (tree decl, tree exp ATTRIBUTE_UNUSED)
18517 {
18518 tree type;
18519 if (decl)
18520 {
18521 if (TARGET_ALTIVEC_VRSAVE)
18522 {
18523 for (type = TYPE_ARG_TYPES (TREE_TYPE (decl));
18524 type; type = TREE_CHAIN (type))
18525 {
18526 if (TREE_CODE (TREE_VALUE (type)) == VECTOR_TYPE)
18527 return false;
18528 }
18529 }
18530 if (DEFAULT_ABI == ABI_DARWIN
18531 || ((*targetm.binds_local_p) (decl)
18532 && (DEFAULT_ABI != ABI_AIX || !DECL_EXTERNAL (decl))))
18533 {
18534 tree attr_list = TYPE_ATTRIBUTES (TREE_TYPE (decl));
18535
18536 if (!lookup_attribute ("longcall", attr_list)
18537 || lookup_attribute ("shortcall", attr_list))
18538 return true;
18539 }
18540 }
18541 return false;
18542 }
18543
18544 /* NULL if INSN insn is valid within a low-overhead loop.
18545 Otherwise return why doloop cannot be applied.
18546 PowerPC uses the COUNT register for branch on table instructions. */
18547
18548 static const char *
18549 rs6000_invalid_within_doloop (const_rtx insn)
18550 {
18551 if (CALL_P (insn))
18552 return "Function call in the loop.";
18553
18554 if (JUMP_P (insn)
18555 && (GET_CODE (PATTERN (insn)) == ADDR_DIFF_VEC
18556 || GET_CODE (PATTERN (insn)) == ADDR_VEC))
18557 return "Computed branch in the loop.";
18558
18559 return NULL;
18560 }
18561
18562 static int
18563 rs6000_ra_ever_killed (void)
18564 {
18565 rtx top;
18566 rtx reg;
18567 rtx insn;
18568
18569 if (cfun->is_thunk)
18570 return 0;
18571
18572 if (cfun->machine->lr_save_state)
18573 return cfun->machine->lr_save_state - 1;
18574
18575 /* regs_ever_live has LR marked as used if any sibcalls are present,
18576 but this should not force saving and restoring in the
18577 pro/epilogue. Likewise, reg_set_between_p thinks a sibcall
18578 clobbers LR, so that is inappropriate. */
18579
18580 /* Also, the prologue can generate a store into LR that
18581 doesn't really count, like this:
18582
18583 move LR->R0
18584 bcl to set PIC register
18585 move LR->R31
18586 move R0->LR
18587
18588 When we're called from the epilogue, we need to avoid counting
18589 this as a store. */
18590
18591 push_topmost_sequence ();
18592 top = get_insns ();
18593 pop_topmost_sequence ();
18594 reg = gen_rtx_REG (Pmode, LR_REGNO);
18595
18596 for (insn = NEXT_INSN (top); insn != NULL_RTX; insn = NEXT_INSN (insn))
18597 {
18598 if (INSN_P (insn))
18599 {
18600 if (CALL_P (insn))
18601 {
18602 if (!SIBLING_CALL_P (insn))
18603 return 1;
18604 }
18605 else if (find_regno_note (insn, REG_INC, LR_REGNO))
18606 return 1;
18607 else if (set_of (reg, insn) != NULL_RTX
18608 && !prologue_epilogue_contains (insn))
18609 return 1;
18610 }
18611 }
18612 return 0;
18613 }
18614 \f
18615 /* Emit instructions needed to load the TOC register.
18616 This is only needed when TARGET_TOC, TARGET_MINIMAL_TOC, and there is
18617 a constant pool; or for SVR4 -fpic. */
18618
18619 void
18620 rs6000_emit_load_toc_table (int fromprolog)
18621 {
18622 rtx dest;
18623 dest = gen_rtx_REG (Pmode, RS6000_PIC_OFFSET_TABLE_REGNUM);
18624
18625 if (TARGET_ELF && TARGET_SECURE_PLT && DEFAULT_ABI != ABI_AIX && flag_pic)
18626 {
18627 char buf[30];
18628 rtx lab, tmp1, tmp2, got;
18629
18630 ASM_GENERATE_INTERNAL_LABEL (buf, "LCF", rs6000_pic_labelno);
18631 lab = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (buf));
18632 if (flag_pic == 2)
18633 got = gen_rtx_SYMBOL_REF (Pmode, toc_label_name);
18634 else
18635 got = rs6000_got_sym ();
18636 tmp1 = tmp2 = dest;
18637 if (!fromprolog)
18638 {
18639 tmp1 = gen_reg_rtx (Pmode);
18640 tmp2 = gen_reg_rtx (Pmode);
18641 }
18642 emit_insn (gen_load_toc_v4_PIC_1 (lab));
18643 emit_move_insn (tmp1,
18644 gen_rtx_REG (Pmode, LR_REGNO));
18645 emit_insn (gen_load_toc_v4_PIC_3b (tmp2, tmp1, got, lab));
18646 emit_insn (gen_load_toc_v4_PIC_3c (dest, tmp2, got, lab));
18647 }
18648 else if (TARGET_ELF && DEFAULT_ABI == ABI_V4 && flag_pic == 1)
18649 {
18650 emit_insn (gen_load_toc_v4_pic_si ());
18651 emit_move_insn (dest, gen_rtx_REG (Pmode, LR_REGNO));
18652 }
18653 else if (TARGET_ELF && DEFAULT_ABI != ABI_AIX && flag_pic == 2)
18654 {
18655 char buf[30];
18656 rtx temp0 = (fromprolog
18657 ? gen_rtx_REG (Pmode, 0)
18658 : gen_reg_rtx (Pmode));
18659
18660 if (fromprolog)
18661 {
18662 rtx symF, symL;
18663
18664 ASM_GENERATE_INTERNAL_LABEL (buf, "LCF", rs6000_pic_labelno);
18665 symF = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (buf));
18666
18667 ASM_GENERATE_INTERNAL_LABEL (buf, "LCL", rs6000_pic_labelno);
18668 symL = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (buf));
18669
18670 emit_insn (gen_load_toc_v4_PIC_1 (symF));
18671 emit_move_insn (dest,
18672 gen_rtx_REG (Pmode, LR_REGNO));
18673 emit_insn (gen_load_toc_v4_PIC_2 (temp0, dest, symL, symF));
18674 }
18675 else
18676 {
18677 rtx tocsym, lab;
18678
18679 tocsym = gen_rtx_SYMBOL_REF (Pmode, toc_label_name);
18680 lab = gen_label_rtx ();
18681 emit_insn (gen_load_toc_v4_PIC_1b (tocsym, lab));
18682 emit_move_insn (dest, gen_rtx_REG (Pmode, LR_REGNO));
18683 emit_move_insn (temp0, gen_rtx_MEM (Pmode, dest));
18684 }
18685 emit_insn (gen_addsi3 (dest, temp0, dest));
18686 }
18687 else if (TARGET_ELF && !TARGET_AIX && flag_pic == 0 && TARGET_MINIMAL_TOC)
18688 {
18689 /* This is for AIX code running in non-PIC ELF32. */
18690 char buf[30];
18691 rtx realsym;
18692 ASM_GENERATE_INTERNAL_LABEL (buf, "LCTOC", 1);
18693 realsym = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (buf));
18694
18695 emit_insn (gen_elf_high (dest, realsym));
18696 emit_insn (gen_elf_low (dest, dest, realsym));
18697 }
18698 else
18699 {
18700 gcc_assert (DEFAULT_ABI == ABI_AIX);
18701
18702 if (TARGET_32BIT)
18703 emit_insn (gen_load_toc_aix_si (dest));
18704 else
18705 emit_insn (gen_load_toc_aix_di (dest));
18706 }
18707 }
18708
18709 /* Emit instructions to restore the link register after determining where
18710 its value has been stored. */
18711
18712 void
18713 rs6000_emit_eh_reg_restore (rtx source, rtx scratch)
18714 {
18715 rs6000_stack_t *info = rs6000_stack_info ();
18716 rtx operands[2];
18717
18718 operands[0] = source;
18719 operands[1] = scratch;
18720
18721 if (info->lr_save_p)
18722 {
18723 rtx frame_rtx = stack_pointer_rtx;
18724 HOST_WIDE_INT sp_offset = 0;
18725 rtx tmp;
18726
18727 if (frame_pointer_needed
18728 || cfun->calls_alloca
18729 || info->total_size > 32767)
18730 {
18731 tmp = gen_frame_mem (Pmode, frame_rtx);
18732 emit_move_insn (operands[1], tmp);
18733 frame_rtx = operands[1];
18734 }
18735 else if (info->push_p)
18736 sp_offset = info->total_size;
18737
18738 tmp = plus_constant (frame_rtx, info->lr_save_offset + sp_offset);
18739 tmp = gen_frame_mem (Pmode, tmp);
18740 emit_move_insn (tmp, operands[0]);
18741 }
18742 else
18743 emit_move_insn (gen_rtx_REG (Pmode, LR_REGNO), operands[0]);
18744
18745 /* Freeze lr_save_p. We've just emitted rtl that depends on the
18746 state of lr_save_p so any change from here on would be a bug. In
18747 particular, stop rs6000_ra_ever_killed from considering the SET
18748 of lr we may have added just above. */
18749 cfun->machine->lr_save_state = info->lr_save_p + 1;
18750 }
18751
18752 static GTY(()) alias_set_type set = -1;
18753
18754 alias_set_type
18755 get_TOC_alias_set (void)
18756 {
18757 if (set == -1)
18758 set = new_alias_set ();
18759 return set;
18760 }
18761
18762 /* This returns nonzero if the current function uses the TOC. This is
18763 determined by the presence of (use (unspec ... UNSPEC_TOC)), which
18764 is generated by the ABI_V4 load_toc_* patterns. */
18765 #if TARGET_ELF
18766 static int
18767 uses_TOC (void)
18768 {
18769 rtx insn;
18770
18771 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
18772 if (INSN_P (insn))
18773 {
18774 rtx pat = PATTERN (insn);
18775 int i;
18776
18777 if (GET_CODE (pat) == PARALLEL)
18778 for (i = 0; i < XVECLEN (pat, 0); i++)
18779 {
18780 rtx sub = XVECEXP (pat, 0, i);
18781 if (GET_CODE (sub) == USE)
18782 {
18783 sub = XEXP (sub, 0);
18784 if (GET_CODE (sub) == UNSPEC
18785 && XINT (sub, 1) == UNSPEC_TOC)
18786 return 1;
18787 }
18788 }
18789 }
18790 return 0;
18791 }
18792 #endif
18793
18794 rtx
18795 create_TOC_reference (rtx symbol, rtx largetoc_reg)
18796 {
18797 rtx tocrel, tocreg;
18798
18799 if (TARGET_DEBUG_ADDR)
18800 {
18801 if (GET_CODE (symbol) == SYMBOL_REF)
18802 fprintf (stderr, "\ncreate_TOC_reference, (symbol_ref %s)\n",
18803 XSTR (symbol, 0));
18804 else
18805 {
18806 fprintf (stderr, "\ncreate_TOC_reference, code %s:\n",
18807 GET_RTX_NAME (GET_CODE (symbol)));
18808 debug_rtx (symbol);
18809 }
18810 }
18811
18812 if (!can_create_pseudo_p ())
18813 df_set_regs_ever_live (TOC_REGISTER, true);
18814
18815 tocrel = gen_rtx_CONST (Pmode,
18816 gen_rtx_UNSPEC (Pmode, gen_rtvec (1, symbol),
18817 UNSPEC_TOCREL));
18818 tocreg = gen_rtx_REG (Pmode, TOC_REGISTER);
18819 if (TARGET_CMODEL != CMODEL_SMALL)
18820 {
18821 rtx hi = gen_rtx_PLUS (Pmode, tocreg, gen_rtx_HIGH (Pmode, tocrel));
18822 if (largetoc_reg != NULL)
18823 {
18824 emit_move_insn (largetoc_reg, hi);
18825 hi = largetoc_reg;
18826 }
18827 return gen_rtx_LO_SUM (Pmode, hi, copy_rtx (tocrel));
18828 }
18829 else
18830 return gen_rtx_PLUS (Pmode, tocreg, tocrel);
18831 }
18832
18833 /* Issue assembly directives that create a reference to the given DWARF
18834 FRAME_TABLE_LABEL from the current function section. */
18835 void
18836 rs6000_aix_asm_output_dwarf_table_ref (char * frame_table_label)
18837 {
18838 fprintf (asm_out_file, "\t.ref %s\n",
18839 TARGET_STRIP_NAME_ENCODING (frame_table_label));
18840 }
18841
18842 /* If _Unwind_* has been called from within the same module,
18843 toc register is not guaranteed to be saved to 40(1) on function
18844 entry. Save it there in that case. */
18845
18846 void
18847 rs6000_aix_emit_builtin_unwind_init (void)
18848 {
18849 rtx mem;
18850 rtx stack_top = gen_reg_rtx (Pmode);
18851 rtx opcode_addr = gen_reg_rtx (Pmode);
18852 rtx opcode = gen_reg_rtx (SImode);
18853 rtx tocompare = gen_reg_rtx (SImode);
18854 rtx no_toc_save_needed = gen_label_rtx ();
18855
18856 mem = gen_frame_mem (Pmode, hard_frame_pointer_rtx);
18857 emit_move_insn (stack_top, mem);
18858
18859 mem = gen_frame_mem (Pmode,
18860 gen_rtx_PLUS (Pmode, stack_top,
18861 GEN_INT (2 * GET_MODE_SIZE (Pmode))));
18862 emit_move_insn (opcode_addr, mem);
18863 emit_move_insn (opcode, gen_rtx_MEM (SImode, opcode_addr));
18864 emit_move_insn (tocompare, gen_int_mode (TARGET_32BIT ? 0x80410014
18865 : 0xE8410028, SImode));
18866
18867 do_compare_rtx_and_jump (opcode, tocompare, EQ, 1,
18868 SImode, NULL_RTX, NULL_RTX,
18869 no_toc_save_needed, -1);
18870
18871 mem = gen_frame_mem (Pmode,
18872 gen_rtx_PLUS (Pmode, stack_top,
18873 GEN_INT (5 * GET_MODE_SIZE (Pmode))));
18874 emit_move_insn (mem, gen_rtx_REG (Pmode, 2));
18875 emit_label (no_toc_save_needed);
18876 }
18877 \f
18878 /* This ties together stack memory (MEM with an alias set of frame_alias_set)
18879 and the change to the stack pointer. */
18880
18881 static void
18882 rs6000_emit_stack_tie (void)
18883 {
18884 rtx mem = gen_frame_mem (BLKmode,
18885 gen_rtx_REG (Pmode, STACK_POINTER_REGNUM));
18886
18887 emit_insn (gen_stack_tie (mem));
18888 }
18889
18890 /* Emit the correct code for allocating stack space, as insns.
18891 If COPY_REG, make sure a copy of the old frame is left there.
18892 The generated code may use hard register 0 as a temporary. */
18893
18894 static void
18895 rs6000_emit_allocate_stack (HOST_WIDE_INT size, rtx copy_reg)
18896 {
18897 rtx insn;
18898 rtx stack_reg = gen_rtx_REG (Pmode, STACK_POINTER_REGNUM);
18899 rtx tmp_reg = gen_rtx_REG (Pmode, 0);
18900 rtx todec = gen_int_mode (-size, Pmode);
18901 rtx par, set, mem;
18902
18903 if (INTVAL (todec) != -size)
18904 {
18905 warning (0, "stack frame too large");
18906 emit_insn (gen_trap ());
18907 return;
18908 }
18909
18910 if (crtl->limit_stack)
18911 {
18912 if (REG_P (stack_limit_rtx)
18913 && REGNO (stack_limit_rtx) > 1
18914 && REGNO (stack_limit_rtx) <= 31)
18915 {
18916 emit_insn (gen_add3_insn (tmp_reg, stack_limit_rtx, GEN_INT (size)));
18917 emit_insn (gen_cond_trap (LTU, stack_reg, tmp_reg,
18918 const0_rtx));
18919 }
18920 else if (GET_CODE (stack_limit_rtx) == SYMBOL_REF
18921 && TARGET_32BIT
18922 && DEFAULT_ABI == ABI_V4)
18923 {
18924 rtx toload = gen_rtx_CONST (VOIDmode,
18925 gen_rtx_PLUS (Pmode,
18926 stack_limit_rtx,
18927 GEN_INT (size)));
18928
18929 emit_insn (gen_elf_high (tmp_reg, toload));
18930 emit_insn (gen_elf_low (tmp_reg, tmp_reg, toload));
18931 emit_insn (gen_cond_trap (LTU, stack_reg, tmp_reg,
18932 const0_rtx));
18933 }
18934 else
18935 warning (0, "stack limit expression is not supported");
18936 }
18937
18938 if (copy_reg)
18939 emit_move_insn (copy_reg, stack_reg);
18940
18941 if (size > 32767)
18942 {
18943 /* Need a note here so that try_split doesn't get confused. */
18944 if (get_last_insn () == NULL_RTX)
18945 emit_note (NOTE_INSN_DELETED);
18946 insn = emit_move_insn (tmp_reg, todec);
18947 try_split (PATTERN (insn), insn, 0);
18948 todec = tmp_reg;
18949 }
18950
18951 insn = emit_insn (TARGET_32BIT
18952 ? gen_movsi_update_stack (stack_reg, stack_reg,
18953 todec, stack_reg)
18954 : gen_movdi_di_update_stack (stack_reg, stack_reg,
18955 todec, stack_reg));
18956 /* Since we didn't use gen_frame_mem to generate the MEM, grab
18957 it now and set the alias set/attributes. The above gen_*_update
18958 calls will generate a PARALLEL with the MEM set being the first
18959 operation. */
18960 par = PATTERN (insn);
18961 gcc_assert (GET_CODE (par) == PARALLEL);
18962 set = XVECEXP (par, 0, 0);
18963 gcc_assert (GET_CODE (set) == SET);
18964 mem = SET_DEST (set);
18965 gcc_assert (MEM_P (mem));
18966 MEM_NOTRAP_P (mem) = 1;
18967 set_mem_alias_set (mem, get_frame_alias_set ());
18968
18969 RTX_FRAME_RELATED_P (insn) = 1;
18970 add_reg_note (insn, REG_FRAME_RELATED_EXPR,
18971 gen_rtx_SET (VOIDmode, stack_reg,
18972 gen_rtx_PLUS (Pmode, stack_reg,
18973 GEN_INT (-size))));
18974 }
18975
18976 #define PROBE_INTERVAL (1 << STACK_CHECK_PROBE_INTERVAL_EXP)
18977
18978 #if PROBE_INTERVAL > 32768
18979 #error Cannot use indexed addressing mode for stack probing
18980 #endif
18981
18982 /* Emit code to probe a range of stack addresses from FIRST to FIRST+SIZE,
18983 inclusive. These are offsets from the current stack pointer. */
18984
18985 static void
18986 rs6000_emit_probe_stack_range (HOST_WIDE_INT first, HOST_WIDE_INT size)
18987 {
18988 /* See if we have a constant small number of probes to generate. If so,
18989 that's the easy case. */
18990 if (first + size <= 32768)
18991 {
18992 HOST_WIDE_INT i;
18993
18994 /* Probe at FIRST + N * PROBE_INTERVAL for values of N from 1 until
18995 it exceeds SIZE. If only one probe is needed, this will not
18996 generate any code. Then probe at FIRST + SIZE. */
18997 for (i = PROBE_INTERVAL; i < size; i += PROBE_INTERVAL)
18998 emit_stack_probe (plus_constant (stack_pointer_rtx, -(first + i)));
18999
19000 emit_stack_probe (plus_constant (stack_pointer_rtx, -(first + size)));
19001 }
19002
19003 /* Otherwise, do the same as above, but in a loop. Note that we must be
19004 extra careful with variables wrapping around because we might be at
19005 the very top (or the very bottom) of the address space and we have
19006 to be able to handle this case properly; in particular, we use an
19007 equality test for the loop condition. */
19008 else
19009 {
19010 HOST_WIDE_INT rounded_size;
19011 rtx r12 = gen_rtx_REG (Pmode, 12);
19012 rtx r0 = gen_rtx_REG (Pmode, 0);
19013
19014 /* Sanity check for the addressing mode we're going to use. */
19015 gcc_assert (first <= 32768);
19016
19017 /* Step 1: round SIZE to the previous multiple of the interval. */
19018
19019 rounded_size = size & -PROBE_INTERVAL;
19020
19021
19022 /* Step 2: compute initial and final value of the loop counter. */
19023
19024 /* TEST_ADDR = SP + FIRST. */
19025 emit_insn (gen_rtx_SET (VOIDmode, r12,
19026 plus_constant (stack_pointer_rtx, -first)));
19027
19028 /* LAST_ADDR = SP + FIRST + ROUNDED_SIZE. */
19029 if (rounded_size > 32768)
19030 {
19031 emit_move_insn (r0, GEN_INT (-rounded_size));
19032 emit_insn (gen_rtx_SET (VOIDmode, r0,
19033 gen_rtx_PLUS (Pmode, r12, r0)));
19034 }
19035 else
19036 emit_insn (gen_rtx_SET (VOIDmode, r0,
19037 plus_constant (r12, -rounded_size)));
19038
19039
19040 /* Step 3: the loop
19041
19042 while (TEST_ADDR != LAST_ADDR)
19043 {
19044 TEST_ADDR = TEST_ADDR + PROBE_INTERVAL
19045 probe at TEST_ADDR
19046 }
19047
19048 probes at FIRST + N * PROBE_INTERVAL for values of N from 1
19049 until it is equal to ROUNDED_SIZE. */
19050
19051 if (TARGET_64BIT)
19052 emit_insn (gen_probe_stack_rangedi (r12, r12, r0));
19053 else
19054 emit_insn (gen_probe_stack_rangesi (r12, r12, r0));
19055
19056
19057 /* Step 4: probe at FIRST + SIZE if we cannot assert at compile-time
19058 that SIZE is equal to ROUNDED_SIZE. */
19059
19060 if (size != rounded_size)
19061 emit_stack_probe (plus_constant (r12, rounded_size - size));
19062 }
19063 }
19064
19065 /* Probe a range of stack addresses from REG1 to REG2 inclusive. These are
19066 absolute addresses. */
19067
19068 const char *
19069 output_probe_stack_range (rtx reg1, rtx reg2)
19070 {
19071 static int labelno = 0;
19072 char loop_lab[32], end_lab[32];
19073 rtx xops[2];
19074
19075 ASM_GENERATE_INTERNAL_LABEL (loop_lab, "LPSRL", labelno);
19076 ASM_GENERATE_INTERNAL_LABEL (end_lab, "LPSRE", labelno++);
19077
19078 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, loop_lab);
19079
19080 /* Jump to END_LAB if TEST_ADDR == LAST_ADDR. */
19081 xops[0] = reg1;
19082 xops[1] = reg2;
19083 if (TARGET_64BIT)
19084 output_asm_insn ("{cmp|cmpd} 0,%0,%1", xops);
19085 else
19086 output_asm_insn ("{cmp|cmpw} 0,%0,%1", xops);
19087
19088 fputs ("\tbeq 0,", asm_out_file);
19089 assemble_name_raw (asm_out_file, end_lab);
19090 fputc ('\n', asm_out_file);
19091
19092 /* TEST_ADDR = TEST_ADDR + PROBE_INTERVAL. */
19093 xops[1] = GEN_INT (-PROBE_INTERVAL);
19094 output_asm_insn ("{cal %0,%1(%0)|addi %0,%0,%1}", xops);
19095
19096 /* Probe at TEST_ADDR and branch. */
19097 output_asm_insn ("{st|stw} 0,0(%0)", xops);
19098 fprintf (asm_out_file, "\tb ");
19099 assemble_name_raw (asm_out_file, loop_lab);
19100 fputc ('\n', asm_out_file);
19101
19102 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, end_lab);
19103
19104 return "";
19105 }
19106
19107 /* Add to 'insn' a note which is PATTERN (INSN) but with REG replaced
19108 with (plus:P (reg 1) VAL), and with REG2 replaced with RREG if REG2
19109 is not NULL. It would be nice if dwarf2out_frame_debug_expr could
19110 deduce these equivalences by itself so it wasn't necessary to hold
19111 its hand so much. */
19112
19113 static void
19114 rs6000_frame_related (rtx insn, rtx reg, HOST_WIDE_INT val,
19115 rtx reg2, rtx rreg)
19116 {
19117 rtx real, temp;
19118
19119 /* copy_rtx will not make unique copies of registers, so we need to
19120 ensure we don't have unwanted sharing here. */
19121 if (reg == reg2)
19122 reg = gen_raw_REG (GET_MODE (reg), REGNO (reg));
19123
19124 if (reg == rreg)
19125 reg = gen_raw_REG (GET_MODE (reg), REGNO (reg));
19126
19127 real = copy_rtx (PATTERN (insn));
19128
19129 if (reg2 != NULL_RTX)
19130 real = replace_rtx (real, reg2, rreg);
19131
19132 real = replace_rtx (real, reg,
19133 gen_rtx_PLUS (Pmode, gen_rtx_REG (Pmode,
19134 STACK_POINTER_REGNUM),
19135 GEN_INT (val)));
19136
19137 /* We expect that 'real' is either a SET or a PARALLEL containing
19138 SETs (and possibly other stuff). In a PARALLEL, all the SETs
19139 are important so they all have to be marked RTX_FRAME_RELATED_P. */
19140
19141 if (GET_CODE (real) == SET)
19142 {
19143 rtx set = real;
19144
19145 temp = simplify_rtx (SET_SRC (set));
19146 if (temp)
19147 SET_SRC (set) = temp;
19148 temp = simplify_rtx (SET_DEST (set));
19149 if (temp)
19150 SET_DEST (set) = temp;
19151 if (GET_CODE (SET_DEST (set)) == MEM)
19152 {
19153 temp = simplify_rtx (XEXP (SET_DEST (set), 0));
19154 if (temp)
19155 XEXP (SET_DEST (set), 0) = temp;
19156 }
19157 }
19158 else
19159 {
19160 int i;
19161
19162 gcc_assert (GET_CODE (real) == PARALLEL);
19163 for (i = 0; i < XVECLEN (real, 0); i++)
19164 if (GET_CODE (XVECEXP (real, 0, i)) == SET)
19165 {
19166 rtx set = XVECEXP (real, 0, i);
19167
19168 temp = simplify_rtx (SET_SRC (set));
19169 if (temp)
19170 SET_SRC (set) = temp;
19171 temp = simplify_rtx (SET_DEST (set));
19172 if (temp)
19173 SET_DEST (set) = temp;
19174 if (GET_CODE (SET_DEST (set)) == MEM)
19175 {
19176 temp = simplify_rtx (XEXP (SET_DEST (set), 0));
19177 if (temp)
19178 XEXP (SET_DEST (set), 0) = temp;
19179 }
19180 RTX_FRAME_RELATED_P (set) = 1;
19181 }
19182 }
19183
19184 RTX_FRAME_RELATED_P (insn) = 1;
19185 add_reg_note (insn, REG_FRAME_RELATED_EXPR, real);
19186 }
19187
19188 /* Returns an insn that has a vrsave set operation with the
19189 appropriate CLOBBERs. */
19190
19191 static rtx
19192 generate_set_vrsave (rtx reg, rs6000_stack_t *info, int epiloguep)
19193 {
19194 int nclobs, i;
19195 rtx insn, clobs[TOTAL_ALTIVEC_REGS + 1];
19196 rtx vrsave = gen_rtx_REG (SImode, VRSAVE_REGNO);
19197
19198 clobs[0]
19199 = gen_rtx_SET (VOIDmode,
19200 vrsave,
19201 gen_rtx_UNSPEC_VOLATILE (SImode,
19202 gen_rtvec (2, reg, vrsave),
19203 UNSPECV_SET_VRSAVE));
19204
19205 nclobs = 1;
19206
19207 /* We need to clobber the registers in the mask so the scheduler
19208 does not move sets to VRSAVE before sets of AltiVec registers.
19209
19210 However, if the function receives nonlocal gotos, reload will set
19211 all call saved registers live. We will end up with:
19212
19213 (set (reg 999) (mem))
19214 (parallel [ (set (reg vrsave) (unspec blah))
19215 (clobber (reg 999))])
19216
19217 The clobber will cause the store into reg 999 to be dead, and
19218 flow will attempt to delete an epilogue insn. In this case, we
19219 need an unspec use/set of the register. */
19220
19221 for (i = FIRST_ALTIVEC_REGNO; i <= LAST_ALTIVEC_REGNO; ++i)
19222 if (info->vrsave_mask & ALTIVEC_REG_BIT (i))
19223 {
19224 if (!epiloguep || call_used_regs [i])
19225 clobs[nclobs++] = gen_rtx_CLOBBER (VOIDmode,
19226 gen_rtx_REG (V4SImode, i));
19227 else
19228 {
19229 rtx reg = gen_rtx_REG (V4SImode, i);
19230
19231 clobs[nclobs++]
19232 = gen_rtx_SET (VOIDmode,
19233 reg,
19234 gen_rtx_UNSPEC (V4SImode,
19235 gen_rtvec (1, reg), 27));
19236 }
19237 }
19238
19239 insn = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (nclobs));
19240
19241 for (i = 0; i < nclobs; ++i)
19242 XVECEXP (insn, 0, i) = clobs[i];
19243
19244 return insn;
19245 }
19246
19247 /* Save a register into the frame, and emit RTX_FRAME_RELATED_P notes.
19248 Save REGNO into [FRAME_REG + OFFSET] in mode MODE. */
19249
19250 static void
19251 emit_frame_save (rtx frame_reg, rtx frame_ptr, enum machine_mode mode,
19252 unsigned int regno, int offset, HOST_WIDE_INT total_size)
19253 {
19254 rtx reg, offset_rtx, insn, mem, addr, int_rtx;
19255 rtx replacea, replaceb;
19256
19257 int_rtx = GEN_INT (offset);
19258
19259 /* Some cases that need register indexed addressing. */
19260 if ((TARGET_ALTIVEC_ABI && ALTIVEC_VECTOR_MODE (mode))
19261 || (TARGET_VSX && VSX_VECTOR_MODE (mode))
19262 || (TARGET_E500_DOUBLE && mode == DFmode)
19263 || (TARGET_SPE_ABI
19264 && SPE_VECTOR_MODE (mode)
19265 && !SPE_CONST_OFFSET_OK (offset)))
19266 {
19267 /* Whomever calls us must make sure r11 is available in the
19268 flow path of instructions in the prologue. */
19269 offset_rtx = gen_rtx_REG (Pmode, 11);
19270 emit_move_insn (offset_rtx, int_rtx);
19271
19272 replacea = offset_rtx;
19273 replaceb = int_rtx;
19274 }
19275 else
19276 {
19277 offset_rtx = int_rtx;
19278 replacea = NULL_RTX;
19279 replaceb = NULL_RTX;
19280 }
19281
19282 reg = gen_rtx_REG (mode, regno);
19283 addr = gen_rtx_PLUS (Pmode, frame_reg, offset_rtx);
19284 mem = gen_frame_mem (mode, addr);
19285
19286 insn = emit_move_insn (mem, reg);
19287
19288 rs6000_frame_related (insn, frame_ptr, total_size, replacea, replaceb);
19289 }
19290
19291 /* Emit an offset memory reference suitable for a frame store, while
19292 converting to a valid addressing mode. */
19293
19294 static rtx
19295 gen_frame_mem_offset (enum machine_mode mode, rtx reg, int offset)
19296 {
19297 rtx int_rtx, offset_rtx;
19298
19299 int_rtx = GEN_INT (offset);
19300
19301 if ((TARGET_SPE_ABI && SPE_VECTOR_MODE (mode))
19302 || (TARGET_E500_DOUBLE && mode == DFmode))
19303 {
19304 offset_rtx = gen_rtx_REG (Pmode, FIXED_SCRATCH);
19305 emit_move_insn (offset_rtx, int_rtx);
19306 }
19307 else
19308 offset_rtx = int_rtx;
19309
19310 return gen_frame_mem (mode, gen_rtx_PLUS (Pmode, reg, offset_rtx));
19311 }
19312
19313 /* Look for user-defined global regs. We should not save and restore these,
19314 and cannot use stmw/lmw if there are any in its range. */
19315
19316 static bool
19317 no_global_regs_above (int first, bool gpr)
19318 {
19319 int i;
19320 int last = gpr ? 32 : 64;
19321 for (i = first; i < last; i++)
19322 if (global_regs[i])
19323 return false;
19324 return true;
19325 }
19326
19327 #ifndef TARGET_FIX_AND_CONTINUE
19328 #define TARGET_FIX_AND_CONTINUE 0
19329 #endif
19330
19331 /* It's really GPR 13 and FPR 14, but we need the smaller of the two. */
19332 #define FIRST_SAVRES_REGISTER FIRST_SAVED_GP_REGNO
19333 #define LAST_SAVRES_REGISTER 31
19334 #define N_SAVRES_REGISTERS (LAST_SAVRES_REGISTER - FIRST_SAVRES_REGISTER + 1)
19335
19336 static GTY(()) rtx savres_routine_syms[N_SAVRES_REGISTERS][8];
19337
19338 /* Temporary holding space for an out-of-line register save/restore
19339 routine name. */
19340 static char savres_routine_name[30];
19341
19342 /* Return the name for an out-of-line register save/restore routine.
19343 We are saving/restoring GPRs if GPR is true. */
19344
19345 static char *
19346 rs6000_savres_routine_name (rs6000_stack_t *info, int regno,
19347 bool savep, bool gpr, bool lr)
19348 {
19349 const char *prefix = "";
19350 const char *suffix = "";
19351
19352 /* Different targets are supposed to define
19353 {SAVE,RESTORE}_FP_{PREFIX,SUFFIX} with the idea that the needed
19354 routine name could be defined with:
19355
19356 sprintf (name, "%s%d%s", SAVE_FP_PREFIX, regno, SAVE_FP_SUFFIX)
19357
19358 This is a nice idea in practice, but in reality, things are
19359 complicated in several ways:
19360
19361 - ELF targets have save/restore routines for GPRs.
19362
19363 - SPE targets use different prefixes for 32/64-bit registers, and
19364 neither of them fit neatly in the FOO_{PREFIX,SUFFIX} regimen.
19365
19366 - PPC64 ELF targets have routines for save/restore of GPRs that
19367 differ in what they do with the link register, so having a set
19368 prefix doesn't work. (We only use one of the save routines at
19369 the moment, though.)
19370
19371 - PPC32 elf targets have "exit" versions of the restore routines
19372 that restore the link register and can save some extra space.
19373 These require an extra suffix. (There are also "tail" versions
19374 of the restore routines and "GOT" versions of the save routines,
19375 but we don't generate those at present. Same problems apply,
19376 though.)
19377
19378 We deal with all this by synthesizing our own prefix/suffix and
19379 using that for the simple sprintf call shown above. */
19380 if (TARGET_SPE)
19381 {
19382 /* No floating point saves on the SPE. */
19383 gcc_assert (gpr);
19384
19385 if (savep)
19386 prefix = info->spe_64bit_regs_used ? "_save64gpr_" : "_save32gpr_";
19387 else
19388 prefix = info->spe_64bit_regs_used ? "_rest64gpr_" : "_rest32gpr_";
19389
19390 if (lr)
19391 suffix = "_x";
19392 }
19393 else if (DEFAULT_ABI == ABI_V4)
19394 {
19395 if (TARGET_64BIT)
19396 goto aix_names;
19397
19398 if (gpr)
19399 prefix = savep ? "_savegpr_" : "_restgpr_";
19400 else
19401 prefix = savep ? "_savefpr_" : "_restfpr_";
19402
19403 if (lr)
19404 suffix = "_x";
19405 }
19406 else if (DEFAULT_ABI == ABI_AIX)
19407 {
19408 #ifndef POWERPC_LINUX
19409 /* No out-of-line save/restore routines for GPRs on AIX. */
19410 gcc_assert (!TARGET_AIX || !gpr);
19411 #endif
19412
19413 aix_names:
19414 if (gpr)
19415 prefix = (savep
19416 ? (lr ? "_savegpr0_" : "_savegpr1_")
19417 : (lr ? "_restgpr0_" : "_restgpr1_"));
19418 #ifdef POWERPC_LINUX
19419 else if (lr)
19420 prefix = (savep ? "_savefpr_" : "_restfpr_");
19421 #endif
19422 else
19423 {
19424 prefix = savep ? SAVE_FP_PREFIX : RESTORE_FP_PREFIX;
19425 suffix = savep ? SAVE_FP_SUFFIX : RESTORE_FP_SUFFIX;
19426 }
19427 }
19428 else if (DEFAULT_ABI == ABI_DARWIN)
19429 sorry ("Out-of-line save/restore routines not supported on Darwin");
19430
19431 sprintf (savres_routine_name, "%s%d%s", prefix, regno, suffix);
19432
19433 return savres_routine_name;
19434 }
19435
19436 /* Return an RTL SYMBOL_REF for an out-of-line register save/restore routine.
19437 We are saving/restoring GPRs if GPR is true. */
19438
19439 static rtx
19440 rs6000_savres_routine_sym (rs6000_stack_t *info, bool savep,
19441 bool gpr, bool lr)
19442 {
19443 int regno = gpr ? info->first_gp_reg_save : (info->first_fp_reg_save - 32);
19444 rtx sym;
19445 int select = ((savep ? 1 : 0) << 2
19446 | ((TARGET_SPE_ABI
19447 /* On the SPE, we never have any FPRs, but we do have
19448 32/64-bit versions of the routines. */
19449 ? (info->spe_64bit_regs_used ? 1 : 0)
19450 : (gpr ? 1 : 0)) << 1)
19451 | (lr ? 1: 0));
19452
19453 /* Don't generate bogus routine names. */
19454 gcc_assert (FIRST_SAVRES_REGISTER <= regno
19455 && regno <= LAST_SAVRES_REGISTER);
19456
19457 sym = savres_routine_syms[regno-FIRST_SAVRES_REGISTER][select];
19458
19459 if (sym == NULL)
19460 {
19461 char *name;
19462
19463 name = rs6000_savres_routine_name (info, regno, savep, gpr, lr);
19464
19465 sym = savres_routine_syms[regno-FIRST_SAVRES_REGISTER][select]
19466 = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (name));
19467 SYMBOL_REF_FLAGS (sym) |= SYMBOL_FLAG_FUNCTION;
19468 }
19469
19470 return sym;
19471 }
19472
19473 /* Emit a sequence of insns, including a stack tie if needed, for
19474 resetting the stack pointer. If SAVRES is true, then don't reset the
19475 stack pointer, but move the base of the frame into r11 for use by
19476 out-of-line register restore routines. */
19477
19478 static rtx
19479 rs6000_emit_stack_reset (rs6000_stack_t *info,
19480 rtx sp_reg_rtx, rtx frame_reg_rtx,
19481 int sp_offset, bool savres)
19482 {
19483 /* This blockage is needed so that sched doesn't decide to move
19484 the sp change before the register restores. */
19485 if (frame_reg_rtx != sp_reg_rtx
19486 || (TARGET_SPE_ABI
19487 && info->spe_64bit_regs_used != 0
19488 && info->first_gp_reg_save != 32))
19489 rs6000_emit_stack_tie ();
19490
19491 if (frame_reg_rtx != sp_reg_rtx)
19492 {
19493 if (sp_offset != 0)
19494 {
19495 rtx dest_reg = savres ? gen_rtx_REG (Pmode, 11) : sp_reg_rtx;
19496 return emit_insn (gen_add3_insn (dest_reg, frame_reg_rtx,
19497 GEN_INT (sp_offset)));
19498 }
19499 else if (!savres)
19500 return emit_move_insn (sp_reg_rtx, frame_reg_rtx);
19501 }
19502 else if (sp_offset != 0)
19503 {
19504 /* If we are restoring registers out-of-line, we will be using the
19505 "exit" variants of the restore routines, which will reset the
19506 stack for us. But we do need to point r11 into the right place
19507 for those routines. */
19508 rtx dest_reg = (savres
19509 ? gen_rtx_REG (Pmode, 11)
19510 : sp_reg_rtx);
19511
19512 rtx insn = emit_insn (gen_add3_insn (dest_reg, sp_reg_rtx,
19513 GEN_INT (sp_offset)));
19514 if (!savres)
19515 return insn;
19516 }
19517 return NULL_RTX;
19518 }
19519
19520 /* Construct a parallel rtx describing the effect of a call to an
19521 out-of-line register save/restore routine. */
19522
19523 static rtx
19524 rs6000_make_savres_rtx (rs6000_stack_t *info,
19525 rtx frame_reg_rtx, int save_area_offset,
19526 enum machine_mode reg_mode,
19527 bool savep, bool gpr, bool lr)
19528 {
19529 int i;
19530 int offset, start_reg, end_reg, n_regs;
19531 int reg_size = GET_MODE_SIZE (reg_mode);
19532 rtx sym;
19533 rtvec p;
19534
19535 offset = 0;
19536 start_reg = (gpr
19537 ? info->first_gp_reg_save
19538 : info->first_fp_reg_save);
19539 end_reg = gpr ? 32 : 64;
19540 n_regs = end_reg - start_reg;
19541 p = rtvec_alloc ((lr ? 4 : 3) + n_regs);
19542
19543 if (!savep && lr)
19544 RTVEC_ELT (p, offset++) = gen_rtx_RETURN (VOIDmode);
19545
19546 RTVEC_ELT (p, offset++)
19547 = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 65));
19548
19549 sym = rs6000_savres_routine_sym (info, savep, gpr, lr);
19550 RTVEC_ELT (p, offset++) = gen_rtx_USE (VOIDmode, sym);
19551 RTVEC_ELT (p, offset++)
19552 = gen_rtx_USE (VOIDmode,
19553 gen_rtx_REG (Pmode, DEFAULT_ABI != ABI_AIX ? 11
19554 : gpr && !lr ? 12
19555 : 1));
19556
19557 for (i = 0; i < end_reg - start_reg; i++)
19558 {
19559 rtx addr, reg, mem;
19560 reg = gen_rtx_REG (reg_mode, start_reg + i);
19561 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
19562 GEN_INT (save_area_offset + reg_size*i));
19563 mem = gen_frame_mem (reg_mode, addr);
19564
19565 RTVEC_ELT (p, i + offset) = gen_rtx_SET (VOIDmode,
19566 savep ? mem : reg,
19567 savep ? reg : mem);
19568 }
19569
19570 if (savep && lr)
19571 {
19572 rtx addr, reg, mem;
19573 reg = gen_rtx_REG (Pmode, 0);
19574 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
19575 GEN_INT (info->lr_save_offset));
19576 mem = gen_frame_mem (Pmode, addr);
19577 RTVEC_ELT (p, i + offset) = gen_rtx_SET (VOIDmode, mem, reg);
19578 }
19579
19580 return gen_rtx_PARALLEL (VOIDmode, p);
19581 }
19582
19583 /* Determine whether the gp REG is really used. */
19584
19585 static bool
19586 rs6000_reg_live_or_pic_offset_p (int reg)
19587 {
19588 return ((df_regs_ever_live_p (reg)
19589 && (!call_used_regs[reg]
19590 || (reg == RS6000_PIC_OFFSET_TABLE_REGNUM
19591 && TARGET_TOC && TARGET_MINIMAL_TOC)))
19592 || (reg == RS6000_PIC_OFFSET_TABLE_REGNUM
19593 && ((DEFAULT_ABI == ABI_V4 && flag_pic != 0)
19594 || (DEFAULT_ABI == ABI_DARWIN && flag_pic))));
19595 }
19596
19597 enum {
19598 SAVRES_MULTIPLE = 0x1,
19599 SAVRES_INLINE_FPRS = 0x2,
19600 SAVRES_INLINE_GPRS = 0x4,
19601 SAVRES_NOINLINE_GPRS_SAVES_LR = 0x8,
19602 SAVRES_NOINLINE_FPRS_SAVES_LR = 0x10,
19603 SAVRES_NOINLINE_FPRS_DOESNT_RESTORE_LR = 0x20
19604 };
19605
19606 /* Determine the strategy for savings/restoring registers. */
19607
19608 static int
19609 rs6000_savres_strategy (rs6000_stack_t *info, bool savep,
19610 int using_static_chain_p, int sibcall)
19611 {
19612 bool using_multiple_p;
19613 bool common;
19614 bool savres_fprs_inline;
19615 bool savres_gprs_inline;
19616 bool noclobber_global_gprs
19617 = no_global_regs_above (info->first_gp_reg_save, /*gpr=*/true);
19618 int strategy;
19619
19620 using_multiple_p = (TARGET_MULTIPLE && ! TARGET_POWERPC64
19621 && (!TARGET_SPE_ABI
19622 || info->spe_64bit_regs_used == 0)
19623 && info->first_gp_reg_save < 31
19624 && noclobber_global_gprs);
19625 /* Don't bother to try to save things out-of-line if r11 is occupied
19626 by the static chain. It would require too much fiddling and the
19627 static chain is rarely used anyway. */
19628 common = (using_static_chain_p
19629 || sibcall
19630 || crtl->calls_eh_return
19631 || !info->lr_save_p
19632 || cfun->machine->ra_need_lr
19633 || info->total_size > 32767);
19634 savres_fprs_inline = (common
19635 || info->first_fp_reg_save == 64
19636 || !no_global_regs_above (info->first_fp_reg_save,
19637 /*gpr=*/false)
19638 /* The out-of-line FP routines use
19639 double-precision stores; we can't use those
19640 routines if we don't have such stores. */
19641 || (TARGET_HARD_FLOAT && !TARGET_DOUBLE_FLOAT)
19642 || FP_SAVE_INLINE (info->first_fp_reg_save));
19643 savres_gprs_inline = (common
19644 /* Saving CR interferes with the exit routines
19645 used on the SPE, so just punt here. */
19646 || (!savep
19647 && TARGET_SPE_ABI
19648 && info->spe_64bit_regs_used != 0
19649 && info->cr_save_p != 0)
19650 || info->first_gp_reg_save == 32
19651 || !noclobber_global_gprs
19652 || GP_SAVE_INLINE (info->first_gp_reg_save));
19653
19654 if (savep)
19655 /* If we are going to use store multiple, then don't even bother
19656 with the out-of-line routines, since the store-multiple instruction
19657 will always be smaller. */
19658 savres_gprs_inline = savres_gprs_inline || using_multiple_p;
19659 else
19660 {
19661 /* The situation is more complicated with load multiple. We'd
19662 prefer to use the out-of-line routines for restores, since the
19663 "exit" out-of-line routines can handle the restore of LR and
19664 the frame teardown. But we can only use the out-of-line
19665 routines if we know that we've used store multiple or
19666 out-of-line routines in the prologue, i.e. if we've saved all
19667 the registers from first_gp_reg_save. Otherwise, we risk
19668 loading garbage from the stack. Furthermore, we can only use
19669 the "exit" out-of-line gpr restore if we haven't saved any
19670 fprs. */
19671 bool saved_all = !savres_gprs_inline || using_multiple_p;
19672
19673 if (saved_all && info->first_fp_reg_save != 64)
19674 /* We can't use the exit routine; use load multiple if it's
19675 available. */
19676 savres_gprs_inline = savres_gprs_inline || using_multiple_p;
19677 }
19678
19679 strategy = (using_multiple_p
19680 | (savres_fprs_inline << 1)
19681 | (savres_gprs_inline << 2));
19682 #ifdef POWERPC_LINUX
19683 if (TARGET_64BIT)
19684 {
19685 if (!savres_fprs_inline)
19686 strategy |= SAVRES_NOINLINE_FPRS_SAVES_LR;
19687 else if (!savres_gprs_inline && info->first_fp_reg_save == 64)
19688 strategy |= SAVRES_NOINLINE_GPRS_SAVES_LR;
19689 }
19690 #else
19691 if (TARGET_AIX && !savres_fprs_inline)
19692 strategy |= SAVRES_NOINLINE_FPRS_DOESNT_RESTORE_LR;
19693 #endif
19694 return strategy;
19695 }
19696
19697 /* Emit function prologue as insns. */
19698
19699 void
19700 rs6000_emit_prologue (void)
19701 {
19702 rs6000_stack_t *info = rs6000_stack_info ();
19703 enum machine_mode reg_mode = Pmode;
19704 int reg_size = TARGET_32BIT ? 4 : 8;
19705 rtx sp_reg_rtx = gen_rtx_REG (Pmode, STACK_POINTER_REGNUM);
19706 rtx frame_ptr_rtx = gen_rtx_REG (Pmode, 12);
19707 rtx frame_reg_rtx = sp_reg_rtx;
19708 rtx cr_save_rtx = NULL_RTX;
19709 rtx insn;
19710 int strategy;
19711 int saving_FPRs_inline;
19712 int saving_GPRs_inline;
19713 int using_store_multiple;
19714 int using_static_chain_p = (cfun->static_chain_decl != NULL_TREE
19715 && df_regs_ever_live_p (STATIC_CHAIN_REGNUM)
19716 && call_used_regs[STATIC_CHAIN_REGNUM]);
19717 HOST_WIDE_INT sp_offset = 0;
19718
19719 if (flag_stack_usage)
19720 current_function_static_stack_size = info->total_size;
19721
19722 if (flag_stack_check == STATIC_BUILTIN_STACK_CHECK && info->total_size)
19723 rs6000_emit_probe_stack_range (STACK_CHECK_PROTECT, info->total_size);
19724
19725 if (TARGET_FIX_AND_CONTINUE)
19726 {
19727 /* gdb on darwin arranges to forward a function from the old
19728 address by modifying the first 5 instructions of the function
19729 to branch to the overriding function. This is necessary to
19730 permit function pointers that point to the old function to
19731 actually forward to the new function. */
19732 emit_insn (gen_nop ());
19733 emit_insn (gen_nop ());
19734 emit_insn (gen_nop ());
19735 emit_insn (gen_nop ());
19736 emit_insn (gen_nop ());
19737 }
19738
19739 if (TARGET_SPE_ABI && info->spe_64bit_regs_used != 0)
19740 {
19741 reg_mode = V2SImode;
19742 reg_size = 8;
19743 }
19744
19745 strategy = rs6000_savres_strategy (info, /*savep=*/true,
19746 /*static_chain_p=*/using_static_chain_p,
19747 /*sibcall=*/0);
19748 using_store_multiple = strategy & SAVRES_MULTIPLE;
19749 saving_FPRs_inline = strategy & SAVRES_INLINE_FPRS;
19750 saving_GPRs_inline = strategy & SAVRES_INLINE_GPRS;
19751
19752 /* For V.4, update stack before we do any saving and set back pointer. */
19753 if (! WORLD_SAVE_P (info)
19754 && info->push_p
19755 && (DEFAULT_ABI == ABI_V4
19756 || crtl->calls_eh_return))
19757 {
19758 bool need_r11 = (TARGET_SPE
19759 ? (!saving_GPRs_inline
19760 && info->spe_64bit_regs_used == 0)
19761 : (!saving_FPRs_inline || !saving_GPRs_inline));
19762 rtx copy_reg = need_r11 ? gen_rtx_REG (Pmode, 11) : NULL;
19763
19764 if (info->total_size < 32767)
19765 sp_offset = info->total_size;
19766 else if (need_r11)
19767 frame_reg_rtx = copy_reg;
19768 else if (info->cr_save_p
19769 || info->lr_save_p
19770 || info->first_fp_reg_save < 64
19771 || info->first_gp_reg_save < 32
19772 || info->altivec_size != 0
19773 || info->vrsave_mask != 0
19774 || crtl->calls_eh_return)
19775 {
19776 copy_reg = frame_ptr_rtx;
19777 frame_reg_rtx = copy_reg;
19778 }
19779 else
19780 {
19781 /* The prologue won't be saving any regs so there is no need
19782 to set up a frame register to access any frame save area.
19783 We also won't be using sp_offset anywhere below, but set
19784 the correct value anyway to protect against future
19785 changes to this function. */
19786 sp_offset = info->total_size;
19787 }
19788 rs6000_emit_allocate_stack (info->total_size, copy_reg);
19789 if (frame_reg_rtx != sp_reg_rtx)
19790 rs6000_emit_stack_tie ();
19791 }
19792
19793 /* Handle world saves specially here. */
19794 if (WORLD_SAVE_P (info))
19795 {
19796 int i, j, sz;
19797 rtx treg;
19798 rtvec p;
19799 rtx reg0;
19800
19801 /* save_world expects lr in r0. */
19802 reg0 = gen_rtx_REG (Pmode, 0);
19803 if (info->lr_save_p)
19804 {
19805 insn = emit_move_insn (reg0,
19806 gen_rtx_REG (Pmode, LR_REGNO));
19807 RTX_FRAME_RELATED_P (insn) = 1;
19808 }
19809
19810 /* The SAVE_WORLD and RESTORE_WORLD routines make a number of
19811 assumptions about the offsets of various bits of the stack
19812 frame. */
19813 gcc_assert (info->gp_save_offset == -220
19814 && info->fp_save_offset == -144
19815 && info->lr_save_offset == 8
19816 && info->cr_save_offset == 4
19817 && info->push_p
19818 && info->lr_save_p
19819 && (!crtl->calls_eh_return
19820 || info->ehrd_offset == -432)
19821 && info->vrsave_save_offset == -224
19822 && info->altivec_save_offset == -416);
19823
19824 treg = gen_rtx_REG (SImode, 11);
19825 emit_move_insn (treg, GEN_INT (-info->total_size));
19826
19827 /* SAVE_WORLD takes the caller's LR in R0 and the frame size
19828 in R11. It also clobbers R12, so beware! */
19829
19830 /* Preserve CR2 for save_world prologues */
19831 sz = 5;
19832 sz += 32 - info->first_gp_reg_save;
19833 sz += 64 - info->first_fp_reg_save;
19834 sz += LAST_ALTIVEC_REGNO - info->first_altivec_reg_save + 1;
19835 p = rtvec_alloc (sz);
19836 j = 0;
19837 RTVEC_ELT (p, j++) = gen_rtx_CLOBBER (VOIDmode,
19838 gen_rtx_REG (SImode,
19839 LR_REGNO));
19840 RTVEC_ELT (p, j++) = gen_rtx_USE (VOIDmode,
19841 gen_rtx_SYMBOL_REF (Pmode,
19842 "*save_world"));
19843 /* We do floats first so that the instruction pattern matches
19844 properly. */
19845 for (i = 0; i < 64 - info->first_fp_reg_save; i++)
19846 {
19847 rtx reg = gen_rtx_REG (((TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT)
19848 ? DFmode : SFmode),
19849 info->first_fp_reg_save + i);
19850 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
19851 GEN_INT (info->fp_save_offset
19852 + sp_offset + 8 * i));
19853 rtx mem = gen_frame_mem (((TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT)
19854 ? DFmode : SFmode), addr);
19855
19856 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, mem, reg);
19857 }
19858 for (i = 0; info->first_altivec_reg_save + i <= LAST_ALTIVEC_REGNO; i++)
19859 {
19860 rtx reg = gen_rtx_REG (V4SImode, info->first_altivec_reg_save + i);
19861 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
19862 GEN_INT (info->altivec_save_offset
19863 + sp_offset + 16 * i));
19864 rtx mem = gen_frame_mem (V4SImode, addr);
19865
19866 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, mem, reg);
19867 }
19868 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
19869 {
19870 rtx reg = gen_rtx_REG (reg_mode, info->first_gp_reg_save + i);
19871 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
19872 GEN_INT (info->gp_save_offset
19873 + sp_offset + reg_size * i));
19874 rtx mem = gen_frame_mem (reg_mode, addr);
19875
19876 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, mem, reg);
19877 }
19878
19879 {
19880 /* CR register traditionally saved as CR2. */
19881 rtx reg = gen_rtx_REG (reg_mode, CR2_REGNO);
19882 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
19883 GEN_INT (info->cr_save_offset
19884 + sp_offset));
19885 rtx mem = gen_frame_mem (reg_mode, addr);
19886
19887 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, mem, reg);
19888 }
19889 /* Explain about use of R0. */
19890 if (info->lr_save_p)
19891 {
19892 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
19893 GEN_INT (info->lr_save_offset
19894 + sp_offset));
19895 rtx mem = gen_frame_mem (reg_mode, addr);
19896
19897 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, mem, reg0);
19898 }
19899 /* Explain what happens to the stack pointer. */
19900 {
19901 rtx newval = gen_rtx_PLUS (Pmode, sp_reg_rtx, treg);
19902 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, sp_reg_rtx, newval);
19903 }
19904
19905 insn = emit_insn (gen_rtx_PARALLEL (VOIDmode, p));
19906 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
19907 treg, GEN_INT (-info->total_size));
19908 sp_offset = info->total_size;
19909 }
19910
19911 /* If we use the link register, get it into r0. */
19912 if (!WORLD_SAVE_P (info) && info->lr_save_p)
19913 {
19914 rtx addr, reg, mem;
19915
19916 insn = emit_move_insn (gen_rtx_REG (Pmode, 0),
19917 gen_rtx_REG (Pmode, LR_REGNO));
19918 RTX_FRAME_RELATED_P (insn) = 1;
19919
19920 if (!(strategy & (SAVRES_NOINLINE_GPRS_SAVES_LR
19921 | SAVRES_NOINLINE_FPRS_SAVES_LR)))
19922 {
19923 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
19924 GEN_INT (info->lr_save_offset + sp_offset));
19925 reg = gen_rtx_REG (Pmode, 0);
19926 mem = gen_rtx_MEM (Pmode, addr);
19927 /* This should not be of rs6000_sr_alias_set, because of
19928 __builtin_return_address. */
19929
19930 insn = emit_move_insn (mem, reg);
19931 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
19932 NULL_RTX, NULL_RTX);
19933 }
19934 }
19935
19936 /* If we need to save CR, put it into r12 or r11. */
19937 if (!WORLD_SAVE_P (info) && info->cr_save_p && frame_reg_rtx != frame_ptr_rtx)
19938 {
19939 rtx set;
19940
19941 cr_save_rtx
19942 = gen_rtx_REG (SImode, DEFAULT_ABI == ABI_AIX && !saving_GPRs_inline
19943 ? 11 : 12);
19944 insn = emit_insn (gen_movesi_from_cr (cr_save_rtx));
19945 RTX_FRAME_RELATED_P (insn) = 1;
19946 /* Now, there's no way that dwarf2out_frame_debug_expr is going
19947 to understand '(unspec:SI [(reg:CC 68) ...] UNSPEC_MOVESI_FROM_CR)'.
19948 But that's OK. All we have to do is specify that _one_ condition
19949 code register is saved in this stack slot. The thrower's epilogue
19950 will then restore all the call-saved registers.
19951 We use CR2_REGNO (70) to be compatible with gcc-2.95 on Linux. */
19952 set = gen_rtx_SET (VOIDmode, cr_save_rtx,
19953 gen_rtx_REG (SImode, CR2_REGNO));
19954 add_reg_note (insn, REG_FRAME_RELATED_EXPR, set);
19955 }
19956
19957 /* Do any required saving of fpr's. If only one or two to save, do
19958 it ourselves. Otherwise, call function. */
19959 if (!WORLD_SAVE_P (info) && saving_FPRs_inline)
19960 {
19961 int i;
19962 for (i = 0; i < 64 - info->first_fp_reg_save; i++)
19963 if ((df_regs_ever_live_p (info->first_fp_reg_save+i)
19964 && ! call_used_regs[info->first_fp_reg_save+i]))
19965 emit_frame_save (frame_reg_rtx, frame_ptr_rtx,
19966 (TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT)
19967 ? DFmode : SFmode,
19968 info->first_fp_reg_save + i,
19969 info->fp_save_offset + sp_offset + 8 * i,
19970 info->total_size);
19971 }
19972 else if (!WORLD_SAVE_P (info) && info->first_fp_reg_save != 64)
19973 {
19974 rtx par;
19975
19976 par = rs6000_make_savres_rtx (info, frame_reg_rtx,
19977 info->fp_save_offset + sp_offset,
19978 DFmode,
19979 /*savep=*/true, /*gpr=*/false,
19980 /*lr=*/(strategy
19981 & SAVRES_NOINLINE_FPRS_SAVES_LR)
19982 != 0);
19983 insn = emit_insn (par);
19984 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
19985 NULL_RTX, NULL_RTX);
19986 }
19987
19988 /* Save GPRs. This is done as a PARALLEL if we are using
19989 the store-multiple instructions. */
19990 if (!WORLD_SAVE_P (info)
19991 && TARGET_SPE_ABI
19992 && info->spe_64bit_regs_used != 0
19993 && info->first_gp_reg_save != 32)
19994 {
19995 int i;
19996 rtx spe_save_area_ptr;
19997
19998 /* Determine whether we can address all of the registers that need
19999 to be saved with an offset from the stack pointer that fits in
20000 the small const field for SPE memory instructions. */
20001 int spe_regs_addressable_via_sp
20002 = (SPE_CONST_OFFSET_OK(info->spe_gp_save_offset + sp_offset
20003 + (32 - info->first_gp_reg_save - 1) * reg_size)
20004 && saving_GPRs_inline);
20005 int spe_offset;
20006
20007 if (spe_regs_addressable_via_sp)
20008 {
20009 spe_save_area_ptr = frame_reg_rtx;
20010 spe_offset = info->spe_gp_save_offset + sp_offset;
20011 }
20012 else
20013 {
20014 /* Make r11 point to the start of the SPE save area. We need
20015 to be careful here if r11 is holding the static chain. If
20016 it is, then temporarily save it in r0. We would use r0 as
20017 our base register here, but using r0 as a base register in
20018 loads and stores means something different from what we
20019 would like. */
20020 int ool_adjust = (saving_GPRs_inline
20021 ? 0
20022 : (info->first_gp_reg_save
20023 - (FIRST_SAVRES_REGISTER+1))*8);
20024 HOST_WIDE_INT offset = (info->spe_gp_save_offset
20025 + sp_offset - ool_adjust);
20026
20027 if (using_static_chain_p)
20028 {
20029 rtx r0 = gen_rtx_REG (Pmode, 0);
20030 gcc_assert (info->first_gp_reg_save > 11);
20031
20032 emit_move_insn (r0, gen_rtx_REG (Pmode, 11));
20033 }
20034
20035 spe_save_area_ptr = gen_rtx_REG (Pmode, 11);
20036 insn = emit_insn (gen_addsi3 (spe_save_area_ptr,
20037 frame_reg_rtx,
20038 GEN_INT (offset)));
20039 /* We need to make sure the move to r11 gets noted for
20040 properly outputting unwind information. */
20041 if (!saving_GPRs_inline)
20042 rs6000_frame_related (insn, frame_reg_rtx, offset,
20043 NULL_RTX, NULL_RTX);
20044 spe_offset = 0;
20045 }
20046
20047 if (saving_GPRs_inline)
20048 {
20049 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
20050 if (rs6000_reg_live_or_pic_offset_p (info->first_gp_reg_save + i))
20051 {
20052 rtx reg = gen_rtx_REG (reg_mode, info->first_gp_reg_save + i);
20053 rtx offset, addr, mem;
20054
20055 /* We're doing all this to ensure that the offset fits into
20056 the immediate offset of 'evstdd'. */
20057 gcc_assert (SPE_CONST_OFFSET_OK (reg_size * i + spe_offset));
20058
20059 offset = GEN_INT (reg_size * i + spe_offset);
20060 addr = gen_rtx_PLUS (Pmode, spe_save_area_ptr, offset);
20061 mem = gen_rtx_MEM (V2SImode, addr);
20062
20063 insn = emit_move_insn (mem, reg);
20064
20065 rs6000_frame_related (insn, spe_save_area_ptr,
20066 info->spe_gp_save_offset
20067 + sp_offset + reg_size * i,
20068 offset, const0_rtx);
20069 }
20070 }
20071 else
20072 {
20073 rtx par;
20074
20075 par = rs6000_make_savres_rtx (info, gen_rtx_REG (Pmode, 11),
20076 0, reg_mode,
20077 /*savep=*/true, /*gpr=*/true,
20078 /*lr=*/false);
20079 insn = emit_insn (par);
20080 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
20081 NULL_RTX, NULL_RTX);
20082 }
20083
20084
20085 /* Move the static chain pointer back. */
20086 if (using_static_chain_p && !spe_regs_addressable_via_sp)
20087 emit_move_insn (gen_rtx_REG (Pmode, 11), gen_rtx_REG (Pmode, 0));
20088 }
20089 else if (!WORLD_SAVE_P (info) && !saving_GPRs_inline)
20090 {
20091 rtx par;
20092
20093 /* Need to adjust r11 (r12) if we saved any FPRs. */
20094 if (info->first_fp_reg_save != 64)
20095 {
20096 rtx dest_reg = gen_rtx_REG (reg_mode, DEFAULT_ABI == ABI_AIX
20097 ? 12 : 11);
20098 rtx offset = GEN_INT (sp_offset
20099 + (-8 * (64-info->first_fp_reg_save)));
20100 emit_insn (gen_add3_insn (dest_reg, frame_reg_rtx, offset));
20101 }
20102
20103 par = rs6000_make_savres_rtx (info, frame_reg_rtx,
20104 info->gp_save_offset + sp_offset,
20105 reg_mode,
20106 /*savep=*/true, /*gpr=*/true,
20107 /*lr=*/(strategy
20108 & SAVRES_NOINLINE_GPRS_SAVES_LR)
20109 != 0);
20110 insn = emit_insn (par);
20111 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
20112 NULL_RTX, NULL_RTX);
20113 }
20114 else if (!WORLD_SAVE_P (info) && using_store_multiple)
20115 {
20116 rtvec p;
20117 int i;
20118 p = rtvec_alloc (32 - info->first_gp_reg_save);
20119 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
20120 {
20121 rtx addr, reg, mem;
20122 reg = gen_rtx_REG (reg_mode, info->first_gp_reg_save + i);
20123 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
20124 GEN_INT (info->gp_save_offset
20125 + sp_offset
20126 + reg_size * i));
20127 mem = gen_frame_mem (reg_mode, addr);
20128
20129 RTVEC_ELT (p, i) = gen_rtx_SET (VOIDmode, mem, reg);
20130 }
20131 insn = emit_insn (gen_rtx_PARALLEL (VOIDmode, p));
20132 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
20133 NULL_RTX, NULL_RTX);
20134 }
20135 else if (!WORLD_SAVE_P (info))
20136 {
20137 int i;
20138 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
20139 if (rs6000_reg_live_or_pic_offset_p (info->first_gp_reg_save + i))
20140 {
20141 rtx addr, reg, mem;
20142 reg = gen_rtx_REG (reg_mode, info->first_gp_reg_save + i);
20143
20144 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
20145 GEN_INT (info->gp_save_offset
20146 + sp_offset
20147 + reg_size * i));
20148 mem = gen_frame_mem (reg_mode, addr);
20149
20150 insn = emit_move_insn (mem, reg);
20151 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
20152 NULL_RTX, NULL_RTX);
20153 }
20154 }
20155
20156 /* ??? There's no need to emit actual instructions here, but it's the
20157 easiest way to get the frame unwind information emitted. */
20158 if (crtl->calls_eh_return)
20159 {
20160 unsigned int i, regno;
20161
20162 /* In AIX ABI we need to pretend we save r2 here. */
20163 if (TARGET_AIX)
20164 {
20165 rtx addr, reg, mem;
20166
20167 reg = gen_rtx_REG (reg_mode, 2);
20168 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
20169 GEN_INT (sp_offset + 5 * reg_size));
20170 mem = gen_frame_mem (reg_mode, addr);
20171
20172 insn = emit_move_insn (mem, reg);
20173 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
20174 NULL_RTX, NULL_RTX);
20175 PATTERN (insn) = gen_blockage ();
20176 }
20177
20178 for (i = 0; ; ++i)
20179 {
20180 regno = EH_RETURN_DATA_REGNO (i);
20181 if (regno == INVALID_REGNUM)
20182 break;
20183
20184 emit_frame_save (frame_reg_rtx, frame_ptr_rtx, reg_mode, regno,
20185 info->ehrd_offset + sp_offset
20186 + reg_size * (int) i,
20187 info->total_size);
20188 }
20189 }
20190
20191 /* Save CR if we use any that must be preserved. */
20192 if (!WORLD_SAVE_P (info) && info->cr_save_p)
20193 {
20194 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
20195 GEN_INT (info->cr_save_offset + sp_offset));
20196 rtx mem = gen_frame_mem (SImode, addr);
20197 /* See the large comment above about why CR2_REGNO is used. */
20198 rtx magic_eh_cr_reg = gen_rtx_REG (SImode, CR2_REGNO);
20199
20200 /* If r12 was used to hold the original sp, copy cr into r0 now
20201 that it's free. */
20202 if (REGNO (frame_reg_rtx) == 12)
20203 {
20204 rtx set;
20205
20206 cr_save_rtx = gen_rtx_REG (SImode, 0);
20207 insn = emit_insn (gen_movesi_from_cr (cr_save_rtx));
20208 RTX_FRAME_RELATED_P (insn) = 1;
20209 set = gen_rtx_SET (VOIDmode, cr_save_rtx, magic_eh_cr_reg);
20210 add_reg_note (insn, REG_FRAME_RELATED_EXPR, set);
20211 }
20212 insn = emit_move_insn (mem, cr_save_rtx);
20213
20214 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
20215 NULL_RTX, NULL_RTX);
20216 }
20217
20218 /* Update stack and set back pointer unless this is V.4,
20219 for which it was done previously. */
20220 if (!WORLD_SAVE_P (info) && info->push_p
20221 && !(DEFAULT_ABI == ABI_V4 || crtl->calls_eh_return))
20222 {
20223 rtx copy_reg = NULL;
20224
20225 if (info->total_size < 32767)
20226 sp_offset = info->total_size;
20227 else if (info->altivec_size != 0
20228 || info->vrsave_mask != 0)
20229 {
20230 copy_reg = frame_ptr_rtx;
20231 frame_reg_rtx = copy_reg;
20232 }
20233 else
20234 sp_offset = info->total_size;
20235 rs6000_emit_allocate_stack (info->total_size, copy_reg);
20236 if (frame_reg_rtx != sp_reg_rtx)
20237 rs6000_emit_stack_tie ();
20238 }
20239
20240 /* Set frame pointer, if needed. */
20241 if (frame_pointer_needed)
20242 {
20243 insn = emit_move_insn (gen_rtx_REG (Pmode, HARD_FRAME_POINTER_REGNUM),
20244 sp_reg_rtx);
20245 RTX_FRAME_RELATED_P (insn) = 1;
20246 }
20247
20248 /* Save AltiVec registers if needed. Save here because the red zone does
20249 not include AltiVec registers. */
20250 if (!WORLD_SAVE_P (info) && TARGET_ALTIVEC_ABI && info->altivec_size != 0)
20251 {
20252 int i;
20253
20254 /* There should be a non inline version of this, for when we
20255 are saving lots of vector registers. */
20256 for (i = info->first_altivec_reg_save; i <= LAST_ALTIVEC_REGNO; ++i)
20257 if (info->vrsave_mask & ALTIVEC_REG_BIT (i))
20258 {
20259 rtx areg, savereg, mem;
20260 int offset;
20261
20262 offset = info->altivec_save_offset + sp_offset
20263 + 16 * (i - info->first_altivec_reg_save);
20264
20265 savereg = gen_rtx_REG (V4SImode, i);
20266
20267 areg = gen_rtx_REG (Pmode, 0);
20268 emit_move_insn (areg, GEN_INT (offset));
20269
20270 /* AltiVec addressing mode is [reg+reg]. */
20271 mem = gen_frame_mem (V4SImode,
20272 gen_rtx_PLUS (Pmode, frame_reg_rtx, areg));
20273
20274 insn = emit_move_insn (mem, savereg);
20275
20276 rs6000_frame_related (insn, frame_ptr_rtx, info->total_size,
20277 areg, GEN_INT (offset));
20278 }
20279 }
20280
20281 /* VRSAVE is a bit vector representing which AltiVec registers
20282 are used. The OS uses this to determine which vector
20283 registers to save on a context switch. We need to save
20284 VRSAVE on the stack frame, add whatever AltiVec registers we
20285 used in this function, and do the corresponding magic in the
20286 epilogue. */
20287
20288 if (TARGET_ALTIVEC && TARGET_ALTIVEC_VRSAVE
20289 && info->vrsave_mask != 0)
20290 {
20291 rtx reg, mem, vrsave;
20292 int offset;
20293
20294 /* Get VRSAVE onto a GPR. Note that ABI_V4 might be using r12
20295 as frame_reg_rtx and r11 as the static chain pointer for
20296 nested functions. */
20297 reg = gen_rtx_REG (SImode, 0);
20298 vrsave = gen_rtx_REG (SImode, VRSAVE_REGNO);
20299 if (TARGET_MACHO)
20300 emit_insn (gen_get_vrsave_internal (reg));
20301 else
20302 emit_insn (gen_rtx_SET (VOIDmode, reg, vrsave));
20303
20304 if (!WORLD_SAVE_P (info))
20305 {
20306 /* Save VRSAVE. */
20307 offset = info->vrsave_save_offset + sp_offset;
20308 mem = gen_frame_mem (SImode,
20309 gen_rtx_PLUS (Pmode, frame_reg_rtx,
20310 GEN_INT (offset)));
20311 insn = emit_move_insn (mem, reg);
20312 }
20313
20314 /* Include the registers in the mask. */
20315 emit_insn (gen_iorsi3 (reg, reg, GEN_INT ((int) info->vrsave_mask)));
20316
20317 insn = emit_insn (generate_set_vrsave (reg, info, 0));
20318 }
20319
20320 /* If we are using RS6000_PIC_OFFSET_TABLE_REGNUM, we need to set it up. */
20321 if ((TARGET_TOC && TARGET_MINIMAL_TOC && get_pool_size () != 0)
20322 || (DEFAULT_ABI == ABI_V4
20323 && (flag_pic == 1 || (flag_pic && TARGET_SECURE_PLT))
20324 && df_regs_ever_live_p (RS6000_PIC_OFFSET_TABLE_REGNUM)))
20325 {
20326 /* If emit_load_toc_table will use the link register, we need to save
20327 it. We use R12 for this purpose because emit_load_toc_table
20328 can use register 0. This allows us to use a plain 'blr' to return
20329 from the procedure more often. */
20330 int save_LR_around_toc_setup = (TARGET_ELF
20331 && DEFAULT_ABI != ABI_AIX
20332 && flag_pic
20333 && ! info->lr_save_p
20334 && EDGE_COUNT (EXIT_BLOCK_PTR->preds) > 0);
20335 if (save_LR_around_toc_setup)
20336 {
20337 rtx lr = gen_rtx_REG (Pmode, LR_REGNO);
20338
20339 insn = emit_move_insn (frame_ptr_rtx, lr);
20340 RTX_FRAME_RELATED_P (insn) = 1;
20341
20342 rs6000_emit_load_toc_table (TRUE);
20343
20344 insn = emit_move_insn (lr, frame_ptr_rtx);
20345 RTX_FRAME_RELATED_P (insn) = 1;
20346 }
20347 else
20348 rs6000_emit_load_toc_table (TRUE);
20349 }
20350
20351 #if TARGET_MACHO
20352 if (DEFAULT_ABI == ABI_DARWIN
20353 && flag_pic && crtl->uses_pic_offset_table)
20354 {
20355 rtx lr = gen_rtx_REG (Pmode, LR_REGNO);
20356 rtx src = gen_rtx_SYMBOL_REF (Pmode, MACHOPIC_FUNCTION_BASE_NAME);
20357
20358 /* Save and restore LR locally around this call (in R0). */
20359 if (!info->lr_save_p)
20360 emit_move_insn (gen_rtx_REG (Pmode, 0), lr);
20361
20362 emit_insn (gen_load_macho_picbase (src));
20363
20364 emit_move_insn (gen_rtx_REG (Pmode,
20365 RS6000_PIC_OFFSET_TABLE_REGNUM),
20366 lr);
20367
20368 if (!info->lr_save_p)
20369 emit_move_insn (lr, gen_rtx_REG (Pmode, 0));
20370 }
20371 #endif
20372 }
20373
20374 /* Write function prologue. */
20375
20376 static void
20377 rs6000_output_function_prologue (FILE *file,
20378 HOST_WIDE_INT size ATTRIBUTE_UNUSED)
20379 {
20380 rs6000_stack_t *info = rs6000_stack_info ();
20381
20382 if (TARGET_DEBUG_STACK)
20383 debug_stack_info (info);
20384
20385 /* Write .extern for any function we will call to save and restore
20386 fp values. */
20387 if (info->first_fp_reg_save < 64
20388 && !FP_SAVE_INLINE (info->first_fp_reg_save))
20389 {
20390 char *name;
20391 int regno = info->first_fp_reg_save - 32;
20392
20393 name = rs6000_savres_routine_name (info, regno, /*savep=*/true,
20394 /*gpr=*/false, /*lr=*/false);
20395 fprintf (file, "\t.extern %s\n", name);
20396
20397 name = rs6000_savres_routine_name (info, regno, /*savep=*/false,
20398 /*gpr=*/false, /*lr=*/true);
20399 fprintf (file, "\t.extern %s\n", name);
20400 }
20401
20402 /* Write .extern for AIX common mode routines, if needed. */
20403 if (! TARGET_POWER && ! TARGET_POWERPC && ! common_mode_defined)
20404 {
20405 fputs ("\t.extern __mulh\n", file);
20406 fputs ("\t.extern __mull\n", file);
20407 fputs ("\t.extern __divss\n", file);
20408 fputs ("\t.extern __divus\n", file);
20409 fputs ("\t.extern __quoss\n", file);
20410 fputs ("\t.extern __quous\n", file);
20411 common_mode_defined = 1;
20412 }
20413
20414 if (! HAVE_prologue)
20415 {
20416 rtx prologue;
20417
20418 start_sequence ();
20419
20420 /* A NOTE_INSN_DELETED is supposed to be at the start and end of
20421 the "toplevel" insn chain. */
20422 emit_note (NOTE_INSN_DELETED);
20423 rs6000_emit_prologue ();
20424 emit_note (NOTE_INSN_DELETED);
20425
20426 /* Expand INSN_ADDRESSES so final() doesn't crash. */
20427 {
20428 rtx insn;
20429 unsigned addr = 0;
20430 for (insn = get_insns (); insn != 0; insn = NEXT_INSN (insn))
20431 {
20432 INSN_ADDRESSES_NEW (insn, addr);
20433 addr += 4;
20434 }
20435 }
20436
20437 prologue = get_insns ();
20438 end_sequence ();
20439
20440 if (TARGET_DEBUG_STACK)
20441 debug_rtx_list (prologue, 100);
20442
20443 emit_insn_before_noloc (prologue, BB_HEAD (ENTRY_BLOCK_PTR->next_bb),
20444 ENTRY_BLOCK_PTR);
20445 }
20446
20447 rs6000_pic_labelno++;
20448 }
20449
20450 /* Non-zero if vmx regs are restored before the frame pop, zero if
20451 we restore after the pop when possible. */
20452 #define ALWAYS_RESTORE_ALTIVEC_BEFORE_POP 0
20453
20454 /* Reload CR from REG. */
20455
20456 static void
20457 rs6000_restore_saved_cr (rtx reg, int using_mfcr_multiple)
20458 {
20459 int count = 0;
20460 int i;
20461
20462 if (using_mfcr_multiple)
20463 {
20464 for (i = 0; i < 8; i++)
20465 if (df_regs_ever_live_p (CR0_REGNO+i) && ! call_used_regs[CR0_REGNO+i])
20466 count++;
20467 gcc_assert (count);
20468 }
20469
20470 if (using_mfcr_multiple && count > 1)
20471 {
20472 rtvec p;
20473 int ndx;
20474
20475 p = rtvec_alloc (count);
20476
20477 ndx = 0;
20478 for (i = 0; i < 8; i++)
20479 if (df_regs_ever_live_p (CR0_REGNO+i) && ! call_used_regs[CR0_REGNO+i])
20480 {
20481 rtvec r = rtvec_alloc (2);
20482 RTVEC_ELT (r, 0) = reg;
20483 RTVEC_ELT (r, 1) = GEN_INT (1 << (7-i));
20484 RTVEC_ELT (p, ndx) =
20485 gen_rtx_SET (VOIDmode, gen_rtx_REG (CCmode, CR0_REGNO+i),
20486 gen_rtx_UNSPEC (CCmode, r, UNSPEC_MOVESI_TO_CR));
20487 ndx++;
20488 }
20489 emit_insn (gen_rtx_PARALLEL (VOIDmode, p));
20490 gcc_assert (ndx == count);
20491 }
20492 else
20493 for (i = 0; i < 8; i++)
20494 if (df_regs_ever_live_p (CR0_REGNO+i) && ! call_used_regs[CR0_REGNO+i])
20495 {
20496 emit_insn (gen_movsi_to_cr_one (gen_rtx_REG (CCmode,
20497 CR0_REGNO+i),
20498 reg));
20499 }
20500 }
20501
20502 /* Return true if OFFSET from stack pointer can be clobbered by signals.
20503 V.4 doesn't have any stack cushion, AIX ABIs have 220 or 288 bytes
20504 below stack pointer not cloberred by signals. */
20505
20506 static inline bool
20507 offset_below_red_zone_p (HOST_WIDE_INT offset)
20508 {
20509 return offset < (DEFAULT_ABI == ABI_V4
20510 ? 0
20511 : TARGET_32BIT ? -220 : -288);
20512 }
20513
20514 /* Emit function epilogue as insns. */
20515
20516 void
20517 rs6000_emit_epilogue (int sibcall)
20518 {
20519 rs6000_stack_t *info;
20520 int restoring_GPRs_inline;
20521 int restoring_FPRs_inline;
20522 int using_load_multiple;
20523 int using_mtcr_multiple;
20524 int use_backchain_to_restore_sp;
20525 int restore_lr;
20526 int strategy;
20527 int sp_offset = 0;
20528 rtx sp_reg_rtx = gen_rtx_REG (Pmode, 1);
20529 rtx frame_reg_rtx = sp_reg_rtx;
20530 rtx cfa_restores = NULL_RTX;
20531 rtx insn;
20532 rtx cr_save_reg = NULL_RTX;
20533 enum machine_mode reg_mode = Pmode;
20534 int reg_size = TARGET_32BIT ? 4 : 8;
20535 int i;
20536
20537 info = rs6000_stack_info ();
20538
20539 if (TARGET_SPE_ABI && info->spe_64bit_regs_used != 0)
20540 {
20541 reg_mode = V2SImode;
20542 reg_size = 8;
20543 }
20544
20545 strategy = rs6000_savres_strategy (info, /*savep=*/false,
20546 /*static_chain_p=*/0, sibcall);
20547 using_load_multiple = strategy & SAVRES_MULTIPLE;
20548 restoring_FPRs_inline = strategy & SAVRES_INLINE_FPRS;
20549 restoring_GPRs_inline = strategy & SAVRES_INLINE_GPRS;
20550 using_mtcr_multiple = (rs6000_cpu == PROCESSOR_PPC601
20551 || rs6000_cpu == PROCESSOR_PPC603
20552 || rs6000_cpu == PROCESSOR_PPC750
20553 || optimize_size);
20554 /* Restore via the backchain when we have a large frame, since this
20555 is more efficient than an addis, addi pair. The second condition
20556 here will not trigger at the moment; We don't actually need a
20557 frame pointer for alloca, but the generic parts of the compiler
20558 give us one anyway. */
20559 use_backchain_to_restore_sp = (info->total_size > 32767
20560 || info->total_size
20561 + (info->lr_save_p ? info->lr_save_offset : 0)
20562 > 32767
20563 || (cfun->calls_alloca
20564 && !frame_pointer_needed));
20565 restore_lr = (info->lr_save_p
20566 && (restoring_FPRs_inline
20567 || (strategy & SAVRES_NOINLINE_FPRS_DOESNT_RESTORE_LR))
20568 && (restoring_GPRs_inline
20569 || info->first_fp_reg_save < 64));
20570
20571 if (WORLD_SAVE_P (info))
20572 {
20573 int i, j;
20574 char rname[30];
20575 const char *alloc_rname;
20576 rtvec p;
20577
20578 /* eh_rest_world_r10 will return to the location saved in the LR
20579 stack slot (which is not likely to be our caller.)
20580 Input: R10 -- stack adjustment. Clobbers R0, R11, R12, R7, R8.
20581 rest_world is similar, except any R10 parameter is ignored.
20582 The exception-handling stuff that was here in 2.95 is no
20583 longer necessary. */
20584
20585 p = rtvec_alloc (9
20586 + 1
20587 + 32 - info->first_gp_reg_save
20588 + LAST_ALTIVEC_REGNO + 1 - info->first_altivec_reg_save
20589 + 63 + 1 - info->first_fp_reg_save);
20590
20591 strcpy (rname, ((crtl->calls_eh_return) ?
20592 "*eh_rest_world_r10" : "*rest_world"));
20593 alloc_rname = ggc_strdup (rname);
20594
20595 j = 0;
20596 RTVEC_ELT (p, j++) = gen_rtx_RETURN (VOIDmode);
20597 RTVEC_ELT (p, j++) = gen_rtx_USE (VOIDmode,
20598 gen_rtx_REG (Pmode,
20599 LR_REGNO));
20600 RTVEC_ELT (p, j++)
20601 = gen_rtx_USE (VOIDmode, gen_rtx_SYMBOL_REF (Pmode, alloc_rname));
20602 /* The instruction pattern requires a clobber here;
20603 it is shared with the restVEC helper. */
20604 RTVEC_ELT (p, j++)
20605 = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 11));
20606
20607 {
20608 /* CR register traditionally saved as CR2. */
20609 rtx reg = gen_rtx_REG (reg_mode, CR2_REGNO);
20610 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
20611 GEN_INT (info->cr_save_offset));
20612 rtx mem = gen_frame_mem (reg_mode, addr);
20613
20614 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, reg, mem);
20615 }
20616
20617 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
20618 {
20619 rtx reg = gen_rtx_REG (reg_mode, info->first_gp_reg_save + i);
20620 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
20621 GEN_INT (info->gp_save_offset
20622 + reg_size * i));
20623 rtx mem = gen_frame_mem (reg_mode, addr);
20624
20625 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, reg, mem);
20626 }
20627 for (i = 0; info->first_altivec_reg_save + i <= LAST_ALTIVEC_REGNO; i++)
20628 {
20629 rtx reg = gen_rtx_REG (V4SImode, info->first_altivec_reg_save + i);
20630 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
20631 GEN_INT (info->altivec_save_offset
20632 + 16 * i));
20633 rtx mem = gen_frame_mem (V4SImode, addr);
20634
20635 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, reg, mem);
20636 }
20637 for (i = 0; info->first_fp_reg_save + i <= 63; i++)
20638 {
20639 rtx reg = gen_rtx_REG (((TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT)
20640 ? DFmode : SFmode),
20641 info->first_fp_reg_save + i);
20642 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
20643 GEN_INT (info->fp_save_offset
20644 + 8 * i));
20645 rtx mem = gen_frame_mem (((TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT)
20646 ? DFmode : SFmode), addr);
20647
20648 RTVEC_ELT (p, j++) = gen_rtx_SET (VOIDmode, reg, mem);
20649 }
20650 RTVEC_ELT (p, j++)
20651 = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 0));
20652 RTVEC_ELT (p, j++)
20653 = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (SImode, 12));
20654 RTVEC_ELT (p, j++)
20655 = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (SImode, 7));
20656 RTVEC_ELT (p, j++)
20657 = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (SImode, 8));
20658 RTVEC_ELT (p, j++)
20659 = gen_rtx_USE (VOIDmode, gen_rtx_REG (SImode, 10));
20660 emit_jump_insn (gen_rtx_PARALLEL (VOIDmode, p));
20661
20662 return;
20663 }
20664
20665 /* frame_reg_rtx + sp_offset points to the top of this stack frame. */
20666 if (info->push_p)
20667 sp_offset = info->total_size;
20668
20669 /* Restore AltiVec registers if we must do so before adjusting the
20670 stack. */
20671 if (TARGET_ALTIVEC_ABI
20672 && info->altivec_size != 0
20673 && (ALWAYS_RESTORE_ALTIVEC_BEFORE_POP
20674 || (DEFAULT_ABI != ABI_V4
20675 && offset_below_red_zone_p (info->altivec_save_offset))))
20676 {
20677 int i;
20678
20679 if (use_backchain_to_restore_sp)
20680 {
20681 frame_reg_rtx = gen_rtx_REG (Pmode, 11);
20682 emit_move_insn (frame_reg_rtx,
20683 gen_rtx_MEM (Pmode, sp_reg_rtx));
20684 sp_offset = 0;
20685 }
20686 else if (frame_pointer_needed)
20687 frame_reg_rtx = hard_frame_pointer_rtx;
20688
20689 for (i = info->first_altivec_reg_save; i <= LAST_ALTIVEC_REGNO; ++i)
20690 if (info->vrsave_mask & ALTIVEC_REG_BIT (i))
20691 {
20692 rtx addr, areg, mem, reg;
20693
20694 areg = gen_rtx_REG (Pmode, 0);
20695 emit_move_insn
20696 (areg, GEN_INT (info->altivec_save_offset
20697 + sp_offset
20698 + 16 * (i - info->first_altivec_reg_save)));
20699
20700 /* AltiVec addressing mode is [reg+reg]. */
20701 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx, areg);
20702 mem = gen_frame_mem (V4SImode, addr);
20703
20704 reg = gen_rtx_REG (V4SImode, i);
20705 emit_move_insn (reg, mem);
20706 if (offset_below_red_zone_p (info->altivec_save_offset
20707 + (i - info->first_altivec_reg_save)
20708 * 16))
20709 cfa_restores = alloc_reg_note (REG_CFA_RESTORE, reg,
20710 cfa_restores);
20711 }
20712 }
20713
20714 /* Restore VRSAVE if we must do so before adjusting the stack. */
20715 if (TARGET_ALTIVEC
20716 && TARGET_ALTIVEC_VRSAVE
20717 && info->vrsave_mask != 0
20718 && (ALWAYS_RESTORE_ALTIVEC_BEFORE_POP
20719 || (DEFAULT_ABI != ABI_V4
20720 && offset_below_red_zone_p (info->vrsave_save_offset))))
20721 {
20722 rtx addr, mem, reg;
20723
20724 if (frame_reg_rtx == sp_reg_rtx)
20725 {
20726 if (use_backchain_to_restore_sp)
20727 {
20728 frame_reg_rtx = gen_rtx_REG (Pmode, 11);
20729 emit_move_insn (frame_reg_rtx,
20730 gen_rtx_MEM (Pmode, sp_reg_rtx));
20731 sp_offset = 0;
20732 }
20733 else if (frame_pointer_needed)
20734 frame_reg_rtx = hard_frame_pointer_rtx;
20735 }
20736
20737 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
20738 GEN_INT (info->vrsave_save_offset + sp_offset));
20739 mem = gen_frame_mem (SImode, addr);
20740 reg = gen_rtx_REG (SImode, 12);
20741 emit_move_insn (reg, mem);
20742
20743 emit_insn (generate_set_vrsave (reg, info, 1));
20744 }
20745
20746 insn = NULL_RTX;
20747 /* If we have a large stack frame, restore the old stack pointer
20748 using the backchain. */
20749 if (use_backchain_to_restore_sp)
20750 {
20751 if (frame_reg_rtx == sp_reg_rtx)
20752 {
20753 /* Under V.4, don't reset the stack pointer until after we're done
20754 loading the saved registers. */
20755 if (DEFAULT_ABI == ABI_V4)
20756 frame_reg_rtx = gen_rtx_REG (Pmode, 11);
20757
20758 insn = emit_move_insn (frame_reg_rtx,
20759 gen_rtx_MEM (Pmode, sp_reg_rtx));
20760 sp_offset = 0;
20761 }
20762 else if (ALWAYS_RESTORE_ALTIVEC_BEFORE_POP
20763 && DEFAULT_ABI == ABI_V4)
20764 /* frame_reg_rtx has been set up by the altivec restore. */
20765 ;
20766 else
20767 {
20768 insn = emit_move_insn (sp_reg_rtx, frame_reg_rtx);
20769 frame_reg_rtx = sp_reg_rtx;
20770 }
20771 }
20772 /* If we have a frame pointer, we can restore the old stack pointer
20773 from it. */
20774 else if (frame_pointer_needed)
20775 {
20776 frame_reg_rtx = sp_reg_rtx;
20777 if (DEFAULT_ABI == ABI_V4)
20778 frame_reg_rtx = gen_rtx_REG (Pmode, 11);
20779 /* Prevent reordering memory accesses against stack pointer restore. */
20780 else if (cfun->calls_alloca
20781 || offset_below_red_zone_p (-info->total_size))
20782 {
20783 rtx mem1 = gen_rtx_MEM (BLKmode, hard_frame_pointer_rtx);
20784 rtx mem2 = gen_rtx_MEM (BLKmode, sp_reg_rtx);
20785 MEM_NOTRAP_P (mem1) = 1;
20786 MEM_NOTRAP_P (mem2) = 1;
20787 emit_insn (gen_frame_tie (mem1, mem2));
20788 }
20789
20790 insn = emit_insn (gen_add3_insn (frame_reg_rtx, hard_frame_pointer_rtx,
20791 GEN_INT (info->total_size)));
20792 sp_offset = 0;
20793 }
20794 else if (info->push_p
20795 && DEFAULT_ABI != ABI_V4
20796 && !crtl->calls_eh_return)
20797 {
20798 /* Prevent reordering memory accesses against stack pointer restore. */
20799 if (cfun->calls_alloca
20800 || offset_below_red_zone_p (-info->total_size))
20801 {
20802 rtx mem = gen_rtx_MEM (BLKmode, sp_reg_rtx);
20803 MEM_NOTRAP_P (mem) = 1;
20804 emit_insn (gen_stack_tie (mem));
20805 }
20806 insn = emit_insn (gen_add3_insn (sp_reg_rtx, sp_reg_rtx,
20807 GEN_INT (info->total_size)));
20808 sp_offset = 0;
20809 }
20810 if (insn && frame_reg_rtx == sp_reg_rtx)
20811 {
20812 if (cfa_restores)
20813 {
20814 REG_NOTES (insn) = cfa_restores;
20815 cfa_restores = NULL_RTX;
20816 }
20817 add_reg_note (insn, REG_CFA_DEF_CFA, sp_reg_rtx);
20818 RTX_FRAME_RELATED_P (insn) = 1;
20819 }
20820
20821 /* Restore AltiVec registers if we have not done so already. */
20822 if (!ALWAYS_RESTORE_ALTIVEC_BEFORE_POP
20823 && TARGET_ALTIVEC_ABI
20824 && info->altivec_size != 0
20825 && (DEFAULT_ABI == ABI_V4
20826 || !offset_below_red_zone_p (info->altivec_save_offset)))
20827 {
20828 int i;
20829
20830 for (i = info->first_altivec_reg_save; i <= LAST_ALTIVEC_REGNO; ++i)
20831 if (info->vrsave_mask & ALTIVEC_REG_BIT (i))
20832 {
20833 rtx addr, areg, mem, reg;
20834
20835 areg = gen_rtx_REG (Pmode, 0);
20836 emit_move_insn
20837 (areg, GEN_INT (info->altivec_save_offset
20838 + sp_offset
20839 + 16 * (i - info->first_altivec_reg_save)));
20840
20841 /* AltiVec addressing mode is [reg+reg]. */
20842 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx, areg);
20843 mem = gen_frame_mem (V4SImode, addr);
20844
20845 reg = gen_rtx_REG (V4SImode, i);
20846 emit_move_insn (reg, mem);
20847 if (DEFAULT_ABI == ABI_V4)
20848 cfa_restores = alloc_reg_note (REG_CFA_RESTORE, reg,
20849 cfa_restores);
20850 }
20851 }
20852
20853 /* Restore VRSAVE if we have not done so already. */
20854 if (!ALWAYS_RESTORE_ALTIVEC_BEFORE_POP
20855 && TARGET_ALTIVEC
20856 && TARGET_ALTIVEC_VRSAVE
20857 && info->vrsave_mask != 0
20858 && (DEFAULT_ABI == ABI_V4
20859 || !offset_below_red_zone_p (info->vrsave_save_offset)))
20860 {
20861 rtx addr, mem, reg;
20862
20863 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
20864 GEN_INT (info->vrsave_save_offset + sp_offset));
20865 mem = gen_frame_mem (SImode, addr);
20866 reg = gen_rtx_REG (SImode, 12);
20867 emit_move_insn (reg, mem);
20868
20869 emit_insn (generate_set_vrsave (reg, info, 1));
20870 }
20871
20872 /* Get the old lr if we saved it. If we are restoring registers
20873 out-of-line, then the out-of-line routines can do this for us. */
20874 if (restore_lr && restoring_GPRs_inline)
20875 {
20876 rtx mem = gen_frame_mem_offset (Pmode, frame_reg_rtx,
20877 info->lr_save_offset + sp_offset);
20878
20879 emit_move_insn (gen_rtx_REG (Pmode, 0), mem);
20880 }
20881
20882 /* Get the old cr if we saved it. */
20883 if (info->cr_save_p)
20884 {
20885 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
20886 GEN_INT (info->cr_save_offset + sp_offset));
20887 rtx mem = gen_frame_mem (SImode, addr);
20888
20889 cr_save_reg = gen_rtx_REG (SImode,
20890 DEFAULT_ABI == ABI_AIX
20891 && !restoring_GPRs_inline
20892 && info->first_fp_reg_save < 64
20893 ? 11 : 12);
20894 emit_move_insn (cr_save_reg, mem);
20895 }
20896
20897 /* Set LR here to try to overlap restores below. LR is always saved
20898 above incoming stack, so it never needs REG_CFA_RESTORE. */
20899 if (restore_lr && restoring_GPRs_inline)
20900 emit_move_insn (gen_rtx_REG (Pmode, LR_REGNO),
20901 gen_rtx_REG (Pmode, 0));
20902
20903 /* Load exception handler data registers, if needed. */
20904 if (crtl->calls_eh_return)
20905 {
20906 unsigned int i, regno;
20907
20908 if (TARGET_AIX)
20909 {
20910 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
20911 GEN_INT (sp_offset + 5 * reg_size));
20912 rtx mem = gen_frame_mem (reg_mode, addr);
20913
20914 emit_move_insn (gen_rtx_REG (reg_mode, 2), mem);
20915 }
20916
20917 for (i = 0; ; ++i)
20918 {
20919 rtx mem;
20920
20921 regno = EH_RETURN_DATA_REGNO (i);
20922 if (regno == INVALID_REGNUM)
20923 break;
20924
20925 mem = gen_frame_mem_offset (reg_mode, frame_reg_rtx,
20926 info->ehrd_offset + sp_offset
20927 + reg_size * (int) i);
20928
20929 emit_move_insn (gen_rtx_REG (reg_mode, regno), mem);
20930 }
20931 }
20932
20933 /* Restore GPRs. This is done as a PARALLEL if we are using
20934 the load-multiple instructions. */
20935 if (TARGET_SPE_ABI
20936 && info->spe_64bit_regs_used != 0
20937 && info->first_gp_reg_save != 32)
20938 {
20939 /* Determine whether we can address all of the registers that need
20940 to be saved with an offset from the stack pointer that fits in
20941 the small const field for SPE memory instructions. */
20942 int spe_regs_addressable_via_sp
20943 = (SPE_CONST_OFFSET_OK(info->spe_gp_save_offset + sp_offset
20944 + (32 - info->first_gp_reg_save - 1) * reg_size)
20945 && restoring_GPRs_inline);
20946 int spe_offset;
20947
20948 if (spe_regs_addressable_via_sp)
20949 spe_offset = info->spe_gp_save_offset + sp_offset;
20950 else
20951 {
20952 rtx old_frame_reg_rtx = frame_reg_rtx;
20953 /* Make r11 point to the start of the SPE save area. We worried about
20954 not clobbering it when we were saving registers in the prologue.
20955 There's no need to worry here because the static chain is passed
20956 anew to every function. */
20957 int ool_adjust = (restoring_GPRs_inline
20958 ? 0
20959 : (info->first_gp_reg_save
20960 - (FIRST_SAVRES_REGISTER+1))*8);
20961
20962 if (frame_reg_rtx == sp_reg_rtx)
20963 frame_reg_rtx = gen_rtx_REG (Pmode, 11);
20964 emit_insn (gen_addsi3 (frame_reg_rtx, old_frame_reg_rtx,
20965 GEN_INT (info->spe_gp_save_offset
20966 + sp_offset
20967 - ool_adjust)));
20968 /* Keep the invariant that frame_reg_rtx + sp_offset points
20969 at the top of the stack frame. */
20970 sp_offset = -info->spe_gp_save_offset;
20971
20972 spe_offset = 0;
20973 }
20974
20975 if (restoring_GPRs_inline)
20976 {
20977 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
20978 if (rs6000_reg_live_or_pic_offset_p (info->first_gp_reg_save + i))
20979 {
20980 rtx offset, addr, mem, reg;
20981
20982 /* We're doing all this to ensure that the immediate offset
20983 fits into the immediate field of 'evldd'. */
20984 gcc_assert (SPE_CONST_OFFSET_OK (spe_offset + reg_size * i));
20985
20986 offset = GEN_INT (spe_offset + reg_size * i);
20987 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx, offset);
20988 mem = gen_rtx_MEM (V2SImode, addr);
20989 reg = gen_rtx_REG (reg_mode, info->first_gp_reg_save + i);
20990
20991 insn = emit_move_insn (reg, mem);
20992 if (DEFAULT_ABI == ABI_V4)
20993 {
20994 if (frame_pointer_needed
20995 && info->first_gp_reg_save + i
20996 == HARD_FRAME_POINTER_REGNUM)
20997 {
20998 add_reg_note (insn, REG_CFA_DEF_CFA,
20999 plus_constant (frame_reg_rtx,
21000 sp_offset));
21001 RTX_FRAME_RELATED_P (insn) = 1;
21002 }
21003
21004 cfa_restores = alloc_reg_note (REG_CFA_RESTORE, reg,
21005 cfa_restores);
21006 }
21007 }
21008 }
21009 else
21010 {
21011 rtx par;
21012
21013 par = rs6000_make_savres_rtx (info, gen_rtx_REG (Pmode, 11),
21014 0, reg_mode,
21015 /*savep=*/false, /*gpr=*/true,
21016 /*lr=*/true);
21017 emit_jump_insn (par);
21018 /* We don't want anybody else emitting things after we jumped
21019 back. */
21020 return;
21021 }
21022 }
21023 else if (!restoring_GPRs_inline)
21024 {
21025 /* We are jumping to an out-of-line function. */
21026 bool can_use_exit = info->first_fp_reg_save == 64;
21027 rtx par;
21028
21029 /* Emit stack reset code if we need it. */
21030 if (can_use_exit)
21031 rs6000_emit_stack_reset (info, sp_reg_rtx, frame_reg_rtx,
21032 sp_offset, can_use_exit);
21033 else
21034 {
21035 emit_insn (gen_add3_insn (gen_rtx_REG (Pmode, DEFAULT_ABI == ABI_AIX
21036 ? 12 : 11),
21037 frame_reg_rtx,
21038 GEN_INT (sp_offset - info->fp_size)));
21039 if (REGNO (frame_reg_rtx) == 11)
21040 sp_offset += info->fp_size;
21041 }
21042
21043 par = rs6000_make_savres_rtx (info, frame_reg_rtx,
21044 info->gp_save_offset, reg_mode,
21045 /*savep=*/false, /*gpr=*/true,
21046 /*lr=*/can_use_exit);
21047
21048 if (can_use_exit)
21049 {
21050 if (info->cr_save_p)
21051 {
21052 rs6000_restore_saved_cr (cr_save_reg, using_mtcr_multiple);
21053 if (DEFAULT_ABI == ABI_V4)
21054 cfa_restores
21055 = alloc_reg_note (REG_CFA_RESTORE,
21056 gen_rtx_REG (SImode, CR2_REGNO),
21057 cfa_restores);
21058 }
21059
21060 emit_jump_insn (par);
21061
21062 /* We don't want anybody else emitting things after we jumped
21063 back. */
21064 return;
21065 }
21066
21067 insn = emit_insn (par);
21068 if (DEFAULT_ABI == ABI_V4)
21069 {
21070 if (frame_pointer_needed)
21071 {
21072 add_reg_note (insn, REG_CFA_DEF_CFA,
21073 plus_constant (frame_reg_rtx, sp_offset));
21074 RTX_FRAME_RELATED_P (insn) = 1;
21075 }
21076
21077 for (i = info->first_gp_reg_save; i < 32; i++)
21078 cfa_restores
21079 = alloc_reg_note (REG_CFA_RESTORE,
21080 gen_rtx_REG (reg_mode, i), cfa_restores);
21081 }
21082 }
21083 else if (using_load_multiple)
21084 {
21085 rtvec p;
21086 p = rtvec_alloc (32 - info->first_gp_reg_save);
21087 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
21088 {
21089 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
21090 GEN_INT (info->gp_save_offset
21091 + sp_offset
21092 + reg_size * i));
21093 rtx mem = gen_frame_mem (reg_mode, addr);
21094 rtx reg = gen_rtx_REG (reg_mode, info->first_gp_reg_save + i);
21095
21096 RTVEC_ELT (p, i) = gen_rtx_SET (VOIDmode, reg, mem);
21097 if (DEFAULT_ABI == ABI_V4)
21098 cfa_restores = alloc_reg_note (REG_CFA_RESTORE, reg,
21099 cfa_restores);
21100 }
21101 insn = emit_insn (gen_rtx_PARALLEL (VOIDmode, p));
21102 if (DEFAULT_ABI == ABI_V4 && frame_pointer_needed)
21103 {
21104 add_reg_note (insn, REG_CFA_DEF_CFA,
21105 plus_constant (frame_reg_rtx, sp_offset));
21106 RTX_FRAME_RELATED_P (insn) = 1;
21107 }
21108 }
21109 else
21110 {
21111 for (i = 0; i < 32 - info->first_gp_reg_save; i++)
21112 if (rs6000_reg_live_or_pic_offset_p (info->first_gp_reg_save + i))
21113 {
21114 rtx addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
21115 GEN_INT (info->gp_save_offset
21116 + sp_offset
21117 + reg_size * i));
21118 rtx mem = gen_frame_mem (reg_mode, addr);
21119 rtx reg = gen_rtx_REG (reg_mode, info->first_gp_reg_save + i);
21120
21121 insn = emit_move_insn (reg, mem);
21122 if (DEFAULT_ABI == ABI_V4)
21123 {
21124 if (frame_pointer_needed
21125 && info->first_gp_reg_save + i
21126 == HARD_FRAME_POINTER_REGNUM)
21127 {
21128 add_reg_note (insn, REG_CFA_DEF_CFA,
21129 plus_constant (frame_reg_rtx, sp_offset));
21130 RTX_FRAME_RELATED_P (insn) = 1;
21131 }
21132
21133 cfa_restores = alloc_reg_note (REG_CFA_RESTORE, reg,
21134 cfa_restores);
21135 }
21136 }
21137 }
21138
21139 if (restore_lr && !restoring_GPRs_inline)
21140 {
21141 rtx mem = gen_frame_mem_offset (Pmode, frame_reg_rtx,
21142 info->lr_save_offset + sp_offset);
21143
21144 emit_move_insn (gen_rtx_REG (Pmode, 0), mem);
21145 emit_move_insn (gen_rtx_REG (Pmode, LR_REGNO),
21146 gen_rtx_REG (Pmode, 0));
21147 }
21148
21149 /* Restore fpr's if we need to do it without calling a function. */
21150 if (restoring_FPRs_inline)
21151 for (i = 0; i < 64 - info->first_fp_reg_save; i++)
21152 if ((df_regs_ever_live_p (info->first_fp_reg_save+i)
21153 && ! call_used_regs[info->first_fp_reg_save+i]))
21154 {
21155 rtx addr, mem, reg;
21156 addr = gen_rtx_PLUS (Pmode, frame_reg_rtx,
21157 GEN_INT (info->fp_save_offset
21158 + sp_offset
21159 + 8 * i));
21160 mem = gen_frame_mem (((TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT)
21161 ? DFmode : SFmode), addr);
21162 reg = gen_rtx_REG (((TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT)
21163 ? DFmode : SFmode),
21164 info->first_fp_reg_save + i);
21165
21166 emit_move_insn (reg, mem);
21167 if (DEFAULT_ABI == ABI_V4)
21168 cfa_restores = alloc_reg_note (REG_CFA_RESTORE, reg,
21169 cfa_restores);
21170 }
21171
21172 /* If we saved cr, restore it here. Just those that were used. */
21173 if (info->cr_save_p)
21174 {
21175 rs6000_restore_saved_cr (cr_save_reg, using_mtcr_multiple);
21176 if (DEFAULT_ABI == ABI_V4)
21177 cfa_restores
21178 = alloc_reg_note (REG_CFA_RESTORE, gen_rtx_REG (SImode, CR2_REGNO),
21179 cfa_restores);
21180 }
21181
21182 /* If this is V.4, unwind the stack pointer after all of the loads
21183 have been done. */
21184 insn = rs6000_emit_stack_reset (info, sp_reg_rtx, frame_reg_rtx,
21185 sp_offset, !restoring_FPRs_inline);
21186 if (insn)
21187 {
21188 if (cfa_restores)
21189 {
21190 REG_NOTES (insn) = cfa_restores;
21191 cfa_restores = NULL_RTX;
21192 }
21193 add_reg_note (insn, REG_CFA_DEF_CFA, sp_reg_rtx);
21194 RTX_FRAME_RELATED_P (insn) = 1;
21195 }
21196
21197 if (crtl->calls_eh_return)
21198 {
21199 rtx sa = EH_RETURN_STACKADJ_RTX;
21200 emit_insn (gen_add3_insn (sp_reg_rtx, sp_reg_rtx, sa));
21201 }
21202
21203 if (!sibcall)
21204 {
21205 rtvec p;
21206 bool lr = (strategy & SAVRES_NOINLINE_FPRS_DOESNT_RESTORE_LR) == 0;
21207 if (! restoring_FPRs_inline)
21208 p = rtvec_alloc (4 + 64 - info->first_fp_reg_save);
21209 else
21210 p = rtvec_alloc (2);
21211
21212 RTVEC_ELT (p, 0) = gen_rtx_RETURN (VOIDmode);
21213 RTVEC_ELT (p, 1) = ((restoring_FPRs_inline || !lr)
21214 ? gen_rtx_USE (VOIDmode, gen_rtx_REG (Pmode, 65))
21215 : gen_rtx_CLOBBER (VOIDmode,
21216 gen_rtx_REG (Pmode, 65)));
21217
21218 /* If we have to restore more than two FP registers, branch to the
21219 restore function. It will return to our caller. */
21220 if (! restoring_FPRs_inline)
21221 {
21222 int i;
21223 rtx sym;
21224
21225 sym = rs6000_savres_routine_sym (info,
21226 /*savep=*/false,
21227 /*gpr=*/false,
21228 /*lr=*/lr);
21229 RTVEC_ELT (p, 2) = gen_rtx_USE (VOIDmode, sym);
21230 RTVEC_ELT (p, 3) = gen_rtx_USE (VOIDmode,
21231 gen_rtx_REG (Pmode,
21232 DEFAULT_ABI == ABI_AIX
21233 ? 1 : 11));
21234 for (i = 0; i < 64 - info->first_fp_reg_save; i++)
21235 {
21236 rtx addr, mem;
21237 addr = gen_rtx_PLUS (Pmode, sp_reg_rtx,
21238 GEN_INT (info->fp_save_offset + 8*i));
21239 mem = gen_frame_mem (DFmode, addr);
21240
21241 RTVEC_ELT (p, i+4) =
21242 gen_rtx_SET (VOIDmode,
21243 gen_rtx_REG (DFmode, info->first_fp_reg_save + i),
21244 mem);
21245 }
21246 }
21247
21248 emit_jump_insn (gen_rtx_PARALLEL (VOIDmode, p));
21249 }
21250 }
21251
21252 /* Write function epilogue. */
21253
21254 static void
21255 rs6000_output_function_epilogue (FILE *file,
21256 HOST_WIDE_INT size ATTRIBUTE_UNUSED)
21257 {
21258 if (! HAVE_epilogue)
21259 {
21260 rtx insn = get_last_insn ();
21261 /* If the last insn was a BARRIER, we don't have to write anything except
21262 the trace table. */
21263 if (GET_CODE (insn) == NOTE)
21264 insn = prev_nonnote_insn (insn);
21265 if (insn == 0 || GET_CODE (insn) != BARRIER)
21266 {
21267 /* This is slightly ugly, but at least we don't have two
21268 copies of the epilogue-emitting code. */
21269 start_sequence ();
21270
21271 /* A NOTE_INSN_DELETED is supposed to be at the start
21272 and end of the "toplevel" insn chain. */
21273 emit_note (NOTE_INSN_DELETED);
21274 rs6000_emit_epilogue (FALSE);
21275 emit_note (NOTE_INSN_DELETED);
21276
21277 /* Expand INSN_ADDRESSES so final() doesn't crash. */
21278 {
21279 rtx insn;
21280 unsigned addr = 0;
21281 for (insn = get_insns (); insn != 0; insn = NEXT_INSN (insn))
21282 {
21283 INSN_ADDRESSES_NEW (insn, addr);
21284 addr += 4;
21285 }
21286 }
21287
21288 if (TARGET_DEBUG_STACK)
21289 debug_rtx_list (get_insns (), 100);
21290 final (get_insns (), file, FALSE);
21291 end_sequence ();
21292 }
21293 }
21294
21295 #if TARGET_MACHO
21296 macho_branch_islands ();
21297 /* Mach-O doesn't support labels at the end of objects, so if
21298 it looks like we might want one, insert a NOP. */
21299 {
21300 rtx insn = get_last_insn ();
21301 while (insn
21302 && NOTE_P (insn)
21303 && NOTE_KIND (insn) != NOTE_INSN_DELETED_LABEL)
21304 insn = PREV_INSN (insn);
21305 if (insn
21306 && (LABEL_P (insn)
21307 || (NOTE_P (insn)
21308 && NOTE_KIND (insn) == NOTE_INSN_DELETED_LABEL)))
21309 fputs ("\tnop\n", file);
21310 }
21311 #endif
21312
21313 /* Output a traceback table here. See /usr/include/sys/debug.h for info
21314 on its format.
21315
21316 We don't output a traceback table if -finhibit-size-directive was
21317 used. The documentation for -finhibit-size-directive reads
21318 ``don't output a @code{.size} assembler directive, or anything
21319 else that would cause trouble if the function is split in the
21320 middle, and the two halves are placed at locations far apart in
21321 memory.'' The traceback table has this property, since it
21322 includes the offset from the start of the function to the
21323 traceback table itself.
21324
21325 System V.4 Powerpc's (and the embedded ABI derived from it) use a
21326 different traceback table. */
21327 if (DEFAULT_ABI == ABI_AIX && ! flag_inhibit_size_directive
21328 && rs6000_traceback != traceback_none && !cfun->is_thunk)
21329 {
21330 const char *fname = NULL;
21331 const char *language_string = lang_hooks.name;
21332 int fixed_parms = 0, float_parms = 0, parm_info = 0;
21333 int i;
21334 int optional_tbtab;
21335 rs6000_stack_t *info = rs6000_stack_info ();
21336
21337 if (rs6000_traceback == traceback_full)
21338 optional_tbtab = 1;
21339 else if (rs6000_traceback == traceback_part)
21340 optional_tbtab = 0;
21341 else
21342 optional_tbtab = !optimize_size && !TARGET_ELF;
21343
21344 if (optional_tbtab)
21345 {
21346 fname = XSTR (XEXP (DECL_RTL (current_function_decl), 0), 0);
21347 while (*fname == '.') /* V.4 encodes . in the name */
21348 fname++;
21349
21350 /* Need label immediately before tbtab, so we can compute
21351 its offset from the function start. */
21352 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (file, "LT");
21353 ASM_OUTPUT_LABEL (file, fname);
21354 }
21355
21356 /* The .tbtab pseudo-op can only be used for the first eight
21357 expressions, since it can't handle the possibly variable
21358 length fields that follow. However, if you omit the optional
21359 fields, the assembler outputs zeros for all optional fields
21360 anyways, giving each variable length field is minimum length
21361 (as defined in sys/debug.h). Thus we can not use the .tbtab
21362 pseudo-op at all. */
21363
21364 /* An all-zero word flags the start of the tbtab, for debuggers
21365 that have to find it by searching forward from the entry
21366 point or from the current pc. */
21367 fputs ("\t.long 0\n", file);
21368
21369 /* Tbtab format type. Use format type 0. */
21370 fputs ("\t.byte 0,", file);
21371
21372 /* Language type. Unfortunately, there does not seem to be any
21373 official way to discover the language being compiled, so we
21374 use language_string.
21375 C is 0. Fortran is 1. Pascal is 2. Ada is 3. C++ is 9.
21376 Java is 13. Objective-C is 14. Objective-C++ isn't assigned
21377 a number, so for now use 9. LTO isn't assigned a number either,
21378 so for now use 0. */
21379 if (! strcmp (language_string, "GNU C")
21380 || ! strcmp (language_string, "GNU GIMPLE"))
21381 i = 0;
21382 else if (! strcmp (language_string, "GNU F77")
21383 || ! strcmp (language_string, "GNU Fortran"))
21384 i = 1;
21385 else if (! strcmp (language_string, "GNU Pascal"))
21386 i = 2;
21387 else if (! strcmp (language_string, "GNU Ada"))
21388 i = 3;
21389 else if (! strcmp (language_string, "GNU C++")
21390 || ! strcmp (language_string, "GNU Objective-C++"))
21391 i = 9;
21392 else if (! strcmp (language_string, "GNU Java"))
21393 i = 13;
21394 else if (! strcmp (language_string, "GNU Objective-C"))
21395 i = 14;
21396 else
21397 gcc_unreachable ();
21398 fprintf (file, "%d,", i);
21399
21400 /* 8 single bit fields: global linkage (not set for C extern linkage,
21401 apparently a PL/I convention?), out-of-line epilogue/prologue, offset
21402 from start of procedure stored in tbtab, internal function, function
21403 has controlled storage, function has no toc, function uses fp,
21404 function logs/aborts fp operations. */
21405 /* Assume that fp operations are used if any fp reg must be saved. */
21406 fprintf (file, "%d,",
21407 (optional_tbtab << 5) | ((info->first_fp_reg_save != 64) << 1));
21408
21409 /* 6 bitfields: function is interrupt handler, name present in
21410 proc table, function calls alloca, on condition directives
21411 (controls stack walks, 3 bits), saves condition reg, saves
21412 link reg. */
21413 /* The `function calls alloca' bit seems to be set whenever reg 31 is
21414 set up as a frame pointer, even when there is no alloca call. */
21415 fprintf (file, "%d,",
21416 ((optional_tbtab << 6)
21417 | ((optional_tbtab & frame_pointer_needed) << 5)
21418 | (info->cr_save_p << 1)
21419 | (info->lr_save_p)));
21420
21421 /* 3 bitfields: saves backchain, fixup code, number of fpr saved
21422 (6 bits). */
21423 fprintf (file, "%d,",
21424 (info->push_p << 7) | (64 - info->first_fp_reg_save));
21425
21426 /* 2 bitfields: spare bits (2 bits), number of gpr saved (6 bits). */
21427 fprintf (file, "%d,", (32 - first_reg_to_save ()));
21428
21429 if (optional_tbtab)
21430 {
21431 /* Compute the parameter info from the function decl argument
21432 list. */
21433 tree decl;
21434 int next_parm_info_bit = 31;
21435
21436 for (decl = DECL_ARGUMENTS (current_function_decl);
21437 decl; decl = DECL_CHAIN (decl))
21438 {
21439 rtx parameter = DECL_INCOMING_RTL (decl);
21440 enum machine_mode mode = GET_MODE (parameter);
21441
21442 if (GET_CODE (parameter) == REG)
21443 {
21444 if (SCALAR_FLOAT_MODE_P (mode))
21445 {
21446 int bits;
21447
21448 float_parms++;
21449
21450 switch (mode)
21451 {
21452 case SFmode:
21453 case SDmode:
21454 bits = 0x2;
21455 break;
21456
21457 case DFmode:
21458 case DDmode:
21459 case TFmode:
21460 case TDmode:
21461 bits = 0x3;
21462 break;
21463
21464 default:
21465 gcc_unreachable ();
21466 }
21467
21468 /* If only one bit will fit, don't or in this entry. */
21469 if (next_parm_info_bit > 0)
21470 parm_info |= (bits << (next_parm_info_bit - 1));
21471 next_parm_info_bit -= 2;
21472 }
21473 else
21474 {
21475 fixed_parms += ((GET_MODE_SIZE (mode)
21476 + (UNITS_PER_WORD - 1))
21477 / UNITS_PER_WORD);
21478 next_parm_info_bit -= 1;
21479 }
21480 }
21481 }
21482 }
21483
21484 /* Number of fixed point parameters. */
21485 /* This is actually the number of words of fixed point parameters; thus
21486 an 8 byte struct counts as 2; and thus the maximum value is 8. */
21487 fprintf (file, "%d,", fixed_parms);
21488
21489 /* 2 bitfields: number of floating point parameters (7 bits), parameters
21490 all on stack. */
21491 /* This is actually the number of fp registers that hold parameters;
21492 and thus the maximum value is 13. */
21493 /* Set parameters on stack bit if parameters are not in their original
21494 registers, regardless of whether they are on the stack? Xlc
21495 seems to set the bit when not optimizing. */
21496 fprintf (file, "%d\n", ((float_parms << 1) | (! optimize)));
21497
21498 if (! optional_tbtab)
21499 return;
21500
21501 /* Optional fields follow. Some are variable length. */
21502
21503 /* Parameter types, left adjusted bit fields: 0 fixed, 10 single float,
21504 11 double float. */
21505 /* There is an entry for each parameter in a register, in the order that
21506 they occur in the parameter list. Any intervening arguments on the
21507 stack are ignored. If the list overflows a long (max possible length
21508 34 bits) then completely leave off all elements that don't fit. */
21509 /* Only emit this long if there was at least one parameter. */
21510 if (fixed_parms || float_parms)
21511 fprintf (file, "\t.long %d\n", parm_info);
21512
21513 /* Offset from start of code to tb table. */
21514 fputs ("\t.long ", file);
21515 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (file, "LT");
21516 RS6000_OUTPUT_BASENAME (file, fname);
21517 putc ('-', file);
21518 rs6000_output_function_entry (file, fname);
21519 putc ('\n', file);
21520
21521 /* Interrupt handler mask. */
21522 /* Omit this long, since we never set the interrupt handler bit
21523 above. */
21524
21525 /* Number of CTL (controlled storage) anchors. */
21526 /* Omit this long, since the has_ctl bit is never set above. */
21527
21528 /* Displacement into stack of each CTL anchor. */
21529 /* Omit this list of longs, because there are no CTL anchors. */
21530
21531 /* Length of function name. */
21532 if (*fname == '*')
21533 ++fname;
21534 fprintf (file, "\t.short %d\n", (int) strlen (fname));
21535
21536 /* Function name. */
21537 assemble_string (fname, strlen (fname));
21538
21539 /* Register for alloca automatic storage; this is always reg 31.
21540 Only emit this if the alloca bit was set above. */
21541 if (frame_pointer_needed)
21542 fputs ("\t.byte 31\n", file);
21543
21544 fputs ("\t.align 2\n", file);
21545 }
21546 }
21547 \f
21548 /* A C compound statement that outputs the assembler code for a thunk
21549 function, used to implement C++ virtual function calls with
21550 multiple inheritance. The thunk acts as a wrapper around a virtual
21551 function, adjusting the implicit object parameter before handing
21552 control off to the real function.
21553
21554 First, emit code to add the integer DELTA to the location that
21555 contains the incoming first argument. Assume that this argument
21556 contains a pointer, and is the one used to pass the `this' pointer
21557 in C++. This is the incoming argument *before* the function
21558 prologue, e.g. `%o0' on a sparc. The addition must preserve the
21559 values of all other incoming arguments.
21560
21561 After the addition, emit code to jump to FUNCTION, which is a
21562 `FUNCTION_DECL'. This is a direct pure jump, not a call, and does
21563 not touch the return address. Hence returning from FUNCTION will
21564 return to whoever called the current `thunk'.
21565
21566 The effect must be as if FUNCTION had been called directly with the
21567 adjusted first argument. This macro is responsible for emitting
21568 all of the code for a thunk function; output_function_prologue()
21569 and output_function_epilogue() are not invoked.
21570
21571 The THUNK_FNDECL is redundant. (DELTA and FUNCTION have already
21572 been extracted from it.) It might possibly be useful on some
21573 targets, but probably not.
21574
21575 If you do not define this macro, the target-independent code in the
21576 C++ frontend will generate a less efficient heavyweight thunk that
21577 calls FUNCTION instead of jumping to it. The generic approach does
21578 not support varargs. */
21579
21580 static void
21581 rs6000_output_mi_thunk (FILE *file, tree thunk_fndecl ATTRIBUTE_UNUSED,
21582 HOST_WIDE_INT delta, HOST_WIDE_INT vcall_offset,
21583 tree function)
21584 {
21585 rtx this_rtx, insn, funexp;
21586
21587 reload_completed = 1;
21588 epilogue_completed = 1;
21589
21590 /* Mark the end of the (empty) prologue. */
21591 emit_note (NOTE_INSN_PROLOGUE_END);
21592
21593 /* Find the "this" pointer. If the function returns a structure,
21594 the structure return pointer is in r3. */
21595 if (aggregate_value_p (TREE_TYPE (TREE_TYPE (function)), function))
21596 this_rtx = gen_rtx_REG (Pmode, 4);
21597 else
21598 this_rtx = gen_rtx_REG (Pmode, 3);
21599
21600 /* Apply the constant offset, if required. */
21601 if (delta)
21602 emit_insn (gen_add3_insn (this_rtx, this_rtx, GEN_INT (delta)));
21603
21604 /* Apply the offset from the vtable, if required. */
21605 if (vcall_offset)
21606 {
21607 rtx vcall_offset_rtx = GEN_INT (vcall_offset);
21608 rtx tmp = gen_rtx_REG (Pmode, 12);
21609
21610 emit_move_insn (tmp, gen_rtx_MEM (Pmode, this_rtx));
21611 if (((unsigned HOST_WIDE_INT) vcall_offset) + 0x8000 >= 0x10000)
21612 {
21613 emit_insn (gen_add3_insn (tmp, tmp, vcall_offset_rtx));
21614 emit_move_insn (tmp, gen_rtx_MEM (Pmode, tmp));
21615 }
21616 else
21617 {
21618 rtx loc = gen_rtx_PLUS (Pmode, tmp, vcall_offset_rtx);
21619
21620 emit_move_insn (tmp, gen_rtx_MEM (Pmode, loc));
21621 }
21622 emit_insn (gen_add3_insn (this_rtx, this_rtx, tmp));
21623 }
21624
21625 /* Generate a tail call to the target function. */
21626 if (!TREE_USED (function))
21627 {
21628 assemble_external (function);
21629 TREE_USED (function) = 1;
21630 }
21631 funexp = XEXP (DECL_RTL (function), 0);
21632 funexp = gen_rtx_MEM (FUNCTION_MODE, funexp);
21633
21634 #if TARGET_MACHO
21635 if (MACHOPIC_INDIRECT)
21636 funexp = machopic_indirect_call_target (funexp);
21637 #endif
21638
21639 /* gen_sibcall expects reload to convert scratch pseudo to LR so we must
21640 generate sibcall RTL explicitly. */
21641 insn = emit_call_insn (
21642 gen_rtx_PARALLEL (VOIDmode,
21643 gen_rtvec (4,
21644 gen_rtx_CALL (VOIDmode,
21645 funexp, const0_rtx),
21646 gen_rtx_USE (VOIDmode, const0_rtx),
21647 gen_rtx_USE (VOIDmode,
21648 gen_rtx_REG (SImode,
21649 LR_REGNO)),
21650 gen_rtx_RETURN (VOIDmode))));
21651 SIBLING_CALL_P (insn) = 1;
21652 emit_barrier ();
21653
21654 /* Run just enough of rest_of_compilation to get the insns emitted.
21655 There's not really enough bulk here to make other passes such as
21656 instruction scheduling worth while. Note that use_thunk calls
21657 assemble_start_function and assemble_end_function. */
21658 insn = get_insns ();
21659 insn_locators_alloc ();
21660 shorten_branches (insn);
21661 final_start_function (insn, file, 1);
21662 final (insn, file, 1);
21663 final_end_function ();
21664
21665 reload_completed = 0;
21666 epilogue_completed = 0;
21667 }
21668 \f
21669 /* A quick summary of the various types of 'constant-pool tables'
21670 under PowerPC:
21671
21672 Target Flags Name One table per
21673 AIX (none) AIX TOC object file
21674 AIX -mfull-toc AIX TOC object file
21675 AIX -mminimal-toc AIX minimal TOC translation unit
21676 SVR4/EABI (none) SVR4 SDATA object file
21677 SVR4/EABI -fpic SVR4 pic object file
21678 SVR4/EABI -fPIC SVR4 PIC translation unit
21679 SVR4/EABI -mrelocatable EABI TOC function
21680 SVR4/EABI -maix AIX TOC object file
21681 SVR4/EABI -maix -mminimal-toc
21682 AIX minimal TOC translation unit
21683
21684 Name Reg. Set by entries contains:
21685 made by addrs? fp? sum?
21686
21687 AIX TOC 2 crt0 as Y option option
21688 AIX minimal TOC 30 prolog gcc Y Y option
21689 SVR4 SDATA 13 crt0 gcc N Y N
21690 SVR4 pic 30 prolog ld Y not yet N
21691 SVR4 PIC 30 prolog gcc Y option option
21692 EABI TOC 30 prolog gcc Y option option
21693
21694 */
21695
21696 /* Hash functions for the hash table. */
21697
21698 static unsigned
21699 rs6000_hash_constant (rtx k)
21700 {
21701 enum rtx_code code = GET_CODE (k);
21702 enum machine_mode mode = GET_MODE (k);
21703 unsigned result = (code << 3) ^ mode;
21704 const char *format;
21705 int flen, fidx;
21706
21707 format = GET_RTX_FORMAT (code);
21708 flen = strlen (format);
21709 fidx = 0;
21710
21711 switch (code)
21712 {
21713 case LABEL_REF:
21714 return result * 1231 + (unsigned) INSN_UID (XEXP (k, 0));
21715
21716 case CONST_DOUBLE:
21717 if (mode != VOIDmode)
21718 return real_hash (CONST_DOUBLE_REAL_VALUE (k)) * result;
21719 flen = 2;
21720 break;
21721
21722 case CODE_LABEL:
21723 fidx = 3;
21724 break;
21725
21726 default:
21727 break;
21728 }
21729
21730 for (; fidx < flen; fidx++)
21731 switch (format[fidx])
21732 {
21733 case 's':
21734 {
21735 unsigned i, len;
21736 const char *str = XSTR (k, fidx);
21737 len = strlen (str);
21738 result = result * 613 + len;
21739 for (i = 0; i < len; i++)
21740 result = result * 613 + (unsigned) str[i];
21741 break;
21742 }
21743 case 'u':
21744 case 'e':
21745 result = result * 1231 + rs6000_hash_constant (XEXP (k, fidx));
21746 break;
21747 case 'i':
21748 case 'n':
21749 result = result * 613 + (unsigned) XINT (k, fidx);
21750 break;
21751 case 'w':
21752 if (sizeof (unsigned) >= sizeof (HOST_WIDE_INT))
21753 result = result * 613 + (unsigned) XWINT (k, fidx);
21754 else
21755 {
21756 size_t i;
21757 for (i = 0; i < sizeof (HOST_WIDE_INT) / sizeof (unsigned); i++)
21758 result = result * 613 + (unsigned) (XWINT (k, fidx)
21759 >> CHAR_BIT * i);
21760 }
21761 break;
21762 case '0':
21763 break;
21764 default:
21765 gcc_unreachable ();
21766 }
21767
21768 return result;
21769 }
21770
21771 static unsigned
21772 toc_hash_function (const void *hash_entry)
21773 {
21774 const struct toc_hash_struct *thc =
21775 (const struct toc_hash_struct *) hash_entry;
21776 return rs6000_hash_constant (thc->key) ^ thc->key_mode;
21777 }
21778
21779 /* Compare H1 and H2 for equivalence. */
21780
21781 static int
21782 toc_hash_eq (const void *h1, const void *h2)
21783 {
21784 rtx r1 = ((const struct toc_hash_struct *) h1)->key;
21785 rtx r2 = ((const struct toc_hash_struct *) h2)->key;
21786
21787 if (((const struct toc_hash_struct *) h1)->key_mode
21788 != ((const struct toc_hash_struct *) h2)->key_mode)
21789 return 0;
21790
21791 return rtx_equal_p (r1, r2);
21792 }
21793
21794 /* These are the names given by the C++ front-end to vtables, and
21795 vtable-like objects. Ideally, this logic should not be here;
21796 instead, there should be some programmatic way of inquiring as
21797 to whether or not an object is a vtable. */
21798
21799 #define VTABLE_NAME_P(NAME) \
21800 (strncmp ("_vt.", name, strlen ("_vt.")) == 0 \
21801 || strncmp ("_ZTV", name, strlen ("_ZTV")) == 0 \
21802 || strncmp ("_ZTT", name, strlen ("_ZTT")) == 0 \
21803 || strncmp ("_ZTI", name, strlen ("_ZTI")) == 0 \
21804 || strncmp ("_ZTC", name, strlen ("_ZTC")) == 0)
21805
21806 #ifdef NO_DOLLAR_IN_LABEL
21807 /* Return a GGC-allocated character string translating dollar signs in
21808 input NAME to underscores. Used by XCOFF ASM_OUTPUT_LABELREF. */
21809
21810 const char *
21811 rs6000_xcoff_strip_dollar (const char *name)
21812 {
21813 char *strip, *p;
21814 int len;
21815
21816 p = strchr (name, '$');
21817
21818 if (p == 0 || p == name)
21819 return name;
21820
21821 len = strlen (name);
21822 strip = (char *) alloca (len + 1);
21823 strcpy (strip, name);
21824 p = strchr (strip, '$');
21825 while (p)
21826 {
21827 *p = '_';
21828 p = strchr (p + 1, '$');
21829 }
21830
21831 return ggc_alloc_string (strip, len);
21832 }
21833 #endif
21834
21835 void
21836 rs6000_output_symbol_ref (FILE *file, rtx x)
21837 {
21838 /* Currently C++ toc references to vtables can be emitted before it
21839 is decided whether the vtable is public or private. If this is
21840 the case, then the linker will eventually complain that there is
21841 a reference to an unknown section. Thus, for vtables only,
21842 we emit the TOC reference to reference the symbol and not the
21843 section. */
21844 const char *name = XSTR (x, 0);
21845
21846 if (VTABLE_NAME_P (name))
21847 {
21848 RS6000_OUTPUT_BASENAME (file, name);
21849 }
21850 else
21851 assemble_name (file, name);
21852 }
21853
21854 /* Output a TOC entry. We derive the entry name from what is being
21855 written. */
21856
21857 void
21858 output_toc (FILE *file, rtx x, int labelno, enum machine_mode mode)
21859 {
21860 char buf[256];
21861 const char *name = buf;
21862 rtx base = x;
21863 HOST_WIDE_INT offset = 0;
21864
21865 gcc_assert (!TARGET_NO_TOC);
21866
21867 /* When the linker won't eliminate them, don't output duplicate
21868 TOC entries (this happens on AIX if there is any kind of TOC,
21869 and on SVR4 under -fPIC or -mrelocatable). Don't do this for
21870 CODE_LABELs. */
21871 if (TARGET_TOC && GET_CODE (x) != LABEL_REF)
21872 {
21873 struct toc_hash_struct *h;
21874 void * * found;
21875
21876 /* Create toc_hash_table. This can't be done at OVERRIDE_OPTIONS
21877 time because GGC is not initialized at that point. */
21878 if (toc_hash_table == NULL)
21879 toc_hash_table = htab_create_ggc (1021, toc_hash_function,
21880 toc_hash_eq, NULL);
21881
21882 h = ggc_alloc_toc_hash_struct ();
21883 h->key = x;
21884 h->key_mode = mode;
21885 h->labelno = labelno;
21886
21887 found = htab_find_slot (toc_hash_table, h, INSERT);
21888 if (*found == NULL)
21889 *found = h;
21890 else /* This is indeed a duplicate.
21891 Set this label equal to that label. */
21892 {
21893 fputs ("\t.set ", file);
21894 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (file, "LC");
21895 fprintf (file, "%d,", labelno);
21896 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (file, "LC");
21897 fprintf (file, "%d\n", ((*(const struct toc_hash_struct **)
21898 found)->labelno));
21899 return;
21900 }
21901 }
21902
21903 /* If we're going to put a double constant in the TOC, make sure it's
21904 aligned properly when strict alignment is on. */
21905 if (GET_CODE (x) == CONST_DOUBLE
21906 && STRICT_ALIGNMENT
21907 && GET_MODE_BITSIZE (mode) >= 64
21908 && ! (TARGET_NO_FP_IN_TOC && ! TARGET_MINIMAL_TOC)) {
21909 ASM_OUTPUT_ALIGN (file, 3);
21910 }
21911
21912 (*targetm.asm_out.internal_label) (file, "LC", labelno);
21913
21914 /* Handle FP constants specially. Note that if we have a minimal
21915 TOC, things we put here aren't actually in the TOC, so we can allow
21916 FP constants. */
21917 if (GET_CODE (x) == CONST_DOUBLE &&
21918 (GET_MODE (x) == TFmode || GET_MODE (x) == TDmode))
21919 {
21920 REAL_VALUE_TYPE rv;
21921 long k[4];
21922
21923 REAL_VALUE_FROM_CONST_DOUBLE (rv, x);
21924 if (DECIMAL_FLOAT_MODE_P (GET_MODE (x)))
21925 REAL_VALUE_TO_TARGET_DECIMAL128 (rv, k);
21926 else
21927 REAL_VALUE_TO_TARGET_LONG_DOUBLE (rv, k);
21928
21929 if (TARGET_64BIT)
21930 {
21931 if (TARGET_MINIMAL_TOC)
21932 fputs (DOUBLE_INT_ASM_OP, file);
21933 else
21934 fprintf (file, "\t.tc FT_%lx_%lx_%lx_%lx[TC],",
21935 k[0] & 0xffffffff, k[1] & 0xffffffff,
21936 k[2] & 0xffffffff, k[3] & 0xffffffff);
21937 fprintf (file, "0x%lx%08lx,0x%lx%08lx\n",
21938 k[0] & 0xffffffff, k[1] & 0xffffffff,
21939 k[2] & 0xffffffff, k[3] & 0xffffffff);
21940 return;
21941 }
21942 else
21943 {
21944 if (TARGET_MINIMAL_TOC)
21945 fputs ("\t.long ", file);
21946 else
21947 fprintf (file, "\t.tc FT_%lx_%lx_%lx_%lx[TC],",
21948 k[0] & 0xffffffff, k[1] & 0xffffffff,
21949 k[2] & 0xffffffff, k[3] & 0xffffffff);
21950 fprintf (file, "0x%lx,0x%lx,0x%lx,0x%lx\n",
21951 k[0] & 0xffffffff, k[1] & 0xffffffff,
21952 k[2] & 0xffffffff, k[3] & 0xffffffff);
21953 return;
21954 }
21955 }
21956 else if (GET_CODE (x) == CONST_DOUBLE &&
21957 (GET_MODE (x) == DFmode || GET_MODE (x) == DDmode))
21958 {
21959 REAL_VALUE_TYPE rv;
21960 long k[2];
21961
21962 REAL_VALUE_FROM_CONST_DOUBLE (rv, x);
21963
21964 if (DECIMAL_FLOAT_MODE_P (GET_MODE (x)))
21965 REAL_VALUE_TO_TARGET_DECIMAL64 (rv, k);
21966 else
21967 REAL_VALUE_TO_TARGET_DOUBLE (rv, k);
21968
21969 if (TARGET_64BIT)
21970 {
21971 if (TARGET_MINIMAL_TOC)
21972 fputs (DOUBLE_INT_ASM_OP, file);
21973 else
21974 fprintf (file, "\t.tc FD_%lx_%lx[TC],",
21975 k[0] & 0xffffffff, k[1] & 0xffffffff);
21976 fprintf (file, "0x%lx%08lx\n",
21977 k[0] & 0xffffffff, k[1] & 0xffffffff);
21978 return;
21979 }
21980 else
21981 {
21982 if (TARGET_MINIMAL_TOC)
21983 fputs ("\t.long ", file);
21984 else
21985 fprintf (file, "\t.tc FD_%lx_%lx[TC],",
21986 k[0] & 0xffffffff, k[1] & 0xffffffff);
21987 fprintf (file, "0x%lx,0x%lx\n",
21988 k[0] & 0xffffffff, k[1] & 0xffffffff);
21989 return;
21990 }
21991 }
21992 else if (GET_CODE (x) == CONST_DOUBLE &&
21993 (GET_MODE (x) == SFmode || GET_MODE (x) == SDmode))
21994 {
21995 REAL_VALUE_TYPE rv;
21996 long l;
21997
21998 REAL_VALUE_FROM_CONST_DOUBLE (rv, x);
21999 if (DECIMAL_FLOAT_MODE_P (GET_MODE (x)))
22000 REAL_VALUE_TO_TARGET_DECIMAL32 (rv, l);
22001 else
22002 REAL_VALUE_TO_TARGET_SINGLE (rv, l);
22003
22004 if (TARGET_64BIT)
22005 {
22006 if (TARGET_MINIMAL_TOC)
22007 fputs (DOUBLE_INT_ASM_OP, file);
22008 else
22009 fprintf (file, "\t.tc FS_%lx[TC],", l & 0xffffffff);
22010 fprintf (file, "0x%lx00000000\n", l & 0xffffffff);
22011 return;
22012 }
22013 else
22014 {
22015 if (TARGET_MINIMAL_TOC)
22016 fputs ("\t.long ", file);
22017 else
22018 fprintf (file, "\t.tc FS_%lx[TC],", l & 0xffffffff);
22019 fprintf (file, "0x%lx\n", l & 0xffffffff);
22020 return;
22021 }
22022 }
22023 else if (GET_MODE (x) == VOIDmode
22024 && (GET_CODE (x) == CONST_INT || GET_CODE (x) == CONST_DOUBLE))
22025 {
22026 unsigned HOST_WIDE_INT low;
22027 HOST_WIDE_INT high;
22028
22029 if (GET_CODE (x) == CONST_DOUBLE)
22030 {
22031 low = CONST_DOUBLE_LOW (x);
22032 high = CONST_DOUBLE_HIGH (x);
22033 }
22034 else
22035 #if HOST_BITS_PER_WIDE_INT == 32
22036 {
22037 low = INTVAL (x);
22038 high = (low & 0x80000000) ? ~0 : 0;
22039 }
22040 #else
22041 {
22042 low = INTVAL (x) & 0xffffffff;
22043 high = (HOST_WIDE_INT) INTVAL (x) >> 32;
22044 }
22045 #endif
22046
22047 /* TOC entries are always Pmode-sized, but since this
22048 is a bigendian machine then if we're putting smaller
22049 integer constants in the TOC we have to pad them.
22050 (This is still a win over putting the constants in
22051 a separate constant pool, because then we'd have
22052 to have both a TOC entry _and_ the actual constant.)
22053
22054 For a 32-bit target, CONST_INT values are loaded and shifted
22055 entirely within `low' and can be stored in one TOC entry. */
22056
22057 /* It would be easy to make this work, but it doesn't now. */
22058 gcc_assert (!TARGET_64BIT || POINTER_SIZE >= GET_MODE_BITSIZE (mode));
22059
22060 if (POINTER_SIZE > GET_MODE_BITSIZE (mode))
22061 {
22062 #if HOST_BITS_PER_WIDE_INT == 32
22063 lshift_double (low, high, POINTER_SIZE - GET_MODE_BITSIZE (mode),
22064 POINTER_SIZE, &low, &high, 0);
22065 #else
22066 low |= high << 32;
22067 low <<= POINTER_SIZE - GET_MODE_BITSIZE (mode);
22068 high = (HOST_WIDE_INT) low >> 32;
22069 low &= 0xffffffff;
22070 #endif
22071 }
22072
22073 if (TARGET_64BIT)
22074 {
22075 if (TARGET_MINIMAL_TOC)
22076 fputs (DOUBLE_INT_ASM_OP, file);
22077 else
22078 fprintf (file, "\t.tc ID_%lx_%lx[TC],",
22079 (long) high & 0xffffffff, (long) low & 0xffffffff);
22080 fprintf (file, "0x%lx%08lx\n",
22081 (long) high & 0xffffffff, (long) low & 0xffffffff);
22082 return;
22083 }
22084 else
22085 {
22086 if (POINTER_SIZE < GET_MODE_BITSIZE (mode))
22087 {
22088 if (TARGET_MINIMAL_TOC)
22089 fputs ("\t.long ", file);
22090 else
22091 fprintf (file, "\t.tc ID_%lx_%lx[TC],",
22092 (long) high & 0xffffffff, (long) low & 0xffffffff);
22093 fprintf (file, "0x%lx,0x%lx\n",
22094 (long) high & 0xffffffff, (long) low & 0xffffffff);
22095 }
22096 else
22097 {
22098 if (TARGET_MINIMAL_TOC)
22099 fputs ("\t.long ", file);
22100 else
22101 fprintf (file, "\t.tc IS_%lx[TC],", (long) low & 0xffffffff);
22102 fprintf (file, "0x%lx\n", (long) low & 0xffffffff);
22103 }
22104 return;
22105 }
22106 }
22107
22108 if (GET_CODE (x) == CONST)
22109 {
22110 gcc_assert (GET_CODE (XEXP (x, 0)) == PLUS
22111 && GET_CODE (XEXP (XEXP (x, 0), 1)) == CONST_INT);
22112
22113 base = XEXP (XEXP (x, 0), 0);
22114 offset = INTVAL (XEXP (XEXP (x, 0), 1));
22115 }
22116
22117 switch (GET_CODE (base))
22118 {
22119 case SYMBOL_REF:
22120 name = XSTR (base, 0);
22121 break;
22122
22123 case LABEL_REF:
22124 ASM_GENERATE_INTERNAL_LABEL (buf, "L",
22125 CODE_LABEL_NUMBER (XEXP (base, 0)));
22126 break;
22127
22128 case CODE_LABEL:
22129 ASM_GENERATE_INTERNAL_LABEL (buf, "L", CODE_LABEL_NUMBER (base));
22130 break;
22131
22132 default:
22133 gcc_unreachable ();
22134 }
22135
22136 if (TARGET_MINIMAL_TOC)
22137 fputs (TARGET_32BIT ? "\t.long " : DOUBLE_INT_ASM_OP, file);
22138 else
22139 {
22140 fputs ("\t.tc ", file);
22141 RS6000_OUTPUT_BASENAME (file, name);
22142
22143 if (offset < 0)
22144 fprintf (file, ".N" HOST_WIDE_INT_PRINT_UNSIGNED, - offset);
22145 else if (offset)
22146 fprintf (file, ".P" HOST_WIDE_INT_PRINT_UNSIGNED, offset);
22147
22148 fputs ("[TC],", file);
22149 }
22150
22151 /* Currently C++ toc references to vtables can be emitted before it
22152 is decided whether the vtable is public or private. If this is
22153 the case, then the linker will eventually complain that there is
22154 a TOC reference to an unknown section. Thus, for vtables only,
22155 we emit the TOC reference to reference the symbol and not the
22156 section. */
22157 if (VTABLE_NAME_P (name))
22158 {
22159 RS6000_OUTPUT_BASENAME (file, name);
22160 if (offset < 0)
22161 fprintf (file, HOST_WIDE_INT_PRINT_DEC, offset);
22162 else if (offset > 0)
22163 fprintf (file, "+" HOST_WIDE_INT_PRINT_DEC, offset);
22164 }
22165 else
22166 output_addr_const (file, x);
22167 putc ('\n', file);
22168 }
22169 \f
22170 /* Output an assembler pseudo-op to write an ASCII string of N characters
22171 starting at P to FILE.
22172
22173 On the RS/6000, we have to do this using the .byte operation and
22174 write out special characters outside the quoted string.
22175 Also, the assembler is broken; very long strings are truncated,
22176 so we must artificially break them up early. */
22177
22178 void
22179 output_ascii (FILE *file, const char *p, int n)
22180 {
22181 char c;
22182 int i, count_string;
22183 const char *for_string = "\t.byte \"";
22184 const char *for_decimal = "\t.byte ";
22185 const char *to_close = NULL;
22186
22187 count_string = 0;
22188 for (i = 0; i < n; i++)
22189 {
22190 c = *p++;
22191 if (c >= ' ' && c < 0177)
22192 {
22193 if (for_string)
22194 fputs (for_string, file);
22195 putc (c, file);
22196
22197 /* Write two quotes to get one. */
22198 if (c == '"')
22199 {
22200 putc (c, file);
22201 ++count_string;
22202 }
22203
22204 for_string = NULL;
22205 for_decimal = "\"\n\t.byte ";
22206 to_close = "\"\n";
22207 ++count_string;
22208
22209 if (count_string >= 512)
22210 {
22211 fputs (to_close, file);
22212
22213 for_string = "\t.byte \"";
22214 for_decimal = "\t.byte ";
22215 to_close = NULL;
22216 count_string = 0;
22217 }
22218 }
22219 else
22220 {
22221 if (for_decimal)
22222 fputs (for_decimal, file);
22223 fprintf (file, "%d", c);
22224
22225 for_string = "\n\t.byte \"";
22226 for_decimal = ", ";
22227 to_close = "\n";
22228 count_string = 0;
22229 }
22230 }
22231
22232 /* Now close the string if we have written one. Then end the line. */
22233 if (to_close)
22234 fputs (to_close, file);
22235 }
22236 \f
22237 /* Generate a unique section name for FILENAME for a section type
22238 represented by SECTION_DESC. Output goes into BUF.
22239
22240 SECTION_DESC can be any string, as long as it is different for each
22241 possible section type.
22242
22243 We name the section in the same manner as xlc. The name begins with an
22244 underscore followed by the filename (after stripping any leading directory
22245 names) with the last period replaced by the string SECTION_DESC. If
22246 FILENAME does not contain a period, SECTION_DESC is appended to the end of
22247 the name. */
22248
22249 void
22250 rs6000_gen_section_name (char **buf, const char *filename,
22251 const char *section_desc)
22252 {
22253 const char *q, *after_last_slash, *last_period = 0;
22254 char *p;
22255 int len;
22256
22257 after_last_slash = filename;
22258 for (q = filename; *q; q++)
22259 {
22260 if (*q == '/')
22261 after_last_slash = q + 1;
22262 else if (*q == '.')
22263 last_period = q;
22264 }
22265
22266 len = strlen (after_last_slash) + strlen (section_desc) + 2;
22267 *buf = (char *) xmalloc (len);
22268
22269 p = *buf;
22270 *p++ = '_';
22271
22272 for (q = after_last_slash; *q; q++)
22273 {
22274 if (q == last_period)
22275 {
22276 strcpy (p, section_desc);
22277 p += strlen (section_desc);
22278 break;
22279 }
22280
22281 else if (ISALNUM (*q))
22282 *p++ = *q;
22283 }
22284
22285 if (last_period == 0)
22286 strcpy (p, section_desc);
22287 else
22288 *p = '\0';
22289 }
22290 \f
22291 /* Emit profile function. */
22292
22293 void
22294 output_profile_hook (int labelno ATTRIBUTE_UNUSED)
22295 {
22296 /* Non-standard profiling for kernels, which just saves LR then calls
22297 _mcount without worrying about arg saves. The idea is to change
22298 the function prologue as little as possible as it isn't easy to
22299 account for arg save/restore code added just for _mcount. */
22300 if (TARGET_PROFILE_KERNEL)
22301 return;
22302
22303 if (DEFAULT_ABI == ABI_AIX)
22304 {
22305 #ifndef NO_PROFILE_COUNTERS
22306 # define NO_PROFILE_COUNTERS 0
22307 #endif
22308 if (NO_PROFILE_COUNTERS)
22309 emit_library_call (init_one_libfunc (RS6000_MCOUNT),
22310 LCT_NORMAL, VOIDmode, 0);
22311 else
22312 {
22313 char buf[30];
22314 const char *label_name;
22315 rtx fun;
22316
22317 ASM_GENERATE_INTERNAL_LABEL (buf, "LP", labelno);
22318 label_name = (*targetm.strip_name_encoding) (ggc_strdup (buf));
22319 fun = gen_rtx_SYMBOL_REF (Pmode, label_name);
22320
22321 emit_library_call (init_one_libfunc (RS6000_MCOUNT),
22322 LCT_NORMAL, VOIDmode, 1, fun, Pmode);
22323 }
22324 }
22325 else if (DEFAULT_ABI == ABI_DARWIN)
22326 {
22327 const char *mcount_name = RS6000_MCOUNT;
22328 int caller_addr_regno = LR_REGNO;
22329
22330 /* Be conservative and always set this, at least for now. */
22331 crtl->uses_pic_offset_table = 1;
22332
22333 #if TARGET_MACHO
22334 /* For PIC code, set up a stub and collect the caller's address
22335 from r0, which is where the prologue puts it. */
22336 if (MACHOPIC_INDIRECT
22337 && crtl->uses_pic_offset_table)
22338 caller_addr_regno = 0;
22339 #endif
22340 emit_library_call (gen_rtx_SYMBOL_REF (Pmode, mcount_name),
22341 LCT_NORMAL, VOIDmode, 1,
22342 gen_rtx_REG (Pmode, caller_addr_regno), Pmode);
22343 }
22344 }
22345
22346 /* Write function profiler code. */
22347
22348 void
22349 output_function_profiler (FILE *file, int labelno)
22350 {
22351 char buf[100];
22352
22353 switch (DEFAULT_ABI)
22354 {
22355 default:
22356 gcc_unreachable ();
22357
22358 case ABI_V4:
22359 if (!TARGET_32BIT)
22360 {
22361 warning (0, "no profiling of 64-bit code for this ABI");
22362 return;
22363 }
22364 ASM_GENERATE_INTERNAL_LABEL (buf, "LP", labelno);
22365 fprintf (file, "\tmflr %s\n", reg_names[0]);
22366 if (NO_PROFILE_COUNTERS)
22367 {
22368 asm_fprintf (file, "\t{st|stw} %s,4(%s)\n",
22369 reg_names[0], reg_names[1]);
22370 }
22371 else if (TARGET_SECURE_PLT && flag_pic)
22372 {
22373 asm_fprintf (file, "\tbcl 20,31,1f\n1:\n\t{st|stw} %s,4(%s)\n",
22374 reg_names[0], reg_names[1]);
22375 asm_fprintf (file, "\tmflr %s\n", reg_names[12]);
22376 asm_fprintf (file, "\t{cau|addis} %s,%s,",
22377 reg_names[12], reg_names[12]);
22378 assemble_name (file, buf);
22379 asm_fprintf (file, "-1b@ha\n\t{cal|la} %s,", reg_names[0]);
22380 assemble_name (file, buf);
22381 asm_fprintf (file, "-1b@l(%s)\n", reg_names[12]);
22382 }
22383 else if (flag_pic == 1)
22384 {
22385 fputs ("\tbl _GLOBAL_OFFSET_TABLE_@local-4\n", file);
22386 asm_fprintf (file, "\t{st|stw} %s,4(%s)\n",
22387 reg_names[0], reg_names[1]);
22388 asm_fprintf (file, "\tmflr %s\n", reg_names[12]);
22389 asm_fprintf (file, "\t{l|lwz} %s,", reg_names[0]);
22390 assemble_name (file, buf);
22391 asm_fprintf (file, "@got(%s)\n", reg_names[12]);
22392 }
22393 else if (flag_pic > 1)
22394 {
22395 asm_fprintf (file, "\t{st|stw} %s,4(%s)\n",
22396 reg_names[0], reg_names[1]);
22397 /* Now, we need to get the address of the label. */
22398 fputs ("\tbcl 20,31,1f\n\t.long ", file);
22399 assemble_name (file, buf);
22400 fputs ("-.\n1:", file);
22401 asm_fprintf (file, "\tmflr %s\n", reg_names[11]);
22402 asm_fprintf (file, "\t{l|lwz} %s,0(%s)\n",
22403 reg_names[0], reg_names[11]);
22404 asm_fprintf (file, "\t{cax|add} %s,%s,%s\n",
22405 reg_names[0], reg_names[0], reg_names[11]);
22406 }
22407 else
22408 {
22409 asm_fprintf (file, "\t{liu|lis} %s,", reg_names[12]);
22410 assemble_name (file, buf);
22411 fputs ("@ha\n", file);
22412 asm_fprintf (file, "\t{st|stw} %s,4(%s)\n",
22413 reg_names[0], reg_names[1]);
22414 asm_fprintf (file, "\t{cal|la} %s,", reg_names[0]);
22415 assemble_name (file, buf);
22416 asm_fprintf (file, "@l(%s)\n", reg_names[12]);
22417 }
22418
22419 /* ABI_V4 saves the static chain reg with ASM_OUTPUT_REG_PUSH. */
22420 fprintf (file, "\tbl %s%s\n",
22421 RS6000_MCOUNT, flag_pic ? "@plt" : "");
22422 break;
22423
22424 case ABI_AIX:
22425 case ABI_DARWIN:
22426 if (!TARGET_PROFILE_KERNEL)
22427 {
22428 /* Don't do anything, done in output_profile_hook (). */
22429 }
22430 else
22431 {
22432 gcc_assert (!TARGET_32BIT);
22433
22434 asm_fprintf (file, "\tmflr %s\n", reg_names[0]);
22435 asm_fprintf (file, "\tstd %s,16(%s)\n", reg_names[0], reg_names[1]);
22436
22437 if (cfun->static_chain_decl != NULL)
22438 {
22439 asm_fprintf (file, "\tstd %s,24(%s)\n",
22440 reg_names[STATIC_CHAIN_REGNUM], reg_names[1]);
22441 fprintf (file, "\tbl %s\n", RS6000_MCOUNT);
22442 asm_fprintf (file, "\tld %s,24(%s)\n",
22443 reg_names[STATIC_CHAIN_REGNUM], reg_names[1]);
22444 }
22445 else
22446 fprintf (file, "\tbl %s\n", RS6000_MCOUNT);
22447 }
22448 break;
22449 }
22450 }
22451
22452 \f
22453
22454 /* The following variable value is the last issued insn. */
22455
22456 static rtx last_scheduled_insn;
22457
22458 /* The following variable helps to balance issuing of load and
22459 store instructions */
22460
22461 static int load_store_pendulum;
22462
22463 /* Power4 load update and store update instructions are cracked into a
22464 load or store and an integer insn which are executed in the same cycle.
22465 Branches have their own dispatch slot which does not count against the
22466 GCC issue rate, but it changes the program flow so there are no other
22467 instructions to issue in this cycle. */
22468
22469 static int
22470 rs6000_variable_issue_1 (rtx insn, int more)
22471 {
22472 last_scheduled_insn = insn;
22473 if (GET_CODE (PATTERN (insn)) == USE
22474 || GET_CODE (PATTERN (insn)) == CLOBBER)
22475 {
22476 cached_can_issue_more = more;
22477 return cached_can_issue_more;
22478 }
22479
22480 if (insn_terminates_group_p (insn, current_group))
22481 {
22482 cached_can_issue_more = 0;
22483 return cached_can_issue_more;
22484 }
22485
22486 /* If no reservation, but reach here */
22487 if (recog_memoized (insn) < 0)
22488 return more;
22489
22490 if (rs6000_sched_groups)
22491 {
22492 if (is_microcoded_insn (insn))
22493 cached_can_issue_more = 0;
22494 else if (is_cracked_insn (insn))
22495 cached_can_issue_more = more > 2 ? more - 2 : 0;
22496 else
22497 cached_can_issue_more = more - 1;
22498
22499 return cached_can_issue_more;
22500 }
22501
22502 if (rs6000_cpu_attr == CPU_CELL && is_nonpipeline_insn (insn))
22503 return 0;
22504
22505 cached_can_issue_more = more - 1;
22506 return cached_can_issue_more;
22507 }
22508
22509 static int
22510 rs6000_variable_issue (FILE *stream, int verbose, rtx insn, int more)
22511 {
22512 int r = rs6000_variable_issue_1 (insn, more);
22513 if (verbose)
22514 fprintf (stream, "// rs6000_variable_issue (more = %d) = %d\n", more, r);
22515 return r;
22516 }
22517
22518 /* Adjust the cost of a scheduling dependency. Return the new cost of
22519 a dependency LINK or INSN on DEP_INSN. COST is the current cost. */
22520
22521 static int
22522 rs6000_adjust_cost (rtx insn, rtx link, rtx dep_insn, int cost)
22523 {
22524 enum attr_type attr_type;
22525
22526 if (! recog_memoized (insn))
22527 return 0;
22528
22529 switch (REG_NOTE_KIND (link))
22530 {
22531 case REG_DEP_TRUE:
22532 {
22533 /* Data dependency; DEP_INSN writes a register that INSN reads
22534 some cycles later. */
22535
22536 /* Separate a load from a narrower, dependent store. */
22537 if (rs6000_sched_groups
22538 && GET_CODE (PATTERN (insn)) == SET
22539 && GET_CODE (PATTERN (dep_insn)) == SET
22540 && GET_CODE (XEXP (PATTERN (insn), 1)) == MEM
22541 && GET_CODE (XEXP (PATTERN (dep_insn), 0)) == MEM
22542 && (GET_MODE_SIZE (GET_MODE (XEXP (PATTERN (insn), 1)))
22543 > GET_MODE_SIZE (GET_MODE (XEXP (PATTERN (dep_insn), 0)))))
22544 return cost + 14;
22545
22546 attr_type = get_attr_type (insn);
22547
22548 switch (attr_type)
22549 {
22550 case TYPE_JMPREG:
22551 /* Tell the first scheduling pass about the latency between
22552 a mtctr and bctr (and mtlr and br/blr). The first
22553 scheduling pass will not know about this latency since
22554 the mtctr instruction, which has the latency associated
22555 to it, will be generated by reload. */
22556 return TARGET_POWER ? 5 : 4;
22557 case TYPE_BRANCH:
22558 /* Leave some extra cycles between a compare and its
22559 dependent branch, to inhibit expensive mispredicts. */
22560 if ((rs6000_cpu_attr == CPU_PPC603
22561 || rs6000_cpu_attr == CPU_PPC604
22562 || rs6000_cpu_attr == CPU_PPC604E
22563 || rs6000_cpu_attr == CPU_PPC620
22564 || rs6000_cpu_attr == CPU_PPC630
22565 || rs6000_cpu_attr == CPU_PPC750
22566 || rs6000_cpu_attr == CPU_PPC7400
22567 || rs6000_cpu_attr == CPU_PPC7450
22568 || rs6000_cpu_attr == CPU_POWER4
22569 || rs6000_cpu_attr == CPU_POWER5
22570 || rs6000_cpu_attr == CPU_POWER7
22571 || rs6000_cpu_attr == CPU_CELL)
22572 && recog_memoized (dep_insn)
22573 && (INSN_CODE (dep_insn) >= 0))
22574
22575 switch (get_attr_type (dep_insn))
22576 {
22577 case TYPE_CMP:
22578 case TYPE_COMPARE:
22579 case TYPE_DELAYED_COMPARE:
22580 case TYPE_IMUL_COMPARE:
22581 case TYPE_LMUL_COMPARE:
22582 case TYPE_FPCOMPARE:
22583 case TYPE_CR_LOGICAL:
22584 case TYPE_DELAYED_CR:
22585 return cost + 2;
22586 default:
22587 break;
22588 }
22589 break;
22590
22591 case TYPE_STORE:
22592 case TYPE_STORE_U:
22593 case TYPE_STORE_UX:
22594 case TYPE_FPSTORE:
22595 case TYPE_FPSTORE_U:
22596 case TYPE_FPSTORE_UX:
22597 if ((rs6000_cpu == PROCESSOR_POWER6)
22598 && recog_memoized (dep_insn)
22599 && (INSN_CODE (dep_insn) >= 0))
22600 {
22601
22602 if (GET_CODE (PATTERN (insn)) != SET)
22603 /* If this happens, we have to extend this to schedule
22604 optimally. Return default for now. */
22605 return cost;
22606
22607 /* Adjust the cost for the case where the value written
22608 by a fixed point operation is used as the address
22609 gen value on a store. */
22610 switch (get_attr_type (dep_insn))
22611 {
22612 case TYPE_LOAD:
22613 case TYPE_LOAD_U:
22614 case TYPE_LOAD_UX:
22615 case TYPE_CNTLZ:
22616 {
22617 if (! store_data_bypass_p (dep_insn, insn))
22618 return 4;
22619 break;
22620 }
22621 case TYPE_LOAD_EXT:
22622 case TYPE_LOAD_EXT_U:
22623 case TYPE_LOAD_EXT_UX:
22624 case TYPE_VAR_SHIFT_ROTATE:
22625 case TYPE_VAR_DELAYED_COMPARE:
22626 {
22627 if (! store_data_bypass_p (dep_insn, insn))
22628 return 6;
22629 break;
22630 }
22631 case TYPE_INTEGER:
22632 case TYPE_COMPARE:
22633 case TYPE_FAST_COMPARE:
22634 case TYPE_EXTS:
22635 case TYPE_SHIFT:
22636 case TYPE_INSERT_WORD:
22637 case TYPE_INSERT_DWORD:
22638 case TYPE_FPLOAD_U:
22639 case TYPE_FPLOAD_UX:
22640 case TYPE_STORE_U:
22641 case TYPE_STORE_UX:
22642 case TYPE_FPSTORE_U:
22643 case TYPE_FPSTORE_UX:
22644 {
22645 if (! store_data_bypass_p (dep_insn, insn))
22646 return 3;
22647 break;
22648 }
22649 case TYPE_IMUL:
22650 case TYPE_IMUL2:
22651 case TYPE_IMUL3:
22652 case TYPE_LMUL:
22653 case TYPE_IMUL_COMPARE:
22654 case TYPE_LMUL_COMPARE:
22655 {
22656 if (! store_data_bypass_p (dep_insn, insn))
22657 return 17;
22658 break;
22659 }
22660 case TYPE_IDIV:
22661 {
22662 if (! store_data_bypass_p (dep_insn, insn))
22663 return 45;
22664 break;
22665 }
22666 case TYPE_LDIV:
22667 {
22668 if (! store_data_bypass_p (dep_insn, insn))
22669 return 57;
22670 break;
22671 }
22672 default:
22673 break;
22674 }
22675 }
22676 break;
22677
22678 case TYPE_LOAD:
22679 case TYPE_LOAD_U:
22680 case TYPE_LOAD_UX:
22681 case TYPE_LOAD_EXT:
22682 case TYPE_LOAD_EXT_U:
22683 case TYPE_LOAD_EXT_UX:
22684 if ((rs6000_cpu == PROCESSOR_POWER6)
22685 && recog_memoized (dep_insn)
22686 && (INSN_CODE (dep_insn) >= 0))
22687 {
22688
22689 /* Adjust the cost for the case where the value written
22690 by a fixed point instruction is used within the address
22691 gen portion of a subsequent load(u)(x) */
22692 switch (get_attr_type (dep_insn))
22693 {
22694 case TYPE_LOAD:
22695 case TYPE_LOAD_U:
22696 case TYPE_LOAD_UX:
22697 case TYPE_CNTLZ:
22698 {
22699 if (set_to_load_agen (dep_insn, insn))
22700 return 4;
22701 break;
22702 }
22703 case TYPE_LOAD_EXT:
22704 case TYPE_LOAD_EXT_U:
22705 case TYPE_LOAD_EXT_UX:
22706 case TYPE_VAR_SHIFT_ROTATE:
22707 case TYPE_VAR_DELAYED_COMPARE:
22708 {
22709 if (set_to_load_agen (dep_insn, insn))
22710 return 6;
22711 break;
22712 }
22713 case TYPE_INTEGER:
22714 case TYPE_COMPARE:
22715 case TYPE_FAST_COMPARE:
22716 case TYPE_EXTS:
22717 case TYPE_SHIFT:
22718 case TYPE_INSERT_WORD:
22719 case TYPE_INSERT_DWORD:
22720 case TYPE_FPLOAD_U:
22721 case TYPE_FPLOAD_UX:
22722 case TYPE_STORE_U:
22723 case TYPE_STORE_UX:
22724 case TYPE_FPSTORE_U:
22725 case TYPE_FPSTORE_UX:
22726 {
22727 if (set_to_load_agen (dep_insn, insn))
22728 return 3;
22729 break;
22730 }
22731 case TYPE_IMUL:
22732 case TYPE_IMUL2:
22733 case TYPE_IMUL3:
22734 case TYPE_LMUL:
22735 case TYPE_IMUL_COMPARE:
22736 case TYPE_LMUL_COMPARE:
22737 {
22738 if (set_to_load_agen (dep_insn, insn))
22739 return 17;
22740 break;
22741 }
22742 case TYPE_IDIV:
22743 {
22744 if (set_to_load_agen (dep_insn, insn))
22745 return 45;
22746 break;
22747 }
22748 case TYPE_LDIV:
22749 {
22750 if (set_to_load_agen (dep_insn, insn))
22751 return 57;
22752 break;
22753 }
22754 default:
22755 break;
22756 }
22757 }
22758 break;
22759
22760 case TYPE_FPLOAD:
22761 if ((rs6000_cpu == PROCESSOR_POWER6)
22762 && recog_memoized (dep_insn)
22763 && (INSN_CODE (dep_insn) >= 0)
22764 && (get_attr_type (dep_insn) == TYPE_MFFGPR))
22765 return 2;
22766
22767 default:
22768 break;
22769 }
22770
22771 /* Fall out to return default cost. */
22772 }
22773 break;
22774
22775 case REG_DEP_OUTPUT:
22776 /* Output dependency; DEP_INSN writes a register that INSN writes some
22777 cycles later. */
22778 if ((rs6000_cpu == PROCESSOR_POWER6)
22779 && recog_memoized (dep_insn)
22780 && (INSN_CODE (dep_insn) >= 0))
22781 {
22782 attr_type = get_attr_type (insn);
22783
22784 switch (attr_type)
22785 {
22786 case TYPE_FP:
22787 if (get_attr_type (dep_insn) == TYPE_FP)
22788 return 1;
22789 break;
22790 case TYPE_FPLOAD:
22791 if (get_attr_type (dep_insn) == TYPE_MFFGPR)
22792 return 2;
22793 break;
22794 default:
22795 break;
22796 }
22797 }
22798 case REG_DEP_ANTI:
22799 /* Anti dependency; DEP_INSN reads a register that INSN writes some
22800 cycles later. */
22801 return 0;
22802
22803 default:
22804 gcc_unreachable ();
22805 }
22806
22807 return cost;
22808 }
22809
22810 /* Debug version of rs6000_adjust_cost. */
22811
22812 static int
22813 rs6000_debug_adjust_cost (rtx insn, rtx link, rtx dep_insn, int cost)
22814 {
22815 int ret = rs6000_adjust_cost (insn, link, dep_insn, cost);
22816
22817 if (ret != cost)
22818 {
22819 const char *dep;
22820
22821 switch (REG_NOTE_KIND (link))
22822 {
22823 default: dep = "unknown depencency"; break;
22824 case REG_DEP_TRUE: dep = "data dependency"; break;
22825 case REG_DEP_OUTPUT: dep = "output dependency"; break;
22826 case REG_DEP_ANTI: dep = "anti depencency"; break;
22827 }
22828
22829 fprintf (stderr,
22830 "\nrs6000_adjust_cost, final cost = %d, orig cost = %d, "
22831 "%s, insn:\n", ret, cost, dep);
22832
22833 debug_rtx (insn);
22834 }
22835
22836 return ret;
22837 }
22838
22839 /* The function returns a true if INSN is microcoded.
22840 Return false otherwise. */
22841
22842 static bool
22843 is_microcoded_insn (rtx insn)
22844 {
22845 if (!insn || !NONDEBUG_INSN_P (insn)
22846 || GET_CODE (PATTERN (insn)) == USE
22847 || GET_CODE (PATTERN (insn)) == CLOBBER)
22848 return false;
22849
22850 if (rs6000_cpu_attr == CPU_CELL)
22851 return get_attr_cell_micro (insn) == CELL_MICRO_ALWAYS;
22852
22853 if (rs6000_sched_groups)
22854 {
22855 enum attr_type type = get_attr_type (insn);
22856 if (type == TYPE_LOAD_EXT_U
22857 || type == TYPE_LOAD_EXT_UX
22858 || type == TYPE_LOAD_UX
22859 || type == TYPE_STORE_UX
22860 || type == TYPE_MFCR)
22861 return true;
22862 }
22863
22864 return false;
22865 }
22866
22867 /* The function returns true if INSN is cracked into 2 instructions
22868 by the processor (and therefore occupies 2 issue slots). */
22869
22870 static bool
22871 is_cracked_insn (rtx insn)
22872 {
22873 if (!insn || !NONDEBUG_INSN_P (insn)
22874 || GET_CODE (PATTERN (insn)) == USE
22875 || GET_CODE (PATTERN (insn)) == CLOBBER)
22876 return false;
22877
22878 if (rs6000_sched_groups)
22879 {
22880 enum attr_type type = get_attr_type (insn);
22881 if (type == TYPE_LOAD_U || type == TYPE_STORE_U
22882 || type == TYPE_FPLOAD_U || type == TYPE_FPSTORE_U
22883 || type == TYPE_FPLOAD_UX || type == TYPE_FPSTORE_UX
22884 || type == TYPE_LOAD_EXT || type == TYPE_DELAYED_CR
22885 || type == TYPE_COMPARE || type == TYPE_DELAYED_COMPARE
22886 || type == TYPE_IMUL_COMPARE || type == TYPE_LMUL_COMPARE
22887 || type == TYPE_IDIV || type == TYPE_LDIV
22888 || type == TYPE_INSERT_WORD)
22889 return true;
22890 }
22891
22892 return false;
22893 }
22894
22895 /* The function returns true if INSN can be issued only from
22896 the branch slot. */
22897
22898 static bool
22899 is_branch_slot_insn (rtx insn)
22900 {
22901 if (!insn || !NONDEBUG_INSN_P (insn)
22902 || GET_CODE (PATTERN (insn)) == USE
22903 || GET_CODE (PATTERN (insn)) == CLOBBER)
22904 return false;
22905
22906 if (rs6000_sched_groups)
22907 {
22908 enum attr_type type = get_attr_type (insn);
22909 if (type == TYPE_BRANCH || type == TYPE_JMPREG)
22910 return true;
22911 return false;
22912 }
22913
22914 return false;
22915 }
22916
22917 /* The function returns true if out_inst sets a value that is
22918 used in the address generation computation of in_insn */
22919 static bool
22920 set_to_load_agen (rtx out_insn, rtx in_insn)
22921 {
22922 rtx out_set, in_set;
22923
22924 /* For performance reasons, only handle the simple case where
22925 both loads are a single_set. */
22926 out_set = single_set (out_insn);
22927 if (out_set)
22928 {
22929 in_set = single_set (in_insn);
22930 if (in_set)
22931 return reg_mentioned_p (SET_DEST (out_set), SET_SRC (in_set));
22932 }
22933
22934 return false;
22935 }
22936
22937 /* The function returns true if the target storage location of
22938 out_insn is adjacent to the target storage location of in_insn */
22939 /* Return 1 if memory locations are adjacent. */
22940
22941 static bool
22942 adjacent_mem_locations (rtx insn1, rtx insn2)
22943 {
22944
22945 rtx a = get_store_dest (PATTERN (insn1));
22946 rtx b = get_store_dest (PATTERN (insn2));
22947
22948 if ((GET_CODE (XEXP (a, 0)) == REG
22949 || (GET_CODE (XEXP (a, 0)) == PLUS
22950 && GET_CODE (XEXP (XEXP (a, 0), 1)) == CONST_INT))
22951 && (GET_CODE (XEXP (b, 0)) == REG
22952 || (GET_CODE (XEXP (b, 0)) == PLUS
22953 && GET_CODE (XEXP (XEXP (b, 0), 1)) == CONST_INT)))
22954 {
22955 HOST_WIDE_INT val0 = 0, val1 = 0, val_diff;
22956 rtx reg0, reg1;
22957
22958 if (GET_CODE (XEXP (a, 0)) == PLUS)
22959 {
22960 reg0 = XEXP (XEXP (a, 0), 0);
22961 val0 = INTVAL (XEXP (XEXP (a, 0), 1));
22962 }
22963 else
22964 reg0 = XEXP (a, 0);
22965
22966 if (GET_CODE (XEXP (b, 0)) == PLUS)
22967 {
22968 reg1 = XEXP (XEXP (b, 0), 0);
22969 val1 = INTVAL (XEXP (XEXP (b, 0), 1));
22970 }
22971 else
22972 reg1 = XEXP (b, 0);
22973
22974 val_diff = val1 - val0;
22975
22976 return ((REGNO (reg0) == REGNO (reg1))
22977 && ((MEM_SIZE (a) && val_diff == INTVAL (MEM_SIZE (a)))
22978 || (MEM_SIZE (b) && val_diff == -INTVAL (MEM_SIZE (b)))));
22979 }
22980
22981 return false;
22982 }
22983
22984 /* A C statement (sans semicolon) to update the integer scheduling
22985 priority INSN_PRIORITY (INSN). Increase the priority to execute the
22986 INSN earlier, reduce the priority to execute INSN later. Do not
22987 define this macro if you do not need to adjust the scheduling
22988 priorities of insns. */
22989
22990 static int
22991 rs6000_adjust_priority (rtx insn ATTRIBUTE_UNUSED, int priority)
22992 {
22993 /* On machines (like the 750) which have asymmetric integer units,
22994 where one integer unit can do multiply and divides and the other
22995 can't, reduce the priority of multiply/divide so it is scheduled
22996 before other integer operations. */
22997
22998 #if 0
22999 if (! INSN_P (insn))
23000 return priority;
23001
23002 if (GET_CODE (PATTERN (insn)) == USE)
23003 return priority;
23004
23005 switch (rs6000_cpu_attr) {
23006 case CPU_PPC750:
23007 switch (get_attr_type (insn))
23008 {
23009 default:
23010 break;
23011
23012 case TYPE_IMUL:
23013 case TYPE_IDIV:
23014 fprintf (stderr, "priority was %#x (%d) before adjustment\n",
23015 priority, priority);
23016 if (priority >= 0 && priority < 0x01000000)
23017 priority >>= 3;
23018 break;
23019 }
23020 }
23021 #endif
23022
23023 if (insn_must_be_first_in_group (insn)
23024 && reload_completed
23025 && current_sched_info->sched_max_insns_priority
23026 && rs6000_sched_restricted_insns_priority)
23027 {
23028
23029 /* Prioritize insns that can be dispatched only in the first
23030 dispatch slot. */
23031 if (rs6000_sched_restricted_insns_priority == 1)
23032 /* Attach highest priority to insn. This means that in
23033 haifa-sched.c:ready_sort(), dispatch-slot restriction considerations
23034 precede 'priority' (critical path) considerations. */
23035 return current_sched_info->sched_max_insns_priority;
23036 else if (rs6000_sched_restricted_insns_priority == 2)
23037 /* Increase priority of insn by a minimal amount. This means that in
23038 haifa-sched.c:ready_sort(), only 'priority' (critical path)
23039 considerations precede dispatch-slot restriction considerations. */
23040 return (priority + 1);
23041 }
23042
23043 if (rs6000_cpu == PROCESSOR_POWER6
23044 && ((load_store_pendulum == -2 && is_load_insn (insn))
23045 || (load_store_pendulum == 2 && is_store_insn (insn))))
23046 /* Attach highest priority to insn if the scheduler has just issued two
23047 stores and this instruction is a load, or two loads and this instruction
23048 is a store. Power6 wants loads and stores scheduled alternately
23049 when possible */
23050 return current_sched_info->sched_max_insns_priority;
23051
23052 return priority;
23053 }
23054
23055 /* Return true if the instruction is nonpipelined on the Cell. */
23056 static bool
23057 is_nonpipeline_insn (rtx insn)
23058 {
23059 enum attr_type type;
23060 if (!insn || !NONDEBUG_INSN_P (insn)
23061 || GET_CODE (PATTERN (insn)) == USE
23062 || GET_CODE (PATTERN (insn)) == CLOBBER)
23063 return false;
23064
23065 type = get_attr_type (insn);
23066 if (type == TYPE_IMUL
23067 || type == TYPE_IMUL2
23068 || type == TYPE_IMUL3
23069 || type == TYPE_LMUL
23070 || type == TYPE_IDIV
23071 || type == TYPE_LDIV
23072 || type == TYPE_SDIV
23073 || type == TYPE_DDIV
23074 || type == TYPE_SSQRT
23075 || type == TYPE_DSQRT
23076 || type == TYPE_MFCR
23077 || type == TYPE_MFCRF
23078 || type == TYPE_MFJMPR)
23079 {
23080 return true;
23081 }
23082 return false;
23083 }
23084
23085
23086 /* Return how many instructions the machine can issue per cycle. */
23087
23088 static int
23089 rs6000_issue_rate (void)
23090 {
23091 /* Unless scheduling for register pressure, use issue rate of 1 for
23092 first scheduling pass to decrease degradation. */
23093 if (!reload_completed && !flag_sched_pressure)
23094 return 1;
23095
23096 switch (rs6000_cpu_attr) {
23097 case CPU_RIOS1: /* ? */
23098 case CPU_RS64A:
23099 case CPU_PPC601: /* ? */
23100 case CPU_PPC7450:
23101 return 3;
23102 case CPU_PPC440:
23103 case CPU_PPC603:
23104 case CPU_PPC750:
23105 case CPU_PPC7400:
23106 case CPU_PPC8540:
23107 case CPU_CELL:
23108 case CPU_PPCE300C2:
23109 case CPU_PPCE300C3:
23110 case CPU_PPCE500MC:
23111 case CPU_PPCE500MC64:
23112 case CPU_TITAN:
23113 return 2;
23114 case CPU_RIOS2:
23115 case CPU_PPC476:
23116 case CPU_PPC604:
23117 case CPU_PPC604E:
23118 case CPU_PPC620:
23119 case CPU_PPC630:
23120 return 4;
23121 case CPU_POWER4:
23122 case CPU_POWER5:
23123 case CPU_POWER6:
23124 case CPU_POWER7:
23125 return 5;
23126 default:
23127 return 1;
23128 }
23129 }
23130
23131 /* Return how many instructions to look ahead for better insn
23132 scheduling. */
23133
23134 static int
23135 rs6000_use_sched_lookahead (void)
23136 {
23137 if (rs6000_cpu_attr == CPU_PPC8540)
23138 return 4;
23139 if (rs6000_cpu_attr == CPU_CELL)
23140 return (reload_completed ? 8 : 0);
23141 return 0;
23142 }
23143
23144 /* We are choosing insn from the ready queue. Return nonzero if INSN can be chosen. */
23145 static int
23146 rs6000_use_sched_lookahead_guard (rtx insn)
23147 {
23148 if (rs6000_cpu_attr != CPU_CELL)
23149 return 1;
23150
23151 if (insn == NULL_RTX || !INSN_P (insn))
23152 abort ();
23153
23154 if (!reload_completed
23155 || is_nonpipeline_insn (insn)
23156 || is_microcoded_insn (insn))
23157 return 0;
23158
23159 return 1;
23160 }
23161
23162 /* Determine is PAT refers to memory. */
23163
23164 static bool
23165 is_mem_ref (rtx pat)
23166 {
23167 const char * fmt;
23168 int i, j;
23169 bool ret = false;
23170
23171 /* stack_tie does not produce any real memory traffic. */
23172 if (GET_CODE (pat) == UNSPEC
23173 && XINT (pat, 1) == UNSPEC_TIE)
23174 return false;
23175
23176 if (GET_CODE (pat) == MEM)
23177 return true;
23178
23179 /* Recursively process the pattern. */
23180 fmt = GET_RTX_FORMAT (GET_CODE (pat));
23181
23182 for (i = GET_RTX_LENGTH (GET_CODE (pat)) - 1; i >= 0 && !ret; i--)
23183 {
23184 if (fmt[i] == 'e')
23185 ret |= is_mem_ref (XEXP (pat, i));
23186 else if (fmt[i] == 'E')
23187 for (j = XVECLEN (pat, i) - 1; j >= 0; j--)
23188 ret |= is_mem_ref (XVECEXP (pat, i, j));
23189 }
23190
23191 return ret;
23192 }
23193
23194 /* Determine if PAT is a PATTERN of a load insn. */
23195
23196 static bool
23197 is_load_insn1 (rtx pat)
23198 {
23199 if (!pat || pat == NULL_RTX)
23200 return false;
23201
23202 if (GET_CODE (pat) == SET)
23203 return is_mem_ref (SET_SRC (pat));
23204
23205 if (GET_CODE (pat) == PARALLEL)
23206 {
23207 int i;
23208
23209 for (i = 0; i < XVECLEN (pat, 0); i++)
23210 if (is_load_insn1 (XVECEXP (pat, 0, i)))
23211 return true;
23212 }
23213
23214 return false;
23215 }
23216
23217 /* Determine if INSN loads from memory. */
23218
23219 static bool
23220 is_load_insn (rtx insn)
23221 {
23222 if (!insn || !INSN_P (insn))
23223 return false;
23224
23225 if (GET_CODE (insn) == CALL_INSN)
23226 return false;
23227
23228 return is_load_insn1 (PATTERN (insn));
23229 }
23230
23231 /* Determine if PAT is a PATTERN of a store insn. */
23232
23233 static bool
23234 is_store_insn1 (rtx pat)
23235 {
23236 if (!pat || pat == NULL_RTX)
23237 return false;
23238
23239 if (GET_CODE (pat) == SET)
23240 return is_mem_ref (SET_DEST (pat));
23241
23242 if (GET_CODE (pat) == PARALLEL)
23243 {
23244 int i;
23245
23246 for (i = 0; i < XVECLEN (pat, 0); i++)
23247 if (is_store_insn1 (XVECEXP (pat, 0, i)))
23248 return true;
23249 }
23250
23251 return false;
23252 }
23253
23254 /* Determine if INSN stores to memory. */
23255
23256 static bool
23257 is_store_insn (rtx insn)
23258 {
23259 if (!insn || !INSN_P (insn))
23260 return false;
23261
23262 return is_store_insn1 (PATTERN (insn));
23263 }
23264
23265 /* Return the dest of a store insn. */
23266
23267 static rtx
23268 get_store_dest (rtx pat)
23269 {
23270 gcc_assert (is_store_insn1 (pat));
23271
23272 if (GET_CODE (pat) == SET)
23273 return SET_DEST (pat);
23274 else if (GET_CODE (pat) == PARALLEL)
23275 {
23276 int i;
23277
23278 for (i = 0; i < XVECLEN (pat, 0); i++)
23279 {
23280 rtx inner_pat = XVECEXP (pat, 0, i);
23281 if (GET_CODE (inner_pat) == SET
23282 && is_mem_ref (SET_DEST (inner_pat)))
23283 return inner_pat;
23284 }
23285 }
23286 /* We shouldn't get here, because we should have either a simple
23287 store insn or a store with update which are covered above. */
23288 gcc_unreachable();
23289 }
23290
23291 /* Returns whether the dependence between INSN and NEXT is considered
23292 costly by the given target. */
23293
23294 static bool
23295 rs6000_is_costly_dependence (dep_t dep, int cost, int distance)
23296 {
23297 rtx insn;
23298 rtx next;
23299
23300 /* If the flag is not enabled - no dependence is considered costly;
23301 allow all dependent insns in the same group.
23302 This is the most aggressive option. */
23303 if (rs6000_sched_costly_dep == no_dep_costly)
23304 return false;
23305
23306 /* If the flag is set to 1 - a dependence is always considered costly;
23307 do not allow dependent instructions in the same group.
23308 This is the most conservative option. */
23309 if (rs6000_sched_costly_dep == all_deps_costly)
23310 return true;
23311
23312 insn = DEP_PRO (dep);
23313 next = DEP_CON (dep);
23314
23315 if (rs6000_sched_costly_dep == store_to_load_dep_costly
23316 && is_load_insn (next)
23317 && is_store_insn (insn))
23318 /* Prevent load after store in the same group. */
23319 return true;
23320
23321 if (rs6000_sched_costly_dep == true_store_to_load_dep_costly
23322 && is_load_insn (next)
23323 && is_store_insn (insn)
23324 && DEP_TYPE (dep) == REG_DEP_TRUE)
23325 /* Prevent load after store in the same group if it is a true
23326 dependence. */
23327 return true;
23328
23329 /* The flag is set to X; dependences with latency >= X are considered costly,
23330 and will not be scheduled in the same group. */
23331 if (rs6000_sched_costly_dep <= max_dep_latency
23332 && ((cost - distance) >= (int)rs6000_sched_costly_dep))
23333 return true;
23334
23335 return false;
23336 }
23337
23338 /* Return the next insn after INSN that is found before TAIL is reached,
23339 skipping any "non-active" insns - insns that will not actually occupy
23340 an issue slot. Return NULL_RTX if such an insn is not found. */
23341
23342 static rtx
23343 get_next_active_insn (rtx insn, rtx tail)
23344 {
23345 if (insn == NULL_RTX || insn == tail)
23346 return NULL_RTX;
23347
23348 while (1)
23349 {
23350 insn = NEXT_INSN (insn);
23351 if (insn == NULL_RTX || insn == tail)
23352 return NULL_RTX;
23353
23354 if (CALL_P (insn)
23355 || JUMP_P (insn)
23356 || (NONJUMP_INSN_P (insn)
23357 && GET_CODE (PATTERN (insn)) != USE
23358 && GET_CODE (PATTERN (insn)) != CLOBBER
23359 && INSN_CODE (insn) != CODE_FOR_stack_tie))
23360 break;
23361 }
23362 return insn;
23363 }
23364
23365 /* We are about to begin issuing insns for this clock cycle. */
23366
23367 static int
23368 rs6000_sched_reorder (FILE *dump ATTRIBUTE_UNUSED, int sched_verbose,
23369 rtx *ready ATTRIBUTE_UNUSED,
23370 int *pn_ready ATTRIBUTE_UNUSED,
23371 int clock_var ATTRIBUTE_UNUSED)
23372 {
23373 int n_ready = *pn_ready;
23374
23375 if (sched_verbose)
23376 fprintf (dump, "// rs6000_sched_reorder :\n");
23377
23378 /* Reorder the ready list, if the second to last ready insn
23379 is a nonepipeline insn. */
23380 if (rs6000_cpu_attr == CPU_CELL && n_ready > 1)
23381 {
23382 if (is_nonpipeline_insn (ready[n_ready - 1])
23383 && (recog_memoized (ready[n_ready - 2]) > 0))
23384 /* Simply swap first two insns. */
23385 {
23386 rtx tmp = ready[n_ready - 1];
23387 ready[n_ready - 1] = ready[n_ready - 2];
23388 ready[n_ready - 2] = tmp;
23389 }
23390 }
23391
23392 if (rs6000_cpu == PROCESSOR_POWER6)
23393 load_store_pendulum = 0;
23394
23395 return rs6000_issue_rate ();
23396 }
23397
23398 /* Like rs6000_sched_reorder, but called after issuing each insn. */
23399
23400 static int
23401 rs6000_sched_reorder2 (FILE *dump, int sched_verbose, rtx *ready,
23402 int *pn_ready, int clock_var ATTRIBUTE_UNUSED)
23403 {
23404 if (sched_verbose)
23405 fprintf (dump, "// rs6000_sched_reorder2 :\n");
23406
23407 /* For Power6, we need to handle some special cases to try and keep the
23408 store queue from overflowing and triggering expensive flushes.
23409
23410 This code monitors how load and store instructions are being issued
23411 and skews the ready list one way or the other to increase the likelihood
23412 that a desired instruction is issued at the proper time.
23413
23414 A couple of things are done. First, we maintain a "load_store_pendulum"
23415 to track the current state of load/store issue.
23416
23417 - If the pendulum is at zero, then no loads or stores have been
23418 issued in the current cycle so we do nothing.
23419
23420 - If the pendulum is 1, then a single load has been issued in this
23421 cycle and we attempt to locate another load in the ready list to
23422 issue with it.
23423
23424 - If the pendulum is -2, then two stores have already been
23425 issued in this cycle, so we increase the priority of the first load
23426 in the ready list to increase it's likelihood of being chosen first
23427 in the next cycle.
23428
23429 - If the pendulum is -1, then a single store has been issued in this
23430 cycle and we attempt to locate another store in the ready list to
23431 issue with it, preferring a store to an adjacent memory location to
23432 facilitate store pairing in the store queue.
23433
23434 - If the pendulum is 2, then two loads have already been
23435 issued in this cycle, so we increase the priority of the first store
23436 in the ready list to increase it's likelihood of being chosen first
23437 in the next cycle.
23438
23439 - If the pendulum < -2 or > 2, then do nothing.
23440
23441 Note: This code covers the most common scenarios. There exist non
23442 load/store instructions which make use of the LSU and which
23443 would need to be accounted for to strictly model the behavior
23444 of the machine. Those instructions are currently unaccounted
23445 for to help minimize compile time overhead of this code.
23446 */
23447 if (rs6000_cpu == PROCESSOR_POWER6 && last_scheduled_insn)
23448 {
23449 int pos;
23450 int i;
23451 rtx tmp;
23452
23453 if (is_store_insn (last_scheduled_insn))
23454 /* Issuing a store, swing the load_store_pendulum to the left */
23455 load_store_pendulum--;
23456 else if (is_load_insn (last_scheduled_insn))
23457 /* Issuing a load, swing the load_store_pendulum to the right */
23458 load_store_pendulum++;
23459 else
23460 return cached_can_issue_more;
23461
23462 /* If the pendulum is balanced, or there is only one instruction on
23463 the ready list, then all is well, so return. */
23464 if ((load_store_pendulum == 0) || (*pn_ready <= 1))
23465 return cached_can_issue_more;
23466
23467 if (load_store_pendulum == 1)
23468 {
23469 /* A load has been issued in this cycle. Scan the ready list
23470 for another load to issue with it */
23471 pos = *pn_ready-1;
23472
23473 while (pos >= 0)
23474 {
23475 if (is_load_insn (ready[pos]))
23476 {
23477 /* Found a load. Move it to the head of the ready list,
23478 and adjust it's priority so that it is more likely to
23479 stay there */
23480 tmp = ready[pos];
23481 for (i=pos; i<*pn_ready-1; i++)
23482 ready[i] = ready[i + 1];
23483 ready[*pn_ready-1] = tmp;
23484
23485 if (!sel_sched_p () && INSN_PRIORITY_KNOWN (tmp))
23486 INSN_PRIORITY (tmp)++;
23487 break;
23488 }
23489 pos--;
23490 }
23491 }
23492 else if (load_store_pendulum == -2)
23493 {
23494 /* Two stores have been issued in this cycle. Increase the
23495 priority of the first load in the ready list to favor it for
23496 issuing in the next cycle. */
23497 pos = *pn_ready-1;
23498
23499 while (pos >= 0)
23500 {
23501 if (is_load_insn (ready[pos])
23502 && !sel_sched_p ()
23503 && INSN_PRIORITY_KNOWN (ready[pos]))
23504 {
23505 INSN_PRIORITY (ready[pos])++;
23506
23507 /* Adjust the pendulum to account for the fact that a load
23508 was found and increased in priority. This is to prevent
23509 increasing the priority of multiple loads */
23510 load_store_pendulum--;
23511
23512 break;
23513 }
23514 pos--;
23515 }
23516 }
23517 else if (load_store_pendulum == -1)
23518 {
23519 /* A store has been issued in this cycle. Scan the ready list for
23520 another store to issue with it, preferring a store to an adjacent
23521 memory location */
23522 int first_store_pos = -1;
23523
23524 pos = *pn_ready-1;
23525
23526 while (pos >= 0)
23527 {
23528 if (is_store_insn (ready[pos]))
23529 {
23530 /* Maintain the index of the first store found on the
23531 list */
23532 if (first_store_pos == -1)
23533 first_store_pos = pos;
23534
23535 if (is_store_insn (last_scheduled_insn)
23536 && adjacent_mem_locations (last_scheduled_insn,ready[pos]))
23537 {
23538 /* Found an adjacent store. Move it to the head of the
23539 ready list, and adjust it's priority so that it is
23540 more likely to stay there */
23541 tmp = ready[pos];
23542 for (i=pos; i<*pn_ready-1; i++)
23543 ready[i] = ready[i + 1];
23544 ready[*pn_ready-1] = tmp;
23545
23546 if (!sel_sched_p () && INSN_PRIORITY_KNOWN (tmp))
23547 INSN_PRIORITY (tmp)++;
23548
23549 first_store_pos = -1;
23550
23551 break;
23552 };
23553 }
23554 pos--;
23555 }
23556
23557 if (first_store_pos >= 0)
23558 {
23559 /* An adjacent store wasn't found, but a non-adjacent store was,
23560 so move the non-adjacent store to the front of the ready
23561 list, and adjust its priority so that it is more likely to
23562 stay there. */
23563 tmp = ready[first_store_pos];
23564 for (i=first_store_pos; i<*pn_ready-1; i++)
23565 ready[i] = ready[i + 1];
23566 ready[*pn_ready-1] = tmp;
23567 if (!sel_sched_p () && INSN_PRIORITY_KNOWN (tmp))
23568 INSN_PRIORITY (tmp)++;
23569 }
23570 }
23571 else if (load_store_pendulum == 2)
23572 {
23573 /* Two loads have been issued in this cycle. Increase the priority
23574 of the first store in the ready list to favor it for issuing in
23575 the next cycle. */
23576 pos = *pn_ready-1;
23577
23578 while (pos >= 0)
23579 {
23580 if (is_store_insn (ready[pos])
23581 && !sel_sched_p ()
23582 && INSN_PRIORITY_KNOWN (ready[pos]))
23583 {
23584 INSN_PRIORITY (ready[pos])++;
23585
23586 /* Adjust the pendulum to account for the fact that a store
23587 was found and increased in priority. This is to prevent
23588 increasing the priority of multiple stores */
23589 load_store_pendulum++;
23590
23591 break;
23592 }
23593 pos--;
23594 }
23595 }
23596 }
23597
23598 return cached_can_issue_more;
23599 }
23600
23601 /* Return whether the presence of INSN causes a dispatch group termination
23602 of group WHICH_GROUP.
23603
23604 If WHICH_GROUP == current_group, this function will return true if INSN
23605 causes the termination of the current group (i.e, the dispatch group to
23606 which INSN belongs). This means that INSN will be the last insn in the
23607 group it belongs to.
23608
23609 If WHICH_GROUP == previous_group, this function will return true if INSN
23610 causes the termination of the previous group (i.e, the dispatch group that
23611 precedes the group to which INSN belongs). This means that INSN will be
23612 the first insn in the group it belongs to). */
23613
23614 static bool
23615 insn_terminates_group_p (rtx insn, enum group_termination which_group)
23616 {
23617 bool first, last;
23618
23619 if (! insn)
23620 return false;
23621
23622 first = insn_must_be_first_in_group (insn);
23623 last = insn_must_be_last_in_group (insn);
23624
23625 if (first && last)
23626 return true;
23627
23628 if (which_group == current_group)
23629 return last;
23630 else if (which_group == previous_group)
23631 return first;
23632
23633 return false;
23634 }
23635
23636
23637 static bool
23638 insn_must_be_first_in_group (rtx insn)
23639 {
23640 enum attr_type type;
23641
23642 if (!insn
23643 || GET_CODE (insn) == NOTE
23644 || DEBUG_INSN_P (insn)
23645 || GET_CODE (PATTERN (insn)) == USE
23646 || GET_CODE (PATTERN (insn)) == CLOBBER)
23647 return false;
23648
23649 switch (rs6000_cpu)
23650 {
23651 case PROCESSOR_POWER5:
23652 if (is_cracked_insn (insn))
23653 return true;
23654 case PROCESSOR_POWER4:
23655 if (is_microcoded_insn (insn))
23656 return true;
23657
23658 if (!rs6000_sched_groups)
23659 return false;
23660
23661 type = get_attr_type (insn);
23662
23663 switch (type)
23664 {
23665 case TYPE_MFCR:
23666 case TYPE_MFCRF:
23667 case TYPE_MTCR:
23668 case TYPE_DELAYED_CR:
23669 case TYPE_CR_LOGICAL:
23670 case TYPE_MTJMPR:
23671 case TYPE_MFJMPR:
23672 case TYPE_IDIV:
23673 case TYPE_LDIV:
23674 case TYPE_LOAD_L:
23675 case TYPE_STORE_C:
23676 case TYPE_ISYNC:
23677 case TYPE_SYNC:
23678 return true;
23679 default:
23680 break;
23681 }
23682 break;
23683 case PROCESSOR_POWER6:
23684 type = get_attr_type (insn);
23685
23686 switch (type)
23687 {
23688 case TYPE_INSERT_DWORD:
23689 case TYPE_EXTS:
23690 case TYPE_CNTLZ:
23691 case TYPE_SHIFT:
23692 case TYPE_VAR_SHIFT_ROTATE:
23693 case TYPE_TRAP:
23694 case TYPE_IMUL:
23695 case TYPE_IMUL2:
23696 case TYPE_IMUL3:
23697 case TYPE_LMUL:
23698 case TYPE_IDIV:
23699 case TYPE_INSERT_WORD:
23700 case TYPE_DELAYED_COMPARE:
23701 case TYPE_IMUL_COMPARE:
23702 case TYPE_LMUL_COMPARE:
23703 case TYPE_FPCOMPARE:
23704 case TYPE_MFCR:
23705 case TYPE_MTCR:
23706 case TYPE_MFJMPR:
23707 case TYPE_MTJMPR:
23708 case TYPE_ISYNC:
23709 case TYPE_SYNC:
23710 case TYPE_LOAD_L:
23711 case TYPE_STORE_C:
23712 case TYPE_LOAD_U:
23713 case TYPE_LOAD_UX:
23714 case TYPE_LOAD_EXT_UX:
23715 case TYPE_STORE_U:
23716 case TYPE_STORE_UX:
23717 case TYPE_FPLOAD_U:
23718 case TYPE_FPLOAD_UX:
23719 case TYPE_FPSTORE_U:
23720 case TYPE_FPSTORE_UX:
23721 return true;
23722 default:
23723 break;
23724 }
23725 break;
23726 case PROCESSOR_POWER7:
23727 type = get_attr_type (insn);
23728
23729 switch (type)
23730 {
23731 case TYPE_CR_LOGICAL:
23732 case TYPE_MFCR:
23733 case TYPE_MFCRF:
23734 case TYPE_MTCR:
23735 case TYPE_IDIV:
23736 case TYPE_LDIV:
23737 case TYPE_COMPARE:
23738 case TYPE_DELAYED_COMPARE:
23739 case TYPE_VAR_DELAYED_COMPARE:
23740 case TYPE_ISYNC:
23741 case TYPE_LOAD_L:
23742 case TYPE_STORE_C:
23743 case TYPE_LOAD_U:
23744 case TYPE_LOAD_UX:
23745 case TYPE_LOAD_EXT:
23746 case TYPE_LOAD_EXT_U:
23747 case TYPE_LOAD_EXT_UX:
23748 case TYPE_STORE_U:
23749 case TYPE_STORE_UX:
23750 case TYPE_FPLOAD_U:
23751 case TYPE_FPLOAD_UX:
23752 case TYPE_FPSTORE_U:
23753 case TYPE_FPSTORE_UX:
23754 case TYPE_MFJMPR:
23755 case TYPE_MTJMPR:
23756 return true;
23757 default:
23758 break;
23759 }
23760 break;
23761 default:
23762 break;
23763 }
23764
23765 return false;
23766 }
23767
23768 static bool
23769 insn_must_be_last_in_group (rtx insn)
23770 {
23771 enum attr_type type;
23772
23773 if (!insn
23774 || GET_CODE (insn) == NOTE
23775 || DEBUG_INSN_P (insn)
23776 || GET_CODE (PATTERN (insn)) == USE
23777 || GET_CODE (PATTERN (insn)) == CLOBBER)
23778 return false;
23779
23780 switch (rs6000_cpu) {
23781 case PROCESSOR_POWER4:
23782 case PROCESSOR_POWER5:
23783 if (is_microcoded_insn (insn))
23784 return true;
23785
23786 if (is_branch_slot_insn (insn))
23787 return true;
23788
23789 break;
23790 case PROCESSOR_POWER6:
23791 type = get_attr_type (insn);
23792
23793 switch (type)
23794 {
23795 case TYPE_EXTS:
23796 case TYPE_CNTLZ:
23797 case TYPE_SHIFT:
23798 case TYPE_VAR_SHIFT_ROTATE:
23799 case TYPE_TRAP:
23800 case TYPE_IMUL:
23801 case TYPE_IMUL2:
23802 case TYPE_IMUL3:
23803 case TYPE_LMUL:
23804 case TYPE_IDIV:
23805 case TYPE_DELAYED_COMPARE:
23806 case TYPE_IMUL_COMPARE:
23807 case TYPE_LMUL_COMPARE:
23808 case TYPE_FPCOMPARE:
23809 case TYPE_MFCR:
23810 case TYPE_MTCR:
23811 case TYPE_MFJMPR:
23812 case TYPE_MTJMPR:
23813 case TYPE_ISYNC:
23814 case TYPE_SYNC:
23815 case TYPE_LOAD_L:
23816 case TYPE_STORE_C:
23817 return true;
23818 default:
23819 break;
23820 }
23821 break;
23822 case PROCESSOR_POWER7:
23823 type = get_attr_type (insn);
23824
23825 switch (type)
23826 {
23827 case TYPE_ISYNC:
23828 case TYPE_SYNC:
23829 case TYPE_LOAD_L:
23830 case TYPE_STORE_C:
23831 case TYPE_LOAD_EXT_U:
23832 case TYPE_LOAD_EXT_UX:
23833 case TYPE_STORE_UX:
23834 return true;
23835 default:
23836 break;
23837 }
23838 break;
23839 default:
23840 break;
23841 }
23842
23843 return false;
23844 }
23845
23846 /* Return true if it is recommended to keep NEXT_INSN "far" (in a separate
23847 dispatch group) from the insns in GROUP_INSNS. Return false otherwise. */
23848
23849 static bool
23850 is_costly_group (rtx *group_insns, rtx next_insn)
23851 {
23852 int i;
23853 int issue_rate = rs6000_issue_rate ();
23854
23855 for (i = 0; i < issue_rate; i++)
23856 {
23857 sd_iterator_def sd_it;
23858 dep_t dep;
23859 rtx insn = group_insns[i];
23860
23861 if (!insn)
23862 continue;
23863
23864 FOR_EACH_DEP (insn, SD_LIST_FORW, sd_it, dep)
23865 {
23866 rtx next = DEP_CON (dep);
23867
23868 if (next == next_insn
23869 && rs6000_is_costly_dependence (dep, dep_cost (dep), 0))
23870 return true;
23871 }
23872 }
23873
23874 return false;
23875 }
23876
23877 /* Utility of the function redefine_groups.
23878 Check if it is too costly to schedule NEXT_INSN together with GROUP_INSNS
23879 in the same dispatch group. If so, insert nops before NEXT_INSN, in order
23880 to keep it "far" (in a separate group) from GROUP_INSNS, following
23881 one of the following schemes, depending on the value of the flag
23882 -minsert_sched_nops = X:
23883 (1) X == sched_finish_regroup_exact: insert exactly as many nops as needed
23884 in order to force NEXT_INSN into a separate group.
23885 (2) X < sched_finish_regroup_exact: insert exactly X nops.
23886 GROUP_END, CAN_ISSUE_MORE and GROUP_COUNT record the state after nop
23887 insertion (has a group just ended, how many vacant issue slots remain in the
23888 last group, and how many dispatch groups were encountered so far). */
23889
23890 static int
23891 force_new_group (int sched_verbose, FILE *dump, rtx *group_insns,
23892 rtx next_insn, bool *group_end, int can_issue_more,
23893 int *group_count)
23894 {
23895 rtx nop;
23896 bool force;
23897 int issue_rate = rs6000_issue_rate ();
23898 bool end = *group_end;
23899 int i;
23900
23901 if (next_insn == NULL_RTX || DEBUG_INSN_P (next_insn))
23902 return can_issue_more;
23903
23904 if (rs6000_sched_insert_nops > sched_finish_regroup_exact)
23905 return can_issue_more;
23906
23907 force = is_costly_group (group_insns, next_insn);
23908 if (!force)
23909 return can_issue_more;
23910
23911 if (sched_verbose > 6)
23912 fprintf (dump,"force: group count = %d, can_issue_more = %d\n",
23913 *group_count ,can_issue_more);
23914
23915 if (rs6000_sched_insert_nops == sched_finish_regroup_exact)
23916 {
23917 if (*group_end)
23918 can_issue_more = 0;
23919
23920 /* Since only a branch can be issued in the last issue_slot, it is
23921 sufficient to insert 'can_issue_more - 1' nops if next_insn is not
23922 a branch. If next_insn is a branch, we insert 'can_issue_more' nops;
23923 in this case the last nop will start a new group and the branch
23924 will be forced to the new group. */
23925 if (can_issue_more && !is_branch_slot_insn (next_insn))
23926 can_issue_more--;
23927
23928 while (can_issue_more > 0)
23929 {
23930 nop = gen_nop ();
23931 emit_insn_before (nop, next_insn);
23932 can_issue_more--;
23933 }
23934
23935 *group_end = true;
23936 return 0;
23937 }
23938
23939 if (rs6000_sched_insert_nops < sched_finish_regroup_exact)
23940 {
23941 int n_nops = rs6000_sched_insert_nops;
23942
23943 /* Nops can't be issued from the branch slot, so the effective
23944 issue_rate for nops is 'issue_rate - 1'. */
23945 if (can_issue_more == 0)
23946 can_issue_more = issue_rate;
23947 can_issue_more--;
23948 if (can_issue_more == 0)
23949 {
23950 can_issue_more = issue_rate - 1;
23951 (*group_count)++;
23952 end = true;
23953 for (i = 0; i < issue_rate; i++)
23954 {
23955 group_insns[i] = 0;
23956 }
23957 }
23958
23959 while (n_nops > 0)
23960 {
23961 nop = gen_nop ();
23962 emit_insn_before (nop, next_insn);
23963 if (can_issue_more == issue_rate - 1) /* new group begins */
23964 end = false;
23965 can_issue_more--;
23966 if (can_issue_more == 0)
23967 {
23968 can_issue_more = issue_rate - 1;
23969 (*group_count)++;
23970 end = true;
23971 for (i = 0; i < issue_rate; i++)
23972 {
23973 group_insns[i] = 0;
23974 }
23975 }
23976 n_nops--;
23977 }
23978
23979 /* Scale back relative to 'issue_rate' (instead of 'issue_rate - 1'). */
23980 can_issue_more++;
23981
23982 /* Is next_insn going to start a new group? */
23983 *group_end
23984 = (end
23985 || (can_issue_more == 1 && !is_branch_slot_insn (next_insn))
23986 || (can_issue_more <= 2 && is_cracked_insn (next_insn))
23987 || (can_issue_more < issue_rate &&
23988 insn_terminates_group_p (next_insn, previous_group)));
23989 if (*group_end && end)
23990 (*group_count)--;
23991
23992 if (sched_verbose > 6)
23993 fprintf (dump, "done force: group count = %d, can_issue_more = %d\n",
23994 *group_count, can_issue_more);
23995 return can_issue_more;
23996 }
23997
23998 return can_issue_more;
23999 }
24000
24001 /* This function tries to synch the dispatch groups that the compiler "sees"
24002 with the dispatch groups that the processor dispatcher is expected to
24003 form in practice. It tries to achieve this synchronization by forcing the
24004 estimated processor grouping on the compiler (as opposed to the function
24005 'pad_goups' which tries to force the scheduler's grouping on the processor).
24006
24007 The function scans the insn sequence between PREV_HEAD_INSN and TAIL and
24008 examines the (estimated) dispatch groups that will be formed by the processor
24009 dispatcher. It marks these group boundaries to reflect the estimated
24010 processor grouping, overriding the grouping that the scheduler had marked.
24011 Depending on the value of the flag '-minsert-sched-nops' this function can
24012 force certain insns into separate groups or force a certain distance between
24013 them by inserting nops, for example, if there exists a "costly dependence"
24014 between the insns.
24015
24016 The function estimates the group boundaries that the processor will form as
24017 follows: It keeps track of how many vacant issue slots are available after
24018 each insn. A subsequent insn will start a new group if one of the following
24019 4 cases applies:
24020 - no more vacant issue slots remain in the current dispatch group.
24021 - only the last issue slot, which is the branch slot, is vacant, but the next
24022 insn is not a branch.
24023 - only the last 2 or less issue slots, including the branch slot, are vacant,
24024 which means that a cracked insn (which occupies two issue slots) can't be
24025 issued in this group.
24026 - less than 'issue_rate' slots are vacant, and the next insn always needs to
24027 start a new group. */
24028
24029 static int
24030 redefine_groups (FILE *dump, int sched_verbose, rtx prev_head_insn, rtx tail)
24031 {
24032 rtx insn, next_insn;
24033 int issue_rate;
24034 int can_issue_more;
24035 int slot, i;
24036 bool group_end;
24037 int group_count = 0;
24038 rtx *group_insns;
24039
24040 /* Initialize. */
24041 issue_rate = rs6000_issue_rate ();
24042 group_insns = XALLOCAVEC (rtx, issue_rate);
24043 for (i = 0; i < issue_rate; i++)
24044 {
24045 group_insns[i] = 0;
24046 }
24047 can_issue_more = issue_rate;
24048 slot = 0;
24049 insn = get_next_active_insn (prev_head_insn, tail);
24050 group_end = false;
24051
24052 while (insn != NULL_RTX)
24053 {
24054 slot = (issue_rate - can_issue_more);
24055 group_insns[slot] = insn;
24056 can_issue_more =
24057 rs6000_variable_issue (dump, sched_verbose, insn, can_issue_more);
24058 if (insn_terminates_group_p (insn, current_group))
24059 can_issue_more = 0;
24060
24061 next_insn = get_next_active_insn (insn, tail);
24062 if (next_insn == NULL_RTX)
24063 return group_count + 1;
24064
24065 /* Is next_insn going to start a new group? */
24066 group_end
24067 = (can_issue_more == 0
24068 || (can_issue_more == 1 && !is_branch_slot_insn (next_insn))
24069 || (can_issue_more <= 2 && is_cracked_insn (next_insn))
24070 || (can_issue_more < issue_rate &&
24071 insn_terminates_group_p (next_insn, previous_group)));
24072
24073 can_issue_more = force_new_group (sched_verbose, dump, group_insns,
24074 next_insn, &group_end, can_issue_more,
24075 &group_count);
24076
24077 if (group_end)
24078 {
24079 group_count++;
24080 can_issue_more = 0;
24081 for (i = 0; i < issue_rate; i++)
24082 {
24083 group_insns[i] = 0;
24084 }
24085 }
24086
24087 if (GET_MODE (next_insn) == TImode && can_issue_more)
24088 PUT_MODE (next_insn, VOIDmode);
24089 else if (!can_issue_more && GET_MODE (next_insn) != TImode)
24090 PUT_MODE (next_insn, TImode);
24091
24092 insn = next_insn;
24093 if (can_issue_more == 0)
24094 can_issue_more = issue_rate;
24095 } /* while */
24096
24097 return group_count;
24098 }
24099
24100 /* Scan the insn sequence between PREV_HEAD_INSN and TAIL and examine the
24101 dispatch group boundaries that the scheduler had marked. Pad with nops
24102 any dispatch groups which have vacant issue slots, in order to force the
24103 scheduler's grouping on the processor dispatcher. The function
24104 returns the number of dispatch groups found. */
24105
24106 static int
24107 pad_groups (FILE *dump, int sched_verbose, rtx prev_head_insn, rtx tail)
24108 {
24109 rtx insn, next_insn;
24110 rtx nop;
24111 int issue_rate;
24112 int can_issue_more;
24113 int group_end;
24114 int group_count = 0;
24115
24116 /* Initialize issue_rate. */
24117 issue_rate = rs6000_issue_rate ();
24118 can_issue_more = issue_rate;
24119
24120 insn = get_next_active_insn (prev_head_insn, tail);
24121 next_insn = get_next_active_insn (insn, tail);
24122
24123 while (insn != NULL_RTX)
24124 {
24125 can_issue_more =
24126 rs6000_variable_issue (dump, sched_verbose, insn, can_issue_more);
24127
24128 group_end = (next_insn == NULL_RTX || GET_MODE (next_insn) == TImode);
24129
24130 if (next_insn == NULL_RTX)
24131 break;
24132
24133 if (group_end)
24134 {
24135 /* If the scheduler had marked group termination at this location
24136 (between insn and next_insn), and neither insn nor next_insn will
24137 force group termination, pad the group with nops to force group
24138 termination. */
24139 if (can_issue_more
24140 && (rs6000_sched_insert_nops == sched_finish_pad_groups)
24141 && !insn_terminates_group_p (insn, current_group)
24142 && !insn_terminates_group_p (next_insn, previous_group))
24143 {
24144 if (!is_branch_slot_insn (next_insn))
24145 can_issue_more--;
24146
24147 while (can_issue_more)
24148 {
24149 nop = gen_nop ();
24150 emit_insn_before (nop, next_insn);
24151 can_issue_more--;
24152 }
24153 }
24154
24155 can_issue_more = issue_rate;
24156 group_count++;
24157 }
24158
24159 insn = next_insn;
24160 next_insn = get_next_active_insn (insn, tail);
24161 }
24162
24163 return group_count;
24164 }
24165
24166 /* We're beginning a new block. Initialize data structures as necessary. */
24167
24168 static void
24169 rs6000_sched_init (FILE *dump ATTRIBUTE_UNUSED,
24170 int sched_verbose ATTRIBUTE_UNUSED,
24171 int max_ready ATTRIBUTE_UNUSED)
24172 {
24173 last_scheduled_insn = NULL_RTX;
24174 load_store_pendulum = 0;
24175 }
24176
24177 /* The following function is called at the end of scheduling BB.
24178 After reload, it inserts nops at insn group bundling. */
24179
24180 static void
24181 rs6000_sched_finish (FILE *dump, int sched_verbose)
24182 {
24183 int n_groups;
24184
24185 if (sched_verbose)
24186 fprintf (dump, "=== Finishing schedule.\n");
24187
24188 if (reload_completed && rs6000_sched_groups)
24189 {
24190 /* Do not run sched_finish hook when selective scheduling enabled. */
24191 if (sel_sched_p ())
24192 return;
24193
24194 if (rs6000_sched_insert_nops == sched_finish_none)
24195 return;
24196
24197 if (rs6000_sched_insert_nops == sched_finish_pad_groups)
24198 n_groups = pad_groups (dump, sched_verbose,
24199 current_sched_info->prev_head,
24200 current_sched_info->next_tail);
24201 else
24202 n_groups = redefine_groups (dump, sched_verbose,
24203 current_sched_info->prev_head,
24204 current_sched_info->next_tail);
24205
24206 if (sched_verbose >= 6)
24207 {
24208 fprintf (dump, "ngroups = %d\n", n_groups);
24209 print_rtl (dump, current_sched_info->prev_head);
24210 fprintf (dump, "Done finish_sched\n");
24211 }
24212 }
24213 }
24214
24215 struct _rs6000_sched_context
24216 {
24217 short cached_can_issue_more;
24218 rtx last_scheduled_insn;
24219 int load_store_pendulum;
24220 };
24221
24222 typedef struct _rs6000_sched_context rs6000_sched_context_def;
24223 typedef rs6000_sched_context_def *rs6000_sched_context_t;
24224
24225 /* Allocate store for new scheduling context. */
24226 static void *
24227 rs6000_alloc_sched_context (void)
24228 {
24229 return xmalloc (sizeof (rs6000_sched_context_def));
24230 }
24231
24232 /* If CLEAN_P is true then initializes _SC with clean data,
24233 and from the global context otherwise. */
24234 static void
24235 rs6000_init_sched_context (void *_sc, bool clean_p)
24236 {
24237 rs6000_sched_context_t sc = (rs6000_sched_context_t) _sc;
24238
24239 if (clean_p)
24240 {
24241 sc->cached_can_issue_more = 0;
24242 sc->last_scheduled_insn = NULL_RTX;
24243 sc->load_store_pendulum = 0;
24244 }
24245 else
24246 {
24247 sc->cached_can_issue_more = cached_can_issue_more;
24248 sc->last_scheduled_insn = last_scheduled_insn;
24249 sc->load_store_pendulum = load_store_pendulum;
24250 }
24251 }
24252
24253 /* Sets the global scheduling context to the one pointed to by _SC. */
24254 static void
24255 rs6000_set_sched_context (void *_sc)
24256 {
24257 rs6000_sched_context_t sc = (rs6000_sched_context_t) _sc;
24258
24259 gcc_assert (sc != NULL);
24260
24261 cached_can_issue_more = sc->cached_can_issue_more;
24262 last_scheduled_insn = sc->last_scheduled_insn;
24263 load_store_pendulum = sc->load_store_pendulum;
24264 }
24265
24266 /* Free _SC. */
24267 static void
24268 rs6000_free_sched_context (void *_sc)
24269 {
24270 gcc_assert (_sc != NULL);
24271
24272 free (_sc);
24273 }
24274
24275 \f
24276 /* Length in units of the trampoline for entering a nested function. */
24277
24278 int
24279 rs6000_trampoline_size (void)
24280 {
24281 int ret = 0;
24282
24283 switch (DEFAULT_ABI)
24284 {
24285 default:
24286 gcc_unreachable ();
24287
24288 case ABI_AIX:
24289 ret = (TARGET_32BIT) ? 12 : 24;
24290 break;
24291
24292 case ABI_DARWIN:
24293 case ABI_V4:
24294 ret = (TARGET_32BIT) ? 40 : 48;
24295 break;
24296 }
24297
24298 return ret;
24299 }
24300
24301 /* Emit RTL insns to initialize the variable parts of a trampoline.
24302 FNADDR is an RTX for the address of the function's pure code.
24303 CXT is an RTX for the static chain value for the function. */
24304
24305 static void
24306 rs6000_trampoline_init (rtx m_tramp, tree fndecl, rtx cxt)
24307 {
24308 int regsize = (TARGET_32BIT) ? 4 : 8;
24309 rtx fnaddr = XEXP (DECL_RTL (fndecl), 0);
24310 rtx ctx_reg = force_reg (Pmode, cxt);
24311 rtx addr = force_reg (Pmode, XEXP (m_tramp, 0));
24312
24313 switch (DEFAULT_ABI)
24314 {
24315 default:
24316 gcc_unreachable ();
24317
24318 /* Under AIX, just build the 3 word function descriptor */
24319 case ABI_AIX:
24320 {
24321 rtx fnmem = gen_const_mem (Pmode, force_reg (Pmode, fnaddr));
24322 rtx fn_reg = gen_reg_rtx (Pmode);
24323 rtx toc_reg = gen_reg_rtx (Pmode);
24324
24325 /* Macro to shorten the code expansions below. */
24326 # define MEM_PLUS(MEM, OFFSET) adjust_address (MEM, Pmode, OFFSET)
24327
24328 m_tramp = replace_equiv_address (m_tramp, addr);
24329
24330 emit_move_insn (fn_reg, MEM_PLUS (fnmem, 0));
24331 emit_move_insn (toc_reg, MEM_PLUS (fnmem, regsize));
24332 emit_move_insn (MEM_PLUS (m_tramp, 0), fn_reg);
24333 emit_move_insn (MEM_PLUS (m_tramp, regsize), toc_reg);
24334 emit_move_insn (MEM_PLUS (m_tramp, 2*regsize), ctx_reg);
24335
24336 # undef MEM_PLUS
24337 }
24338 break;
24339
24340 /* Under V.4/eabi/darwin, __trampoline_setup does the real work. */
24341 case ABI_DARWIN:
24342 case ABI_V4:
24343 emit_library_call (gen_rtx_SYMBOL_REF (Pmode, "__trampoline_setup"),
24344 LCT_NORMAL, VOIDmode, 4,
24345 addr, Pmode,
24346 GEN_INT (rs6000_trampoline_size ()), SImode,
24347 fnaddr, Pmode,
24348 ctx_reg, Pmode);
24349 break;
24350 }
24351 }
24352
24353 \f
24354 /* Returns TRUE iff the target attribute indicated by ATTR_ID takes a plain
24355 identifier as an argument, so the front end shouldn't look it up. */
24356
24357 static bool
24358 rs6000_attribute_takes_identifier_p (const_tree attr_id)
24359 {
24360 return is_attribute_p ("altivec", attr_id);
24361 }
24362
24363 /* Handle the "altivec" attribute. The attribute may have
24364 arguments as follows:
24365
24366 __attribute__((altivec(vector__)))
24367 __attribute__((altivec(pixel__))) (always followed by 'unsigned short')
24368 __attribute__((altivec(bool__))) (always followed by 'unsigned')
24369
24370 and may appear more than once (e.g., 'vector bool char') in a
24371 given declaration. */
24372
24373 static tree
24374 rs6000_handle_altivec_attribute (tree *node,
24375 tree name ATTRIBUTE_UNUSED,
24376 tree args,
24377 int flags ATTRIBUTE_UNUSED,
24378 bool *no_add_attrs)
24379 {
24380 tree type = *node, result = NULL_TREE;
24381 enum machine_mode mode;
24382 int unsigned_p;
24383 char altivec_type
24384 = ((args && TREE_CODE (args) == TREE_LIST && TREE_VALUE (args)
24385 && TREE_CODE (TREE_VALUE (args)) == IDENTIFIER_NODE)
24386 ? *IDENTIFIER_POINTER (TREE_VALUE (args))
24387 : '?');
24388
24389 while (POINTER_TYPE_P (type)
24390 || TREE_CODE (type) == FUNCTION_TYPE
24391 || TREE_CODE (type) == METHOD_TYPE
24392 || TREE_CODE (type) == ARRAY_TYPE)
24393 type = TREE_TYPE (type);
24394
24395 mode = TYPE_MODE (type);
24396
24397 /* Check for invalid AltiVec type qualifiers. */
24398 if (type == long_double_type_node)
24399 error ("use of %<long double%> in AltiVec types is invalid");
24400 else if (type == boolean_type_node)
24401 error ("use of boolean types in AltiVec types is invalid");
24402 else if (TREE_CODE (type) == COMPLEX_TYPE)
24403 error ("use of %<complex%> in AltiVec types is invalid");
24404 else if (DECIMAL_FLOAT_MODE_P (mode))
24405 error ("use of decimal floating point types in AltiVec types is invalid");
24406 else if (!TARGET_VSX)
24407 {
24408 if (type == long_unsigned_type_node || type == long_integer_type_node)
24409 {
24410 if (TARGET_64BIT)
24411 error ("use of %<long%> in AltiVec types is invalid for "
24412 "64-bit code without -mvsx");
24413 else if (rs6000_warn_altivec_long)
24414 warning (0, "use of %<long%> in AltiVec types is deprecated; "
24415 "use %<int%>");
24416 }
24417 else if (type == long_long_unsigned_type_node
24418 || type == long_long_integer_type_node)
24419 error ("use of %<long long%> in AltiVec types is invalid without "
24420 "-mvsx");
24421 else if (type == double_type_node)
24422 error ("use of %<double%> in AltiVec types is invalid without -mvsx");
24423 }
24424
24425 switch (altivec_type)
24426 {
24427 case 'v':
24428 unsigned_p = TYPE_UNSIGNED (type);
24429 switch (mode)
24430 {
24431 case DImode:
24432 result = (unsigned_p ? unsigned_V2DI_type_node : V2DI_type_node);
24433 break;
24434 case SImode:
24435 result = (unsigned_p ? unsigned_V4SI_type_node : V4SI_type_node);
24436 break;
24437 case HImode:
24438 result = (unsigned_p ? unsigned_V8HI_type_node : V8HI_type_node);
24439 break;
24440 case QImode:
24441 result = (unsigned_p ? unsigned_V16QI_type_node : V16QI_type_node);
24442 break;
24443 case SFmode: result = V4SF_type_node; break;
24444 case DFmode: result = V2DF_type_node; break;
24445 /* If the user says 'vector int bool', we may be handed the 'bool'
24446 attribute _before_ the 'vector' attribute, and so select the
24447 proper type in the 'b' case below. */
24448 case V4SImode: case V8HImode: case V16QImode: case V4SFmode:
24449 case V2DImode: case V2DFmode:
24450 result = type;
24451 default: break;
24452 }
24453 break;
24454 case 'b':
24455 switch (mode)
24456 {
24457 case DImode: case V2DImode: result = bool_V2DI_type_node; break;
24458 case SImode: case V4SImode: result = bool_V4SI_type_node; break;
24459 case HImode: case V8HImode: result = bool_V8HI_type_node; break;
24460 case QImode: case V16QImode: result = bool_V16QI_type_node;
24461 default: break;
24462 }
24463 break;
24464 case 'p':
24465 switch (mode)
24466 {
24467 case V8HImode: result = pixel_V8HI_type_node;
24468 default: break;
24469 }
24470 default: break;
24471 }
24472
24473 /* Propagate qualifiers attached to the element type
24474 onto the vector type. */
24475 if (result && result != type && TYPE_QUALS (type))
24476 result = build_qualified_type (result, TYPE_QUALS (type));
24477
24478 *no_add_attrs = true; /* No need to hang on to the attribute. */
24479
24480 if (result)
24481 *node = lang_hooks.types.reconstruct_complex_type (*node, result);
24482
24483 return NULL_TREE;
24484 }
24485
24486 /* AltiVec defines four built-in scalar types that serve as vector
24487 elements; we must teach the compiler how to mangle them. */
24488
24489 static const char *
24490 rs6000_mangle_type (const_tree type)
24491 {
24492 type = TYPE_MAIN_VARIANT (type);
24493
24494 if (TREE_CODE (type) != VOID_TYPE && TREE_CODE (type) != BOOLEAN_TYPE
24495 && TREE_CODE (type) != INTEGER_TYPE && TREE_CODE (type) != REAL_TYPE)
24496 return NULL;
24497
24498 if (type == bool_char_type_node) return "U6__boolc";
24499 if (type == bool_short_type_node) return "U6__bools";
24500 if (type == pixel_type_node) return "u7__pixel";
24501 if (type == bool_int_type_node) return "U6__booli";
24502 if (type == bool_long_type_node) return "U6__booll";
24503
24504 /* Mangle IBM extended float long double as `g' (__float128) on
24505 powerpc*-linux where long-double-64 previously was the default. */
24506 if (TYPE_MAIN_VARIANT (type) == long_double_type_node
24507 && TARGET_ELF
24508 && TARGET_LONG_DOUBLE_128
24509 && !TARGET_IEEEQUAD)
24510 return "g";
24511
24512 /* For all other types, use normal C++ mangling. */
24513 return NULL;
24514 }
24515
24516 /* Handle a "longcall" or "shortcall" attribute; arguments as in
24517 struct attribute_spec.handler. */
24518
24519 static tree
24520 rs6000_handle_longcall_attribute (tree *node, tree name,
24521 tree args ATTRIBUTE_UNUSED,
24522 int flags ATTRIBUTE_UNUSED,
24523 bool *no_add_attrs)
24524 {
24525 if (TREE_CODE (*node) != FUNCTION_TYPE
24526 && TREE_CODE (*node) != FIELD_DECL
24527 && TREE_CODE (*node) != TYPE_DECL)
24528 {
24529 warning (OPT_Wattributes, "%qE attribute only applies to functions",
24530 name);
24531 *no_add_attrs = true;
24532 }
24533
24534 return NULL_TREE;
24535 }
24536
24537 /* Set longcall attributes on all functions declared when
24538 rs6000_default_long_calls is true. */
24539 static void
24540 rs6000_set_default_type_attributes (tree type)
24541 {
24542 if (rs6000_default_long_calls
24543 && (TREE_CODE (type) == FUNCTION_TYPE
24544 || TREE_CODE (type) == METHOD_TYPE))
24545 TYPE_ATTRIBUTES (type) = tree_cons (get_identifier ("longcall"),
24546 NULL_TREE,
24547 TYPE_ATTRIBUTES (type));
24548
24549 #if TARGET_MACHO
24550 darwin_set_default_type_attributes (type);
24551 #endif
24552 }
24553
24554 /* Return a reference suitable for calling a function with the
24555 longcall attribute. */
24556
24557 rtx
24558 rs6000_longcall_ref (rtx call_ref)
24559 {
24560 const char *call_name;
24561 tree node;
24562
24563 if (GET_CODE (call_ref) != SYMBOL_REF)
24564 return call_ref;
24565
24566 /* System V adds '.' to the internal name, so skip them. */
24567 call_name = XSTR (call_ref, 0);
24568 if (*call_name == '.')
24569 {
24570 while (*call_name == '.')
24571 call_name++;
24572
24573 node = get_identifier (call_name);
24574 call_ref = gen_rtx_SYMBOL_REF (VOIDmode, IDENTIFIER_POINTER (node));
24575 }
24576
24577 return force_reg (Pmode, call_ref);
24578 }
24579 \f
24580 #ifndef TARGET_USE_MS_BITFIELD_LAYOUT
24581 #define TARGET_USE_MS_BITFIELD_LAYOUT 0
24582 #endif
24583
24584 /* Handle a "ms_struct" or "gcc_struct" attribute; arguments as in
24585 struct attribute_spec.handler. */
24586 static tree
24587 rs6000_handle_struct_attribute (tree *node, tree name,
24588 tree args ATTRIBUTE_UNUSED,
24589 int flags ATTRIBUTE_UNUSED, bool *no_add_attrs)
24590 {
24591 tree *type = NULL;
24592 if (DECL_P (*node))
24593 {
24594 if (TREE_CODE (*node) == TYPE_DECL)
24595 type = &TREE_TYPE (*node);
24596 }
24597 else
24598 type = node;
24599
24600 if (!(type && (TREE_CODE (*type) == RECORD_TYPE
24601 || TREE_CODE (*type) == UNION_TYPE)))
24602 {
24603 warning (OPT_Wattributes, "%qE attribute ignored", name);
24604 *no_add_attrs = true;
24605 }
24606
24607 else if ((is_attribute_p ("ms_struct", name)
24608 && lookup_attribute ("gcc_struct", TYPE_ATTRIBUTES (*type)))
24609 || ((is_attribute_p ("gcc_struct", name)
24610 && lookup_attribute ("ms_struct", TYPE_ATTRIBUTES (*type)))))
24611 {
24612 warning (OPT_Wattributes, "%qE incompatible attribute ignored",
24613 name);
24614 *no_add_attrs = true;
24615 }
24616
24617 return NULL_TREE;
24618 }
24619
24620 static bool
24621 rs6000_ms_bitfield_layout_p (const_tree record_type)
24622 {
24623 return (TARGET_USE_MS_BITFIELD_LAYOUT &&
24624 !lookup_attribute ("gcc_struct", TYPE_ATTRIBUTES (record_type)))
24625 || lookup_attribute ("ms_struct", TYPE_ATTRIBUTES (record_type));
24626 }
24627 \f
24628 #ifdef USING_ELFOS_H
24629
24630 /* A get_unnamed_section callback, used for switching to toc_section. */
24631
24632 static void
24633 rs6000_elf_output_toc_section_asm_op (const void *data ATTRIBUTE_UNUSED)
24634 {
24635 if (DEFAULT_ABI == ABI_AIX
24636 && TARGET_MINIMAL_TOC
24637 && !TARGET_RELOCATABLE)
24638 {
24639 if (!toc_initialized)
24640 {
24641 toc_initialized = 1;
24642 fprintf (asm_out_file, "%s\n", TOC_SECTION_ASM_OP);
24643 (*targetm.asm_out.internal_label) (asm_out_file, "LCTOC", 0);
24644 fprintf (asm_out_file, "\t.tc ");
24645 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (asm_out_file, "LCTOC1[TC],");
24646 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (asm_out_file, "LCTOC1");
24647 fprintf (asm_out_file, "\n");
24648
24649 fprintf (asm_out_file, "%s\n", MINIMAL_TOC_SECTION_ASM_OP);
24650 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (asm_out_file, "LCTOC1");
24651 fprintf (asm_out_file, " = .+32768\n");
24652 }
24653 else
24654 fprintf (asm_out_file, "%s\n", MINIMAL_TOC_SECTION_ASM_OP);
24655 }
24656 else if (DEFAULT_ABI == ABI_AIX && !TARGET_RELOCATABLE)
24657 fprintf (asm_out_file, "%s\n", TOC_SECTION_ASM_OP);
24658 else
24659 {
24660 fprintf (asm_out_file, "%s\n", MINIMAL_TOC_SECTION_ASM_OP);
24661 if (!toc_initialized)
24662 {
24663 ASM_OUTPUT_INTERNAL_LABEL_PREFIX (asm_out_file, "LCTOC1");
24664 fprintf (asm_out_file, " = .+32768\n");
24665 toc_initialized = 1;
24666 }
24667 }
24668 }
24669
24670 /* Implement TARGET_ASM_INIT_SECTIONS. */
24671
24672 static void
24673 rs6000_elf_asm_init_sections (void)
24674 {
24675 toc_section
24676 = get_unnamed_section (0, rs6000_elf_output_toc_section_asm_op, NULL);
24677
24678 sdata2_section
24679 = get_unnamed_section (SECTION_WRITE, output_section_asm_op,
24680 SDATA2_SECTION_ASM_OP);
24681 }
24682
24683 /* Implement TARGET_SELECT_RTX_SECTION. */
24684
24685 static section *
24686 rs6000_elf_select_rtx_section (enum machine_mode mode, rtx x,
24687 unsigned HOST_WIDE_INT align)
24688 {
24689 if (ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (x, mode))
24690 return toc_section;
24691 else
24692 return default_elf_select_rtx_section (mode, x, align);
24693 }
24694 \f
24695 /* For a SYMBOL_REF, set generic flags and then perform some
24696 target-specific processing.
24697
24698 When the AIX ABI is requested on a non-AIX system, replace the
24699 function name with the real name (with a leading .) rather than the
24700 function descriptor name. This saves a lot of overriding code to
24701 read the prefixes. */
24702
24703 static void
24704 rs6000_elf_encode_section_info (tree decl, rtx rtl, int first)
24705 {
24706 default_encode_section_info (decl, rtl, first);
24707
24708 if (first
24709 && TREE_CODE (decl) == FUNCTION_DECL
24710 && !TARGET_AIX
24711 && DEFAULT_ABI == ABI_AIX)
24712 {
24713 rtx sym_ref = XEXP (rtl, 0);
24714 size_t len = strlen (XSTR (sym_ref, 0));
24715 char *str = XALLOCAVEC (char, len + 2);
24716 str[0] = '.';
24717 memcpy (str + 1, XSTR (sym_ref, 0), len + 1);
24718 XSTR (sym_ref, 0) = ggc_alloc_string (str, len + 1);
24719 }
24720 }
24721
24722 static inline bool
24723 compare_section_name (const char *section, const char *templ)
24724 {
24725 int len;
24726
24727 len = strlen (templ);
24728 return (strncmp (section, templ, len) == 0
24729 && (section[len] == 0 || section[len] == '.'));
24730 }
24731
24732 bool
24733 rs6000_elf_in_small_data_p (const_tree decl)
24734 {
24735 if (rs6000_sdata == SDATA_NONE)
24736 return false;
24737
24738 /* We want to merge strings, so we never consider them small data. */
24739 if (TREE_CODE (decl) == STRING_CST)
24740 return false;
24741
24742 /* Functions are never in the small data area. */
24743 if (TREE_CODE (decl) == FUNCTION_DECL)
24744 return false;
24745
24746 if (TREE_CODE (decl) == VAR_DECL && DECL_SECTION_NAME (decl))
24747 {
24748 const char *section = TREE_STRING_POINTER (DECL_SECTION_NAME (decl));
24749 if (compare_section_name (section, ".sdata")
24750 || compare_section_name (section, ".sdata2")
24751 || compare_section_name (section, ".gnu.linkonce.s")
24752 || compare_section_name (section, ".sbss")
24753 || compare_section_name (section, ".sbss2")
24754 || compare_section_name (section, ".gnu.linkonce.sb")
24755 || strcmp (section, ".PPC.EMB.sdata0") == 0
24756 || strcmp (section, ".PPC.EMB.sbss0") == 0)
24757 return true;
24758 }
24759 else
24760 {
24761 HOST_WIDE_INT size = int_size_in_bytes (TREE_TYPE (decl));
24762
24763 if (size > 0
24764 && (unsigned HOST_WIDE_INT) size <= g_switch_value
24765 /* If it's not public, and we're not going to reference it there,
24766 there's no need to put it in the small data section. */
24767 && (rs6000_sdata != SDATA_DATA || TREE_PUBLIC (decl)))
24768 return true;
24769 }
24770
24771 return false;
24772 }
24773
24774 #endif /* USING_ELFOS_H */
24775 \f
24776 /* Implement TARGET_USE_BLOCKS_FOR_CONSTANT_P. */
24777
24778 static bool
24779 rs6000_use_blocks_for_constant_p (enum machine_mode mode, const_rtx x)
24780 {
24781 return !ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (x, mode);
24782 }
24783 \f
24784 /* Return a REG that occurs in ADDR with coefficient 1.
24785 ADDR can be effectively incremented by incrementing REG.
24786
24787 r0 is special and we must not select it as an address
24788 register by this routine since our caller will try to
24789 increment the returned register via an "la" instruction. */
24790
24791 rtx
24792 find_addr_reg (rtx addr)
24793 {
24794 while (GET_CODE (addr) == PLUS)
24795 {
24796 if (GET_CODE (XEXP (addr, 0)) == REG
24797 && REGNO (XEXP (addr, 0)) != 0)
24798 addr = XEXP (addr, 0);
24799 else if (GET_CODE (XEXP (addr, 1)) == REG
24800 && REGNO (XEXP (addr, 1)) != 0)
24801 addr = XEXP (addr, 1);
24802 else if (CONSTANT_P (XEXP (addr, 0)))
24803 addr = XEXP (addr, 1);
24804 else if (CONSTANT_P (XEXP (addr, 1)))
24805 addr = XEXP (addr, 0);
24806 else
24807 gcc_unreachable ();
24808 }
24809 gcc_assert (GET_CODE (addr) == REG && REGNO (addr) != 0);
24810 return addr;
24811 }
24812
24813 void
24814 rs6000_fatal_bad_address (rtx op)
24815 {
24816 fatal_insn ("bad address", op);
24817 }
24818
24819 #if TARGET_MACHO
24820
24821 typedef struct branch_island_d {
24822 tree function_name;
24823 tree label_name;
24824 int line_number;
24825 } branch_island;
24826
24827 DEF_VEC_O(branch_island);
24828 DEF_VEC_ALLOC_O(branch_island,gc);
24829
24830 static VEC(branch_island,gc) *branch_islands;
24831
24832 /* Remember to generate a branch island for far calls to the given
24833 function. */
24834
24835 static void
24836 add_compiler_branch_island (tree label_name, tree function_name,
24837 int line_number)
24838 {
24839 branch_island *bi = VEC_safe_push (branch_island, gc, branch_islands, NULL);
24840
24841 bi->function_name = function_name;
24842 bi->label_name = label_name;
24843 bi->line_number = line_number;
24844 }
24845
24846 /* Generate far-jump branch islands for everything recorded in
24847 branch_islands. Invoked immediately after the last instruction of
24848 the epilogue has been emitted; the branch islands must be appended
24849 to, and contiguous with, the function body. Mach-O stubs are
24850 generated in machopic_output_stub(). */
24851
24852 static void
24853 macho_branch_islands (void)
24854 {
24855 char tmp_buf[512];
24856
24857 while (!VEC_empty (branch_island, branch_islands))
24858 {
24859 branch_island *bi = VEC_last (branch_island, branch_islands);
24860 const char *label = IDENTIFIER_POINTER (bi->label_name);
24861 const char *name = IDENTIFIER_POINTER (bi->function_name);
24862 char name_buf[512];
24863 /* Cheap copy of the details from the Darwin ASM_OUTPUT_LABELREF(). */
24864 if (name[0] == '*' || name[0] == '&')
24865 strcpy (name_buf, name+1);
24866 else
24867 {
24868 name_buf[0] = '_';
24869 strcpy (name_buf+1, name);
24870 }
24871 strcpy (tmp_buf, "\n");
24872 strcat (tmp_buf, label);
24873 #if defined (DBX_DEBUGGING_INFO) || defined (XCOFF_DEBUGGING_INFO)
24874 if (write_symbols == DBX_DEBUG || write_symbols == XCOFF_DEBUG)
24875 dbxout_stabd (N_SLINE, bi->line_number);
24876 #endif /* DBX_DEBUGGING_INFO || XCOFF_DEBUGGING_INFO */
24877 if (flag_pic)
24878 {
24879 strcat (tmp_buf, ":\n\tmflr r0\n\tbcl 20,31,");
24880 strcat (tmp_buf, label);
24881 strcat (tmp_buf, "_pic\n");
24882 strcat (tmp_buf, label);
24883 strcat (tmp_buf, "_pic:\n\tmflr r11\n");
24884
24885 strcat (tmp_buf, "\taddis r11,r11,ha16(");
24886 strcat (tmp_buf, name_buf);
24887 strcat (tmp_buf, " - ");
24888 strcat (tmp_buf, label);
24889 strcat (tmp_buf, "_pic)\n");
24890
24891 strcat (tmp_buf, "\tmtlr r0\n");
24892
24893 strcat (tmp_buf, "\taddi r12,r11,lo16(");
24894 strcat (tmp_buf, name_buf);
24895 strcat (tmp_buf, " - ");
24896 strcat (tmp_buf, label);
24897 strcat (tmp_buf, "_pic)\n");
24898
24899 strcat (tmp_buf, "\tmtctr r12\n\tbctr\n");
24900 }
24901 else
24902 {
24903 strcat (tmp_buf, ":\nlis r12,hi16(");
24904 strcat (tmp_buf, name_buf);
24905 strcat (tmp_buf, ")\n\tori r12,r12,lo16(");
24906 strcat (tmp_buf, name_buf);
24907 strcat (tmp_buf, ")\n\tmtctr r12\n\tbctr");
24908 }
24909 output_asm_insn (tmp_buf, 0);
24910 #if defined (DBX_DEBUGGING_INFO) || defined (XCOFF_DEBUGGING_INFO)
24911 if (write_symbols == DBX_DEBUG || write_symbols == XCOFF_DEBUG)
24912 dbxout_stabd (N_SLINE, bi->line_number);
24913 #endif /* DBX_DEBUGGING_INFO || XCOFF_DEBUGGING_INFO */
24914 VEC_pop (branch_island, branch_islands);
24915 }
24916 }
24917
24918 /* NO_PREVIOUS_DEF checks in the link list whether the function name is
24919 already there or not. */
24920
24921 static int
24922 no_previous_def (tree function_name)
24923 {
24924 branch_island *bi;
24925 unsigned ix;
24926
24927 FOR_EACH_VEC_ELT (branch_island, branch_islands, ix, bi)
24928 if (function_name == bi->function_name)
24929 return 0;
24930 return 1;
24931 }
24932
24933 /* GET_PREV_LABEL gets the label name from the previous definition of
24934 the function. */
24935
24936 static tree
24937 get_prev_label (tree function_name)
24938 {
24939 branch_island *bi;
24940 unsigned ix;
24941
24942 FOR_EACH_VEC_ELT (branch_island, branch_islands, ix, bi)
24943 if (function_name == bi->function_name)
24944 return bi->label_name;
24945 return NULL_TREE;
24946 }
24947
24948 /* INSN is either a function call or a millicode call. It may have an
24949 unconditional jump in its delay slot.
24950
24951 CALL_DEST is the routine we are calling. */
24952
24953 char *
24954 output_call (rtx insn, rtx *operands, int dest_operand_number,
24955 int cookie_operand_number)
24956 {
24957 static char buf[256];
24958 if (darwin_emit_branch_islands
24959 && GET_CODE (operands[dest_operand_number]) == SYMBOL_REF
24960 && (INTVAL (operands[cookie_operand_number]) & CALL_LONG))
24961 {
24962 tree labelname;
24963 tree funname = get_identifier (XSTR (operands[dest_operand_number], 0));
24964
24965 if (no_previous_def (funname))
24966 {
24967 rtx label_rtx = gen_label_rtx ();
24968 char *label_buf, temp_buf[256];
24969 ASM_GENERATE_INTERNAL_LABEL (temp_buf, "L",
24970 CODE_LABEL_NUMBER (label_rtx));
24971 label_buf = temp_buf[0] == '*' ? temp_buf + 1 : temp_buf;
24972 labelname = get_identifier (label_buf);
24973 add_compiler_branch_island (labelname, funname, insn_line (insn));
24974 }
24975 else
24976 labelname = get_prev_label (funname);
24977
24978 /* "jbsr foo, L42" is Mach-O for "Link as 'bl foo' if a 'bl'
24979 instruction will reach 'foo', otherwise link as 'bl L42'".
24980 "L42" should be a 'branch island', that will do a far jump to
24981 'foo'. Branch islands are generated in
24982 macho_branch_islands(). */
24983 sprintf (buf, "jbsr %%z%d,%.246s",
24984 dest_operand_number, IDENTIFIER_POINTER (labelname));
24985 }
24986 else
24987 sprintf (buf, "bl %%z%d", dest_operand_number);
24988 return buf;
24989 }
24990
24991 /* Generate PIC and indirect symbol stubs. */
24992
24993 void
24994 machopic_output_stub (FILE *file, const char *symb, const char *stub)
24995 {
24996 unsigned int length;
24997 char *symbol_name, *lazy_ptr_name;
24998 char *local_label_0;
24999 static int label = 0;
25000
25001 /* Lose our funky encoding stuff so it doesn't contaminate the stub. */
25002 symb = (*targetm.strip_name_encoding) (symb);
25003
25004
25005 length = strlen (symb);
25006 symbol_name = XALLOCAVEC (char, length + 32);
25007 GEN_SYMBOL_NAME_FOR_SYMBOL (symbol_name, symb, length);
25008
25009 lazy_ptr_name = XALLOCAVEC (char, length + 32);
25010 GEN_LAZY_PTR_NAME_FOR_SYMBOL (lazy_ptr_name, symb, length);
25011
25012 if (flag_pic == 2)
25013 switch_to_section (darwin_sections[machopic_picsymbol_stub1_section]);
25014 else
25015 switch_to_section (darwin_sections[machopic_symbol_stub1_section]);
25016
25017 if (flag_pic == 2)
25018 {
25019 fprintf (file, "\t.align 5\n");
25020
25021 fprintf (file, "%s:\n", stub);
25022 fprintf (file, "\t.indirect_symbol %s\n", symbol_name);
25023
25024 label++;
25025 local_label_0 = XALLOCAVEC (char, sizeof ("\"L00000000000$spb\""));
25026 sprintf (local_label_0, "\"L%011d$spb\"", label);
25027
25028 fprintf (file, "\tmflr r0\n");
25029 fprintf (file, "\tbcl 20,31,%s\n", local_label_0);
25030 fprintf (file, "%s:\n\tmflr r11\n", local_label_0);
25031 fprintf (file, "\taddis r11,r11,ha16(%s-%s)\n",
25032 lazy_ptr_name, local_label_0);
25033 fprintf (file, "\tmtlr r0\n");
25034 fprintf (file, "\t%s r12,lo16(%s-%s)(r11)\n",
25035 (TARGET_64BIT ? "ldu" : "lwzu"),
25036 lazy_ptr_name, local_label_0);
25037 fprintf (file, "\tmtctr r12\n");
25038 fprintf (file, "\tbctr\n");
25039 }
25040 else
25041 {
25042 fprintf (file, "\t.align 4\n");
25043
25044 fprintf (file, "%s:\n", stub);
25045 fprintf (file, "\t.indirect_symbol %s\n", symbol_name);
25046
25047 fprintf (file, "\tlis r11,ha16(%s)\n", lazy_ptr_name);
25048 fprintf (file, "\t%s r12,lo16(%s)(r11)\n",
25049 (TARGET_64BIT ? "ldu" : "lwzu"),
25050 lazy_ptr_name);
25051 fprintf (file, "\tmtctr r12\n");
25052 fprintf (file, "\tbctr\n");
25053 }
25054
25055 switch_to_section (darwin_sections[machopic_lazy_symbol_ptr_section]);
25056 fprintf (file, "%s:\n", lazy_ptr_name);
25057 fprintf (file, "\t.indirect_symbol %s\n", symbol_name);
25058 fprintf (file, "%sdyld_stub_binding_helper\n",
25059 (TARGET_64BIT ? DOUBLE_INT_ASM_OP : "\t.long\t"));
25060 }
25061
25062 /* Legitimize PIC addresses. If the address is already
25063 position-independent, we return ORIG. Newly generated
25064 position-independent addresses go into a reg. This is REG if non
25065 zero, otherwise we allocate register(s) as necessary. */
25066
25067 #define SMALL_INT(X) ((UINTVAL (X) + 0x8000) < 0x10000)
25068
25069 rtx
25070 rs6000_machopic_legitimize_pic_address (rtx orig, enum machine_mode mode,
25071 rtx reg)
25072 {
25073 rtx base, offset;
25074
25075 if (reg == NULL && ! reload_in_progress && ! reload_completed)
25076 reg = gen_reg_rtx (Pmode);
25077
25078 if (GET_CODE (orig) == CONST)
25079 {
25080 rtx reg_temp;
25081
25082 if (GET_CODE (XEXP (orig, 0)) == PLUS
25083 && XEXP (XEXP (orig, 0), 0) == pic_offset_table_rtx)
25084 return orig;
25085
25086 gcc_assert (GET_CODE (XEXP (orig, 0)) == PLUS);
25087
25088 /* Use a different reg for the intermediate value, as
25089 it will be marked UNCHANGING. */
25090 reg_temp = !can_create_pseudo_p () ? reg : gen_reg_rtx (Pmode);
25091 base = rs6000_machopic_legitimize_pic_address (XEXP (XEXP (orig, 0), 0),
25092 Pmode, reg_temp);
25093 offset =
25094 rs6000_machopic_legitimize_pic_address (XEXP (XEXP (orig, 0), 1),
25095 Pmode, reg);
25096
25097 if (GET_CODE (offset) == CONST_INT)
25098 {
25099 if (SMALL_INT (offset))
25100 return plus_constant (base, INTVAL (offset));
25101 else if (! reload_in_progress && ! reload_completed)
25102 offset = force_reg (Pmode, offset);
25103 else
25104 {
25105 rtx mem = force_const_mem (Pmode, orig);
25106 return machopic_legitimize_pic_address (mem, Pmode, reg);
25107 }
25108 }
25109 return gen_rtx_PLUS (Pmode, base, offset);
25110 }
25111
25112 /* Fall back on generic machopic code. */
25113 return machopic_legitimize_pic_address (orig, mode, reg);
25114 }
25115
25116 /* Output a .machine directive for the Darwin assembler, and call
25117 the generic start_file routine. */
25118
25119 static void
25120 rs6000_darwin_file_start (void)
25121 {
25122 static const struct
25123 {
25124 const char *arg;
25125 const char *name;
25126 int if_set;
25127 } mapping[] = {
25128 { "ppc64", "ppc64", MASK_64BIT },
25129 { "970", "ppc970", MASK_PPC_GPOPT | MASK_MFCRF | MASK_POWERPC64 },
25130 { "power4", "ppc970", 0 },
25131 { "G5", "ppc970", 0 },
25132 { "7450", "ppc7450", 0 },
25133 { "7400", "ppc7400", MASK_ALTIVEC },
25134 { "G4", "ppc7400", 0 },
25135 { "750", "ppc750", 0 },
25136 { "740", "ppc750", 0 },
25137 { "G3", "ppc750", 0 },
25138 { "604e", "ppc604e", 0 },
25139 { "604", "ppc604", 0 },
25140 { "603e", "ppc603", 0 },
25141 { "603", "ppc603", 0 },
25142 { "601", "ppc601", 0 },
25143 { NULL, "ppc", 0 } };
25144 const char *cpu_id = "";
25145 size_t i;
25146
25147 rs6000_file_start ();
25148 darwin_file_start ();
25149
25150 /* Determine the argument to -mcpu=. Default to G3 if not specified. */
25151 for (i = 0; i < ARRAY_SIZE (rs6000_select); i++)
25152 if (rs6000_select[i].set_arch_p && rs6000_select[i].string
25153 && rs6000_select[i].string[0] != '\0')
25154 cpu_id = rs6000_select[i].string;
25155
25156 /* Look through the mapping array. Pick the first name that either
25157 matches the argument, has a bit set in IF_SET that is also set
25158 in the target flags, or has a NULL name. */
25159
25160 i = 0;
25161 while (mapping[i].arg != NULL
25162 && strcmp (mapping[i].arg, cpu_id) != 0
25163 && (mapping[i].if_set & target_flags) == 0)
25164 i++;
25165
25166 fprintf (asm_out_file, "\t.machine %s\n", mapping[i].name);
25167 }
25168
25169 #endif /* TARGET_MACHO */
25170
25171 #if TARGET_ELF
25172 static int
25173 rs6000_elf_reloc_rw_mask (void)
25174 {
25175 if (flag_pic)
25176 return 3;
25177 else if (DEFAULT_ABI == ABI_AIX)
25178 return 2;
25179 else
25180 return 0;
25181 }
25182
25183 /* Record an element in the table of global constructors. SYMBOL is
25184 a SYMBOL_REF of the function to be called; PRIORITY is a number
25185 between 0 and MAX_INIT_PRIORITY.
25186
25187 This differs from default_named_section_asm_out_constructor in
25188 that we have special handling for -mrelocatable. */
25189
25190 static void
25191 rs6000_elf_asm_out_constructor (rtx symbol, int priority)
25192 {
25193 const char *section = ".ctors";
25194 char buf[16];
25195
25196 if (priority != DEFAULT_INIT_PRIORITY)
25197 {
25198 sprintf (buf, ".ctors.%.5u",
25199 /* Invert the numbering so the linker puts us in the proper
25200 order; constructors are run from right to left, and the
25201 linker sorts in increasing order. */
25202 MAX_INIT_PRIORITY - priority);
25203 section = buf;
25204 }
25205
25206 switch_to_section (get_section (section, SECTION_WRITE, NULL));
25207 assemble_align (POINTER_SIZE);
25208
25209 if (TARGET_RELOCATABLE)
25210 {
25211 fputs ("\t.long (", asm_out_file);
25212 output_addr_const (asm_out_file, symbol);
25213 fputs (")@fixup\n", asm_out_file);
25214 }
25215 else
25216 assemble_integer (symbol, POINTER_SIZE / BITS_PER_UNIT, POINTER_SIZE, 1);
25217 }
25218
25219 static void
25220 rs6000_elf_asm_out_destructor (rtx symbol, int priority)
25221 {
25222 const char *section = ".dtors";
25223 char buf[16];
25224
25225 if (priority != DEFAULT_INIT_PRIORITY)
25226 {
25227 sprintf (buf, ".dtors.%.5u",
25228 /* Invert the numbering so the linker puts us in the proper
25229 order; constructors are run from right to left, and the
25230 linker sorts in increasing order. */
25231 MAX_INIT_PRIORITY - priority);
25232 section = buf;
25233 }
25234
25235 switch_to_section (get_section (section, SECTION_WRITE, NULL));
25236 assemble_align (POINTER_SIZE);
25237
25238 if (TARGET_RELOCATABLE)
25239 {
25240 fputs ("\t.long (", asm_out_file);
25241 output_addr_const (asm_out_file, symbol);
25242 fputs (")@fixup\n", asm_out_file);
25243 }
25244 else
25245 assemble_integer (symbol, POINTER_SIZE / BITS_PER_UNIT, POINTER_SIZE, 1);
25246 }
25247
25248 void
25249 rs6000_elf_declare_function_name (FILE *file, const char *name, tree decl)
25250 {
25251 if (TARGET_64BIT)
25252 {
25253 fputs ("\t.section\t\".opd\",\"aw\"\n\t.align 3\n", file);
25254 ASM_OUTPUT_LABEL (file, name);
25255 fputs (DOUBLE_INT_ASM_OP, file);
25256 rs6000_output_function_entry (file, name);
25257 fputs (",.TOC.@tocbase,0\n\t.previous\n", file);
25258 if (DOT_SYMBOLS)
25259 {
25260 fputs ("\t.size\t", file);
25261 assemble_name (file, name);
25262 fputs (",24\n\t.type\t.", file);
25263 assemble_name (file, name);
25264 fputs (",@function\n", file);
25265 if (TREE_PUBLIC (decl) && ! DECL_WEAK (decl))
25266 {
25267 fputs ("\t.globl\t.", file);
25268 assemble_name (file, name);
25269 putc ('\n', file);
25270 }
25271 }
25272 else
25273 ASM_OUTPUT_TYPE_DIRECTIVE (file, name, "function");
25274 ASM_DECLARE_RESULT (file, DECL_RESULT (decl));
25275 rs6000_output_function_entry (file, name);
25276 fputs (":\n", file);
25277 return;
25278 }
25279
25280 if (TARGET_RELOCATABLE
25281 && !TARGET_SECURE_PLT
25282 && (get_pool_size () != 0 || crtl->profile)
25283 && uses_TOC ())
25284 {
25285 char buf[256];
25286
25287 (*targetm.asm_out.internal_label) (file, "LCL", rs6000_pic_labelno);
25288
25289 ASM_GENERATE_INTERNAL_LABEL (buf, "LCTOC", 1);
25290 fprintf (file, "\t.long ");
25291 assemble_name (file, buf);
25292 putc ('-', file);
25293 ASM_GENERATE_INTERNAL_LABEL (buf, "LCF", rs6000_pic_labelno);
25294 assemble_name (file, buf);
25295 putc ('\n', file);
25296 }
25297
25298 ASM_OUTPUT_TYPE_DIRECTIVE (file, name, "function");
25299 ASM_DECLARE_RESULT (file, DECL_RESULT (decl));
25300
25301 if (DEFAULT_ABI == ABI_AIX)
25302 {
25303 const char *desc_name, *orig_name;
25304
25305 orig_name = (*targetm.strip_name_encoding) (name);
25306 desc_name = orig_name;
25307 while (*desc_name == '.')
25308 desc_name++;
25309
25310 if (TREE_PUBLIC (decl))
25311 fprintf (file, "\t.globl %s\n", desc_name);
25312
25313 fprintf (file, "%s\n", MINIMAL_TOC_SECTION_ASM_OP);
25314 fprintf (file, "%s:\n", desc_name);
25315 fprintf (file, "\t.long %s\n", orig_name);
25316 fputs ("\t.long _GLOBAL_OFFSET_TABLE_\n", file);
25317 if (DEFAULT_ABI == ABI_AIX)
25318 fputs ("\t.long 0\n", file);
25319 fprintf (file, "\t.previous\n");
25320 }
25321 ASM_OUTPUT_LABEL (file, name);
25322 }
25323
25324 static void
25325 rs6000_elf_end_indicate_exec_stack (void)
25326 {
25327 if (TARGET_32BIT)
25328 file_end_indicate_exec_stack ();
25329 }
25330 #endif
25331
25332 #if TARGET_XCOFF
25333 static void
25334 rs6000_xcoff_asm_output_anchor (rtx symbol)
25335 {
25336 char buffer[100];
25337
25338 sprintf (buffer, "$ + " HOST_WIDE_INT_PRINT_DEC,
25339 SYMBOL_REF_BLOCK_OFFSET (symbol));
25340 ASM_OUTPUT_DEF (asm_out_file, XSTR (symbol, 0), buffer);
25341 }
25342
25343 static void
25344 rs6000_xcoff_asm_globalize_label (FILE *stream, const char *name)
25345 {
25346 fputs (GLOBAL_ASM_OP, stream);
25347 RS6000_OUTPUT_BASENAME (stream, name);
25348 putc ('\n', stream);
25349 }
25350
25351 /* A get_unnamed_decl callback, used for read-only sections. PTR
25352 points to the section string variable. */
25353
25354 static void
25355 rs6000_xcoff_output_readonly_section_asm_op (const void *directive)
25356 {
25357 fprintf (asm_out_file, "\t.csect %s[RO],%s\n",
25358 *(const char *const *) directive,
25359 XCOFF_CSECT_DEFAULT_ALIGNMENT_STR);
25360 }
25361
25362 /* Likewise for read-write sections. */
25363
25364 static void
25365 rs6000_xcoff_output_readwrite_section_asm_op (const void *directive)
25366 {
25367 fprintf (asm_out_file, "\t.csect %s[RW],%s\n",
25368 *(const char *const *) directive,
25369 XCOFF_CSECT_DEFAULT_ALIGNMENT_STR);
25370 }
25371
25372 /* A get_unnamed_section callback, used for switching to toc_section. */
25373
25374 static void
25375 rs6000_xcoff_output_toc_section_asm_op (const void *data ATTRIBUTE_UNUSED)
25376 {
25377 if (TARGET_MINIMAL_TOC)
25378 {
25379 /* toc_section is always selected at least once from
25380 rs6000_xcoff_file_start, so this is guaranteed to
25381 always be defined once and only once in each file. */
25382 if (!toc_initialized)
25383 {
25384 fputs ("\t.toc\nLCTOC..1:\n", asm_out_file);
25385 fputs ("\t.tc toc_table[TC],toc_table[RW]\n", asm_out_file);
25386 toc_initialized = 1;
25387 }
25388 fprintf (asm_out_file, "\t.csect toc_table[RW]%s\n",
25389 (TARGET_32BIT ? "" : ",3"));
25390 }
25391 else
25392 fputs ("\t.toc\n", asm_out_file);
25393 }
25394
25395 /* Implement TARGET_ASM_INIT_SECTIONS. */
25396
25397 static void
25398 rs6000_xcoff_asm_init_sections (void)
25399 {
25400 read_only_data_section
25401 = get_unnamed_section (0, rs6000_xcoff_output_readonly_section_asm_op,
25402 &xcoff_read_only_section_name);
25403
25404 private_data_section
25405 = get_unnamed_section (SECTION_WRITE,
25406 rs6000_xcoff_output_readwrite_section_asm_op,
25407 &xcoff_private_data_section_name);
25408
25409 read_only_private_data_section
25410 = get_unnamed_section (0, rs6000_xcoff_output_readonly_section_asm_op,
25411 &xcoff_private_data_section_name);
25412
25413 toc_section
25414 = get_unnamed_section (0, rs6000_xcoff_output_toc_section_asm_op, NULL);
25415
25416 readonly_data_section = read_only_data_section;
25417 exception_section = data_section;
25418 }
25419
25420 static int
25421 rs6000_xcoff_reloc_rw_mask (void)
25422 {
25423 return 3;
25424 }
25425
25426 static void
25427 rs6000_xcoff_asm_named_section (const char *name, unsigned int flags,
25428 tree decl ATTRIBUTE_UNUSED)
25429 {
25430 int smclass;
25431 static const char * const suffix[3] = { "PR", "RO", "RW" };
25432
25433 if (flags & SECTION_CODE)
25434 smclass = 0;
25435 else if (flags & SECTION_WRITE)
25436 smclass = 2;
25437 else
25438 smclass = 1;
25439
25440 fprintf (asm_out_file, "\t.csect %s%s[%s],%u\n",
25441 (flags & SECTION_CODE) ? "." : "",
25442 name, suffix[smclass], flags & SECTION_ENTSIZE);
25443 }
25444
25445 static section *
25446 rs6000_xcoff_select_section (tree decl, int reloc,
25447 unsigned HOST_WIDE_INT align ATTRIBUTE_UNUSED)
25448 {
25449 if (decl_readonly_section (decl, reloc))
25450 {
25451 if (TREE_PUBLIC (decl))
25452 return read_only_data_section;
25453 else
25454 return read_only_private_data_section;
25455 }
25456 else
25457 {
25458 if (TREE_PUBLIC (decl))
25459 return data_section;
25460 else
25461 return private_data_section;
25462 }
25463 }
25464
25465 static void
25466 rs6000_xcoff_unique_section (tree decl, int reloc ATTRIBUTE_UNUSED)
25467 {
25468 const char *name;
25469
25470 /* Use select_section for private and uninitialized data. */
25471 if (!TREE_PUBLIC (decl)
25472 || DECL_COMMON (decl)
25473 || DECL_INITIAL (decl) == NULL_TREE
25474 || DECL_INITIAL (decl) == error_mark_node
25475 || (flag_zero_initialized_in_bss
25476 && initializer_zerop (DECL_INITIAL (decl))))
25477 return;
25478
25479 name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl));
25480 name = (*targetm.strip_name_encoding) (name);
25481 DECL_SECTION_NAME (decl) = build_string (strlen (name), name);
25482 }
25483
25484 /* Select section for constant in constant pool.
25485
25486 On RS/6000, all constants are in the private read-only data area.
25487 However, if this is being placed in the TOC it must be output as a
25488 toc entry. */
25489
25490 static section *
25491 rs6000_xcoff_select_rtx_section (enum machine_mode mode, rtx x,
25492 unsigned HOST_WIDE_INT align ATTRIBUTE_UNUSED)
25493 {
25494 if (ASM_OUTPUT_SPECIAL_POOL_ENTRY_P (x, mode))
25495 return toc_section;
25496 else
25497 return read_only_private_data_section;
25498 }
25499
25500 /* Remove any trailing [DS] or the like from the symbol name. */
25501
25502 static const char *
25503 rs6000_xcoff_strip_name_encoding (const char *name)
25504 {
25505 size_t len;
25506 if (*name == '*')
25507 name++;
25508 len = strlen (name);
25509 if (name[len - 1] == ']')
25510 return ggc_alloc_string (name, len - 4);
25511 else
25512 return name;
25513 }
25514
25515 /* Section attributes. AIX is always PIC. */
25516
25517 static unsigned int
25518 rs6000_xcoff_section_type_flags (tree decl, const char *name, int reloc)
25519 {
25520 unsigned int align;
25521 unsigned int flags = default_section_type_flags (decl, name, reloc);
25522
25523 /* Align to at least UNIT size. */
25524 if (flags & SECTION_CODE)
25525 align = MIN_UNITS_PER_WORD;
25526 else
25527 /* Increase alignment of large objects if not already stricter. */
25528 align = MAX ((DECL_ALIGN (decl) / BITS_PER_UNIT),
25529 int_size_in_bytes (TREE_TYPE (decl)) > MIN_UNITS_PER_WORD
25530 ? UNITS_PER_FP_WORD : MIN_UNITS_PER_WORD);
25531
25532 return flags | (exact_log2 (align) & SECTION_ENTSIZE);
25533 }
25534
25535 /* Output at beginning of assembler file.
25536
25537 Initialize the section names for the RS/6000 at this point.
25538
25539 Specify filename, including full path, to assembler.
25540
25541 We want to go into the TOC section so at least one .toc will be emitted.
25542 Also, in order to output proper .bs/.es pairs, we need at least one static
25543 [RW] section emitted.
25544
25545 Finally, declare mcount when profiling to make the assembler happy. */
25546
25547 static void
25548 rs6000_xcoff_file_start (void)
25549 {
25550 rs6000_gen_section_name (&xcoff_bss_section_name,
25551 main_input_filename, ".bss_");
25552 rs6000_gen_section_name (&xcoff_private_data_section_name,
25553 main_input_filename, ".rw_");
25554 rs6000_gen_section_name (&xcoff_read_only_section_name,
25555 main_input_filename, ".ro_");
25556
25557 fputs ("\t.file\t", asm_out_file);
25558 output_quoted_string (asm_out_file, main_input_filename);
25559 fputc ('\n', asm_out_file);
25560 if (write_symbols != NO_DEBUG)
25561 switch_to_section (private_data_section);
25562 switch_to_section (text_section);
25563 if (profile_flag)
25564 fprintf (asm_out_file, "\t.extern %s\n", RS6000_MCOUNT);
25565 rs6000_file_start ();
25566 }
25567
25568 /* Output at end of assembler file.
25569 On the RS/6000, referencing data should automatically pull in text. */
25570
25571 static void
25572 rs6000_xcoff_file_end (void)
25573 {
25574 switch_to_section (text_section);
25575 fputs ("_section_.text:\n", asm_out_file);
25576 switch_to_section (data_section);
25577 fputs (TARGET_32BIT
25578 ? "\t.long _section_.text\n" : "\t.llong _section_.text\n",
25579 asm_out_file);
25580 }
25581 #endif /* TARGET_XCOFF */
25582
25583 /* Compute a (partial) cost for rtx X. Return true if the complete
25584 cost has been computed, and false if subexpressions should be
25585 scanned. In either case, *TOTAL contains the cost result. */
25586
25587 static bool
25588 rs6000_rtx_costs (rtx x, int code, int outer_code, int *total,
25589 bool speed)
25590 {
25591 enum machine_mode mode = GET_MODE (x);
25592
25593 switch (code)
25594 {
25595 /* On the RS/6000, if it is valid in the insn, it is free. */
25596 case CONST_INT:
25597 if (((outer_code == SET
25598 || outer_code == PLUS
25599 || outer_code == MINUS)
25600 && (satisfies_constraint_I (x)
25601 || satisfies_constraint_L (x)))
25602 || (outer_code == AND
25603 && (satisfies_constraint_K (x)
25604 || (mode == SImode
25605 ? satisfies_constraint_L (x)
25606 : satisfies_constraint_J (x))
25607 || mask_operand (x, mode)
25608 || (mode == DImode
25609 && mask64_operand (x, DImode))))
25610 || ((outer_code == IOR || outer_code == XOR)
25611 && (satisfies_constraint_K (x)
25612 || (mode == SImode
25613 ? satisfies_constraint_L (x)
25614 : satisfies_constraint_J (x))))
25615 || outer_code == ASHIFT
25616 || outer_code == ASHIFTRT
25617 || outer_code == LSHIFTRT
25618 || outer_code == ROTATE
25619 || outer_code == ROTATERT
25620 || outer_code == ZERO_EXTRACT
25621 || (outer_code == MULT
25622 && satisfies_constraint_I (x))
25623 || ((outer_code == DIV || outer_code == UDIV
25624 || outer_code == MOD || outer_code == UMOD)
25625 && exact_log2 (INTVAL (x)) >= 0)
25626 || (outer_code == COMPARE
25627 && (satisfies_constraint_I (x)
25628 || satisfies_constraint_K (x)))
25629 || (outer_code == EQ
25630 && (satisfies_constraint_I (x)
25631 || satisfies_constraint_K (x)
25632 || (mode == SImode
25633 ? satisfies_constraint_L (x)
25634 : satisfies_constraint_J (x))))
25635 || (outer_code == GTU
25636 && satisfies_constraint_I (x))
25637 || (outer_code == LTU
25638 && satisfies_constraint_P (x)))
25639 {
25640 *total = 0;
25641 return true;
25642 }
25643 else if ((outer_code == PLUS
25644 && reg_or_add_cint_operand (x, VOIDmode))
25645 || (outer_code == MINUS
25646 && reg_or_sub_cint_operand (x, VOIDmode))
25647 || ((outer_code == SET
25648 || outer_code == IOR
25649 || outer_code == XOR)
25650 && (INTVAL (x)
25651 & ~ (unsigned HOST_WIDE_INT) 0xffffffff) == 0))
25652 {
25653 *total = COSTS_N_INSNS (1);
25654 return true;
25655 }
25656 /* FALLTHRU */
25657
25658 case CONST_DOUBLE:
25659 if (mode == DImode && code == CONST_DOUBLE)
25660 {
25661 if ((outer_code == IOR || outer_code == XOR)
25662 && CONST_DOUBLE_HIGH (x) == 0
25663 && (CONST_DOUBLE_LOW (x)
25664 & ~ (unsigned HOST_WIDE_INT) 0xffff) == 0)
25665 {
25666 *total = 0;
25667 return true;
25668 }
25669 else if ((outer_code == AND && and64_2_operand (x, DImode))
25670 || ((outer_code == SET
25671 || outer_code == IOR
25672 || outer_code == XOR)
25673 && CONST_DOUBLE_HIGH (x) == 0))
25674 {
25675 *total = COSTS_N_INSNS (1);
25676 return true;
25677 }
25678 }
25679 /* FALLTHRU */
25680
25681 case CONST:
25682 case HIGH:
25683 case SYMBOL_REF:
25684 case MEM:
25685 /* When optimizing for size, MEM should be slightly more expensive
25686 than generating address, e.g., (plus (reg) (const)).
25687 L1 cache latency is about two instructions. */
25688 *total = !speed ? COSTS_N_INSNS (1) + 1 : COSTS_N_INSNS (2);
25689 return true;
25690
25691 case LABEL_REF:
25692 *total = 0;
25693 return true;
25694
25695 case PLUS:
25696 if (mode == DFmode)
25697 {
25698 if (GET_CODE (XEXP (x, 0)) == MULT)
25699 {
25700 /* FNMA accounted in outer NEG. */
25701 if (outer_code == NEG)
25702 *total = rs6000_cost->dmul - rs6000_cost->fp;
25703 else
25704 *total = rs6000_cost->dmul;
25705 }
25706 else
25707 *total = rs6000_cost->fp;
25708 }
25709 else if (mode == SFmode)
25710 {
25711 /* FNMA accounted in outer NEG. */
25712 if (outer_code == NEG && GET_CODE (XEXP (x, 0)) == MULT)
25713 *total = 0;
25714 else
25715 *total = rs6000_cost->fp;
25716 }
25717 else
25718 *total = COSTS_N_INSNS (1);
25719 return false;
25720
25721 case MINUS:
25722 if (mode == DFmode)
25723 {
25724 if (GET_CODE (XEXP (x, 0)) == MULT
25725 || GET_CODE (XEXP (x, 1)) == MULT)
25726 {
25727 /* FNMA accounted in outer NEG. */
25728 if (outer_code == NEG)
25729 *total = rs6000_cost->dmul - rs6000_cost->fp;
25730 else
25731 *total = rs6000_cost->dmul;
25732 }
25733 else
25734 *total = rs6000_cost->fp;
25735 }
25736 else if (mode == SFmode)
25737 {
25738 /* FNMA accounted in outer NEG. */
25739 if (outer_code == NEG && GET_CODE (XEXP (x, 0)) == MULT)
25740 *total = 0;
25741 else
25742 *total = rs6000_cost->fp;
25743 }
25744 else
25745 *total = COSTS_N_INSNS (1);
25746 return false;
25747
25748 case MULT:
25749 if (GET_CODE (XEXP (x, 1)) == CONST_INT
25750 && satisfies_constraint_I (XEXP (x, 1)))
25751 {
25752 if (INTVAL (XEXP (x, 1)) >= -256
25753 && INTVAL (XEXP (x, 1)) <= 255)
25754 *total = rs6000_cost->mulsi_const9;
25755 else
25756 *total = rs6000_cost->mulsi_const;
25757 }
25758 /* FMA accounted in outer PLUS/MINUS. */
25759 else if ((mode == DFmode || mode == SFmode)
25760 && (outer_code == PLUS || outer_code == MINUS))
25761 *total = 0;
25762 else if (mode == DFmode)
25763 *total = rs6000_cost->dmul;
25764 else if (mode == SFmode)
25765 *total = rs6000_cost->fp;
25766 else if (mode == DImode)
25767 *total = rs6000_cost->muldi;
25768 else
25769 *total = rs6000_cost->mulsi;
25770 return false;
25771
25772 case DIV:
25773 case MOD:
25774 if (FLOAT_MODE_P (mode))
25775 {
25776 *total = mode == DFmode ? rs6000_cost->ddiv
25777 : rs6000_cost->sdiv;
25778 return false;
25779 }
25780 /* FALLTHRU */
25781
25782 case UDIV:
25783 case UMOD:
25784 if (GET_CODE (XEXP (x, 1)) == CONST_INT
25785 && exact_log2 (INTVAL (XEXP (x, 1))) >= 0)
25786 {
25787 if (code == DIV || code == MOD)
25788 /* Shift, addze */
25789 *total = COSTS_N_INSNS (2);
25790 else
25791 /* Shift */
25792 *total = COSTS_N_INSNS (1);
25793 }
25794 else
25795 {
25796 if (GET_MODE (XEXP (x, 1)) == DImode)
25797 *total = rs6000_cost->divdi;
25798 else
25799 *total = rs6000_cost->divsi;
25800 }
25801 /* Add in shift and subtract for MOD. */
25802 if (code == MOD || code == UMOD)
25803 *total += COSTS_N_INSNS (2);
25804 return false;
25805
25806 case CTZ:
25807 case FFS:
25808 *total = COSTS_N_INSNS (4);
25809 return false;
25810
25811 case POPCOUNT:
25812 *total = COSTS_N_INSNS (TARGET_POPCNTD ? 1 : 6);
25813 return false;
25814
25815 case PARITY:
25816 *total = COSTS_N_INSNS (TARGET_CMPB ? 2 : 6);
25817 return false;
25818
25819 case NOT:
25820 if (outer_code == AND || outer_code == IOR || outer_code == XOR)
25821 {
25822 *total = 0;
25823 return false;
25824 }
25825 /* FALLTHRU */
25826
25827 case AND:
25828 case CLZ:
25829 case IOR:
25830 case XOR:
25831 case ZERO_EXTRACT:
25832 *total = COSTS_N_INSNS (1);
25833 return false;
25834
25835 case ASHIFT:
25836 case ASHIFTRT:
25837 case LSHIFTRT:
25838 case ROTATE:
25839 case ROTATERT:
25840 /* Handle mul_highpart. */
25841 if (outer_code == TRUNCATE
25842 && GET_CODE (XEXP (x, 0)) == MULT)
25843 {
25844 if (mode == DImode)
25845 *total = rs6000_cost->muldi;
25846 else
25847 *total = rs6000_cost->mulsi;
25848 return true;
25849 }
25850 else if (outer_code == AND)
25851 *total = 0;
25852 else
25853 *total = COSTS_N_INSNS (1);
25854 return false;
25855
25856 case SIGN_EXTEND:
25857 case ZERO_EXTEND:
25858 if (GET_CODE (XEXP (x, 0)) == MEM)
25859 *total = 0;
25860 else
25861 *total = COSTS_N_INSNS (1);
25862 return false;
25863
25864 case COMPARE:
25865 case NEG:
25866 case ABS:
25867 if (!FLOAT_MODE_P (mode))
25868 {
25869 *total = COSTS_N_INSNS (1);
25870 return false;
25871 }
25872 /* FALLTHRU */
25873
25874 case FLOAT:
25875 case UNSIGNED_FLOAT:
25876 case FIX:
25877 case UNSIGNED_FIX:
25878 case FLOAT_TRUNCATE:
25879 *total = rs6000_cost->fp;
25880 return false;
25881
25882 case FLOAT_EXTEND:
25883 if (mode == DFmode)
25884 *total = 0;
25885 else
25886 *total = rs6000_cost->fp;
25887 return false;
25888
25889 case UNSPEC:
25890 switch (XINT (x, 1))
25891 {
25892 case UNSPEC_FRSP:
25893 *total = rs6000_cost->fp;
25894 return true;
25895
25896 default:
25897 break;
25898 }
25899 break;
25900
25901 case CALL:
25902 case IF_THEN_ELSE:
25903 if (!speed)
25904 {
25905 *total = COSTS_N_INSNS (1);
25906 return true;
25907 }
25908 else if (FLOAT_MODE_P (mode)
25909 && TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT && TARGET_FPRS)
25910 {
25911 *total = rs6000_cost->fp;
25912 return false;
25913 }
25914 break;
25915
25916 case EQ:
25917 case GTU:
25918 case LTU:
25919 /* Carry bit requires mode == Pmode.
25920 NEG or PLUS already counted so only add one. */
25921 if (mode == Pmode
25922 && (outer_code == NEG || outer_code == PLUS))
25923 {
25924 *total = COSTS_N_INSNS (1);
25925 return true;
25926 }
25927 if (outer_code == SET)
25928 {
25929 if (XEXP (x, 1) == const0_rtx)
25930 {
25931 if (TARGET_ISEL && !TARGET_MFCRF)
25932 *total = COSTS_N_INSNS (8);
25933 else
25934 *total = COSTS_N_INSNS (2);
25935 return true;
25936 }
25937 else if (mode == Pmode)
25938 {
25939 *total = COSTS_N_INSNS (3);
25940 return false;
25941 }
25942 }
25943 /* FALLTHRU */
25944
25945 case GT:
25946 case LT:
25947 case UNORDERED:
25948 if (outer_code == SET && (XEXP (x, 1) == const0_rtx))
25949 {
25950 if (TARGET_ISEL && !TARGET_MFCRF)
25951 *total = COSTS_N_INSNS (8);
25952 else
25953 *total = COSTS_N_INSNS (2);
25954 return true;
25955 }
25956 /* CC COMPARE. */
25957 if (outer_code == COMPARE)
25958 {
25959 *total = 0;
25960 return true;
25961 }
25962 break;
25963
25964 default:
25965 break;
25966 }
25967
25968 return false;
25969 }
25970
25971 /* Debug form of r6000_rtx_costs that is selected if -mdebug=cost. */
25972
25973 static bool
25974 rs6000_debug_rtx_costs (rtx x, int code, int outer_code, int *total,
25975 bool speed)
25976 {
25977 bool ret = rs6000_rtx_costs (x, code, outer_code, total, speed);
25978
25979 fprintf (stderr,
25980 "\nrs6000_rtx_costs, return = %s, code = %s, outer_code = %s, "
25981 "total = %d, speed = %s, x:\n",
25982 ret ? "complete" : "scan inner",
25983 GET_RTX_NAME (code),
25984 GET_RTX_NAME (outer_code),
25985 *total,
25986 speed ? "true" : "false");
25987
25988 debug_rtx (x);
25989
25990 return ret;
25991 }
25992
25993 /* Debug form of ADDRESS_COST that is selected if -mdebug=cost. */
25994
25995 static int
25996 rs6000_debug_address_cost (rtx x, bool speed)
25997 {
25998 int ret = TARGET_ADDRESS_COST (x, speed);
25999
26000 fprintf (stderr, "\nrs6000_address_cost, return = %d, speed = %s, x:\n",
26001 ret, speed ? "true" : "false");
26002 debug_rtx (x);
26003
26004 return ret;
26005 }
26006
26007
26008 /* A C expression returning the cost of moving data from a register of class
26009 CLASS1 to one of CLASS2. */
26010
26011 static int
26012 rs6000_register_move_cost (enum machine_mode mode,
26013 reg_class_t from, reg_class_t to)
26014 {
26015 int ret;
26016
26017 /* Moves from/to GENERAL_REGS. */
26018 if (reg_classes_intersect_p (to, GENERAL_REGS)
26019 || reg_classes_intersect_p (from, GENERAL_REGS))
26020 {
26021 if (! reg_classes_intersect_p (to, GENERAL_REGS))
26022 from = to;
26023
26024 if (from == FLOAT_REGS || from == ALTIVEC_REGS || from == VSX_REGS)
26025 ret = (rs6000_memory_move_cost (mode, from, false)
26026 + rs6000_memory_move_cost (mode, GENERAL_REGS, false));
26027
26028 /* It's more expensive to move CR_REGS than CR0_REGS because of the
26029 shift. */
26030 else if (from == CR_REGS)
26031 ret = 4;
26032
26033 /* Power6 has slower LR/CTR moves so make them more expensive than
26034 memory in order to bias spills to memory .*/
26035 else if (rs6000_cpu == PROCESSOR_POWER6
26036 && reg_classes_intersect_p (from, LINK_OR_CTR_REGS))
26037 ret = 6 * hard_regno_nregs[0][mode];
26038
26039 else
26040 /* A move will cost one instruction per GPR moved. */
26041 ret = 2 * hard_regno_nregs[0][mode];
26042 }
26043
26044 /* If we have VSX, we can easily move between FPR or Altivec registers. */
26045 else if (VECTOR_UNIT_VSX_P (mode)
26046 && reg_classes_intersect_p (to, VSX_REGS)
26047 && reg_classes_intersect_p (from, VSX_REGS))
26048 ret = 2 * hard_regno_nregs[32][mode];
26049
26050 /* Moving between two similar registers is just one instruction. */
26051 else if (reg_classes_intersect_p (to, from))
26052 ret = (mode == TFmode || mode == TDmode) ? 4 : 2;
26053
26054 /* Everything else has to go through GENERAL_REGS. */
26055 else
26056 ret = (rs6000_register_move_cost (mode, GENERAL_REGS, to)
26057 + rs6000_register_move_cost (mode, from, GENERAL_REGS));
26058
26059 if (TARGET_DEBUG_COST)
26060 fprintf (stderr,
26061 "rs6000_register_move_cost:, ret=%d, mode=%s, from=%s, to=%s\n",
26062 ret, GET_MODE_NAME (mode), reg_class_names[from],
26063 reg_class_names[to]);
26064
26065 return ret;
26066 }
26067
26068 /* A C expressions returning the cost of moving data of MODE from a register to
26069 or from memory. */
26070
26071 static int
26072 rs6000_memory_move_cost (enum machine_mode mode, reg_class_t rclass,
26073 bool in ATTRIBUTE_UNUSED)
26074 {
26075 int ret;
26076
26077 if (reg_classes_intersect_p (rclass, GENERAL_REGS))
26078 ret = 4 * hard_regno_nregs[0][mode];
26079 else if (reg_classes_intersect_p (rclass, FLOAT_REGS))
26080 ret = 4 * hard_regno_nregs[32][mode];
26081 else if (reg_classes_intersect_p (rclass, ALTIVEC_REGS))
26082 ret = 4 * hard_regno_nregs[FIRST_ALTIVEC_REGNO][mode];
26083 else
26084 ret = 4 + rs6000_register_move_cost (mode, rclass, GENERAL_REGS);
26085
26086 if (TARGET_DEBUG_COST)
26087 fprintf (stderr,
26088 "rs6000_memory_move_cost: ret=%d, mode=%s, rclass=%s, in=%d\n",
26089 ret, GET_MODE_NAME (mode), reg_class_names[rclass], in);
26090
26091 return ret;
26092 }
26093
26094 /* Returns a code for a target-specific builtin that implements
26095 reciprocal of the function, or NULL_TREE if not available. */
26096
26097 static tree
26098 rs6000_builtin_reciprocal (unsigned int fn, bool md_fn,
26099 bool sqrt ATTRIBUTE_UNUSED)
26100 {
26101 if (optimize_insn_for_size_p ())
26102 return NULL_TREE;
26103
26104 if (md_fn)
26105 switch (fn)
26106 {
26107 case VSX_BUILTIN_XVSQRTDP:
26108 if (!RS6000_RECIP_AUTO_RSQRTE_P (V2DFmode))
26109 return NULL_TREE;
26110
26111 return rs6000_builtin_decls[VSX_BUILTIN_VEC_RSQRT_V2DF];
26112
26113 case VSX_BUILTIN_XVSQRTSP:
26114 if (!RS6000_RECIP_AUTO_RSQRTE_P (V4SFmode))
26115 return NULL_TREE;
26116
26117 return rs6000_builtin_decls[VSX_BUILTIN_VEC_RSQRT_V4SF];
26118
26119 default:
26120 return NULL_TREE;
26121 }
26122
26123 else
26124 switch (fn)
26125 {
26126 case BUILT_IN_SQRT:
26127 if (!RS6000_RECIP_AUTO_RSQRTE_P (DFmode))
26128 return NULL_TREE;
26129
26130 return rs6000_builtin_decls[RS6000_BUILTIN_RSQRT];
26131
26132 case BUILT_IN_SQRTF:
26133 if (!RS6000_RECIP_AUTO_RSQRTE_P (SFmode))
26134 return NULL_TREE;
26135
26136 return rs6000_builtin_decls[RS6000_BUILTIN_RSQRTF];
26137
26138 default:
26139 return NULL_TREE;
26140 }
26141 }
26142
26143 /* Load up a constant. If the mode is a vector mode, splat the value across
26144 all of the vector elements. */
26145
26146 static rtx
26147 rs6000_load_constant_and_splat (enum machine_mode mode, REAL_VALUE_TYPE dconst)
26148 {
26149 rtx reg;
26150
26151 if (mode == SFmode || mode == DFmode)
26152 {
26153 rtx d = CONST_DOUBLE_FROM_REAL_VALUE (dconst, mode);
26154 reg = force_reg (mode, d);
26155 }
26156 else if (mode == V4SFmode)
26157 {
26158 rtx d = CONST_DOUBLE_FROM_REAL_VALUE (dconst, SFmode);
26159 rtvec v = gen_rtvec (4, d, d, d, d);
26160 reg = gen_reg_rtx (mode);
26161 rs6000_expand_vector_init (reg, gen_rtx_PARALLEL (mode, v));
26162 }
26163 else if (mode == V2DFmode)
26164 {
26165 rtx d = CONST_DOUBLE_FROM_REAL_VALUE (dconst, DFmode);
26166 rtvec v = gen_rtvec (2, d, d);
26167 reg = gen_reg_rtx (mode);
26168 rs6000_expand_vector_init (reg, gen_rtx_PARALLEL (mode, v));
26169 }
26170 else
26171 gcc_unreachable ();
26172
26173 return reg;
26174 }
26175
26176 /* Generate a FMADD instruction:
26177 dst = (m1 * m2) + a
26178
26179 generating different RTL based on the fused multiply/add switch. */
26180
26181 static void
26182 rs6000_emit_madd (rtx dst, rtx m1, rtx m2, rtx a)
26183 {
26184 enum machine_mode mode = GET_MODE (dst);
26185
26186 if (!TARGET_FUSED_MADD)
26187 {
26188 /* For the simple ops, use the generator function, rather than assuming
26189 that the RTL is standard. */
26190 enum insn_code mcode = optab_handler (smul_optab, mode);
26191 enum insn_code acode = optab_handler (add_optab, mode);
26192 gen_2arg_fn_t gen_mul = (gen_2arg_fn_t) GEN_FCN (mcode);
26193 gen_2arg_fn_t gen_add = (gen_2arg_fn_t) GEN_FCN (acode);
26194 rtx mreg = gen_reg_rtx (mode);
26195
26196 gcc_assert (mcode != CODE_FOR_nothing && acode != CODE_FOR_nothing);
26197 emit_insn (gen_mul (mreg, m1, m2));
26198 emit_insn (gen_add (dst, mreg, a));
26199 }
26200
26201 else
26202 emit_insn (gen_rtx_SET (VOIDmode, dst,
26203 gen_rtx_PLUS (mode,
26204 gen_rtx_MULT (mode, m1, m2),
26205 a)));
26206 }
26207
26208 /* Generate a FMSUB instruction:
26209 dst = (m1 * m2) - a
26210
26211 generating different RTL based on the fused multiply/add switch. */
26212
26213 static void
26214 rs6000_emit_msub (rtx dst, rtx m1, rtx m2, rtx a)
26215 {
26216 enum machine_mode mode = GET_MODE (dst);
26217
26218 if (!TARGET_FUSED_MADD
26219 || (mode == V4SFmode && VECTOR_UNIT_ALTIVEC_P (V4SFmode)))
26220 {
26221 /* For the simple ops, use the generator function, rather than assuming
26222 that the RTL is standard. */
26223 enum insn_code mcode = optab_handler (smul_optab, mode);
26224 enum insn_code scode = optab_handler (add_optab, mode);
26225 gen_2arg_fn_t gen_mul = (gen_2arg_fn_t) GEN_FCN (mcode);
26226 gen_2arg_fn_t gen_sub = (gen_2arg_fn_t) GEN_FCN (scode);
26227 rtx mreg = gen_reg_rtx (mode);
26228
26229 gcc_assert (mcode != CODE_FOR_nothing && scode != CODE_FOR_nothing);
26230 emit_insn (gen_mul (mreg, m1, m2));
26231 emit_insn (gen_sub (dst, mreg, a));
26232 }
26233
26234 else
26235 emit_insn (gen_rtx_SET (VOIDmode, dst,
26236 gen_rtx_MINUS (mode,
26237 gen_rtx_MULT (mode, m1, m2),
26238 a)));
26239 }
26240
26241 /* Generate a FNMSUB instruction:
26242 dst = - ((m1 * m2) - a)
26243
26244 Which is equivalent to (except in the prescence of -0.0):
26245 dst = a - (m1 * m2)
26246
26247 generating different RTL based on the fast-math and fused multiply/add
26248 switches. */
26249
26250 static void
26251 rs6000_emit_nmsub (rtx dst, rtx m1, rtx m2, rtx a)
26252 {
26253 enum machine_mode mode = GET_MODE (dst);
26254
26255 if (!TARGET_FUSED_MADD)
26256 {
26257 /* For the simple ops, use the generator function, rather than assuming
26258 that the RTL is standard. */
26259 enum insn_code mcode = optab_handler (smul_optab, mode);
26260 enum insn_code scode = optab_handler (sub_optab, mode);
26261 gen_2arg_fn_t gen_mul = (gen_2arg_fn_t) GEN_FCN (mcode);
26262 gen_2arg_fn_t gen_sub = (gen_2arg_fn_t) GEN_FCN (scode);
26263 rtx mreg = gen_reg_rtx (mode);
26264
26265 gcc_assert (mcode != CODE_FOR_nothing && scode != CODE_FOR_nothing);
26266 emit_insn (gen_mul (mreg, m1, m2));
26267 emit_insn (gen_sub (dst, a, mreg));
26268 }
26269
26270 else
26271 {
26272 rtx m = gen_rtx_MULT (mode, m1, m2);
26273
26274 if (!HONOR_SIGNED_ZEROS (mode))
26275 emit_insn (gen_rtx_SET (VOIDmode, dst, gen_rtx_MINUS (mode, a, m)));
26276
26277 else
26278 emit_insn (gen_rtx_SET (VOIDmode, dst,
26279 gen_rtx_NEG (mode,
26280 gen_rtx_MINUS (mode, m, a))));
26281 }
26282 }
26283
26284 /* Newton-Raphson approximation of floating point divide with just 2 passes
26285 (either single precision floating point, or newer machines with higher
26286 accuracy estimates). Support both scalar and vector divide. Assumes no
26287 trapping math and finite arguments. */
26288
26289 static void
26290 rs6000_emit_swdiv_high_precision (rtx dst, rtx n, rtx d)
26291 {
26292 enum machine_mode mode = GET_MODE (dst);
26293 rtx x0, e0, e1, y1, u0, v0;
26294 enum insn_code code = optab_handler (smul_optab, mode);
26295 gen_2arg_fn_t gen_mul = (gen_2arg_fn_t) GEN_FCN (code);
26296 rtx one = rs6000_load_constant_and_splat (mode, dconst1);
26297
26298 gcc_assert (code != CODE_FOR_nothing);
26299
26300 /* x0 = 1./d estimate */
26301 x0 = gen_reg_rtx (mode);
26302 emit_insn (gen_rtx_SET (VOIDmode, x0,
26303 gen_rtx_UNSPEC (mode, gen_rtvec (1, d),
26304 UNSPEC_FRES)));
26305
26306 e0 = gen_reg_rtx (mode);
26307 rs6000_emit_nmsub (e0, d, x0, one); /* e0 = 1. - (d * x0) */
26308
26309 e1 = gen_reg_rtx (mode);
26310 rs6000_emit_madd (e1, e0, e0, e0); /* e1 = (e0 * e0) + e0 */
26311
26312 y1 = gen_reg_rtx (mode);
26313 rs6000_emit_madd (y1, e1, x0, x0); /* y1 = (e1 * x0) + x0 */
26314
26315 u0 = gen_reg_rtx (mode);
26316 emit_insn (gen_mul (u0, n, y1)); /* u0 = n * y1 */
26317
26318 v0 = gen_reg_rtx (mode);
26319 rs6000_emit_nmsub (v0, d, u0, n); /* v0 = n - (d * u0) */
26320
26321 rs6000_emit_madd (dst, v0, y1, u0); /* dst = (v0 * y1) + u0 */
26322 }
26323
26324 /* Newton-Raphson approximation of floating point divide that has a low
26325 precision estimate. Assumes no trapping math and finite arguments. */
26326
26327 static void
26328 rs6000_emit_swdiv_low_precision (rtx dst, rtx n, rtx d)
26329 {
26330 enum machine_mode mode = GET_MODE (dst);
26331 rtx x0, e0, e1, e2, y1, y2, y3, u0, v0, one;
26332 enum insn_code code = optab_handler (smul_optab, mode);
26333 gen_2arg_fn_t gen_mul = (gen_2arg_fn_t) GEN_FCN (code);
26334
26335 gcc_assert (code != CODE_FOR_nothing);
26336
26337 one = rs6000_load_constant_and_splat (mode, dconst1);
26338
26339 /* x0 = 1./d estimate */
26340 x0 = gen_reg_rtx (mode);
26341 emit_insn (gen_rtx_SET (VOIDmode, x0,
26342 gen_rtx_UNSPEC (mode, gen_rtvec (1, d),
26343 UNSPEC_FRES)));
26344
26345 e0 = gen_reg_rtx (mode);
26346 rs6000_emit_nmsub (e0, d, x0, one); /* e0 = 1. - d * x0 */
26347
26348 y1 = gen_reg_rtx (mode);
26349 rs6000_emit_madd (y1, e0, x0, x0); /* y1 = x0 + e0 * x0 */
26350
26351 e1 = gen_reg_rtx (mode);
26352 emit_insn (gen_mul (e1, e0, e0)); /* e1 = e0 * e0 */
26353
26354 y2 = gen_reg_rtx (mode);
26355 rs6000_emit_madd (y2, e1, y1, y1); /* y2 = y1 + e1 * y1 */
26356
26357 e2 = gen_reg_rtx (mode);
26358 emit_insn (gen_mul (e2, e1, e1)); /* e2 = e1 * e1 */
26359
26360 y3 = gen_reg_rtx (mode);
26361 rs6000_emit_madd (y3, e2, y2, y2); /* y3 = y2 + e2 * y2 */
26362
26363 u0 = gen_reg_rtx (mode);
26364 emit_insn (gen_mul (u0, n, y3)); /* u0 = n * y3 */
26365
26366 v0 = gen_reg_rtx (mode);
26367 rs6000_emit_nmsub (v0, d, u0, n); /* v0 = n - d * u0 */
26368
26369 rs6000_emit_madd (dst, v0, y3, u0); /* dst = u0 + v0 * y3 */
26370 }
26371
26372 /* Newton-Raphson approximation of floating point divide DST = N/D. If NOTE_P,
26373 add a reg_note saying that this was a division. Support both scalar and
26374 vector divide. Assumes no trapping math and finite arguments. */
26375
26376 void
26377 rs6000_emit_swdiv (rtx dst, rtx n, rtx d, bool note_p)
26378 {
26379 enum machine_mode mode = GET_MODE (dst);
26380
26381 if (RS6000_RECIP_HIGH_PRECISION_P (mode))
26382 rs6000_emit_swdiv_high_precision (dst, n, d);
26383 else
26384 rs6000_emit_swdiv_low_precision (dst, n, d);
26385
26386 if (note_p)
26387 add_reg_note (get_last_insn (), REG_EQUAL, gen_rtx_DIV (mode, n, d));
26388 }
26389
26390 /* Newton-Raphson approximation of single/double-precision floating point
26391 rsqrt. Assumes no trapping math and finite arguments. */
26392
26393 void
26394 rs6000_emit_swrsqrt (rtx dst, rtx src)
26395 {
26396 enum machine_mode mode = GET_MODE (src);
26397 rtx x0 = gen_reg_rtx (mode);
26398 rtx y = gen_reg_rtx (mode);
26399 int passes = (TARGET_RECIP_PRECISION) ? 2 : 3;
26400 REAL_VALUE_TYPE dconst3_2;
26401 int i;
26402 rtx halfthree;
26403 enum insn_code code = optab_handler (smul_optab, mode);
26404 gen_2arg_fn_t gen_mul = (gen_2arg_fn_t) GEN_FCN (code);
26405
26406 gcc_assert (code != CODE_FOR_nothing);
26407
26408 /* Load up the constant 1.5 either as a scalar, or as a vector. */
26409 real_from_integer (&dconst3_2, VOIDmode, 3, 0, 0);
26410 SET_REAL_EXP (&dconst3_2, REAL_EXP (&dconst3_2) - 1);
26411
26412 halfthree = rs6000_load_constant_and_splat (mode, dconst3_2);
26413
26414 /* x0 = rsqrt estimate */
26415 emit_insn (gen_rtx_SET (VOIDmode, x0,
26416 gen_rtx_UNSPEC (mode, gen_rtvec (1, src),
26417 UNSPEC_RSQRT)));
26418
26419 /* y = 0.5 * src = 1.5 * src - src -> fewer constants */
26420 rs6000_emit_msub (y, src, halfthree, src);
26421
26422 for (i = 0; i < passes; i++)
26423 {
26424 rtx x1 = gen_reg_rtx (mode);
26425 rtx u = gen_reg_rtx (mode);
26426 rtx v = gen_reg_rtx (mode);
26427
26428 /* x1 = x0 * (1.5 - y * (x0 * x0)) */
26429 emit_insn (gen_mul (u, x0, x0));
26430 rs6000_emit_nmsub (v, y, u, halfthree);
26431 emit_insn (gen_mul (x1, x0, v));
26432 x0 = x1;
26433 }
26434
26435 emit_move_insn (dst, x0);
26436 return;
26437 }
26438
26439 /* Emit popcount intrinsic on TARGET_POPCNTB (Power5) and TARGET_POPCNTD
26440 (Power7) targets. DST is the target, and SRC is the argument operand. */
26441
26442 void
26443 rs6000_emit_popcount (rtx dst, rtx src)
26444 {
26445 enum machine_mode mode = GET_MODE (dst);
26446 rtx tmp1, tmp2;
26447
26448 /* Use the PPC ISA 2.06 popcnt{w,d} instruction if we can. */
26449 if (TARGET_POPCNTD)
26450 {
26451 if (mode == SImode)
26452 emit_insn (gen_popcntdsi2 (dst, src));
26453 else
26454 emit_insn (gen_popcntddi2 (dst, src));
26455 return;
26456 }
26457
26458 tmp1 = gen_reg_rtx (mode);
26459
26460 if (mode == SImode)
26461 {
26462 emit_insn (gen_popcntbsi2 (tmp1, src));
26463 tmp2 = expand_mult (SImode, tmp1, GEN_INT (0x01010101),
26464 NULL_RTX, 0);
26465 tmp2 = force_reg (SImode, tmp2);
26466 emit_insn (gen_lshrsi3 (dst, tmp2, GEN_INT (24)));
26467 }
26468 else
26469 {
26470 emit_insn (gen_popcntbdi2 (tmp1, src));
26471 tmp2 = expand_mult (DImode, tmp1,
26472 GEN_INT ((HOST_WIDE_INT)
26473 0x01010101 << 32 | 0x01010101),
26474 NULL_RTX, 0);
26475 tmp2 = force_reg (DImode, tmp2);
26476 emit_insn (gen_lshrdi3 (dst, tmp2, GEN_INT (56)));
26477 }
26478 }
26479
26480
26481 /* Emit parity intrinsic on TARGET_POPCNTB targets. DST is the
26482 target, and SRC is the argument operand. */
26483
26484 void
26485 rs6000_emit_parity (rtx dst, rtx src)
26486 {
26487 enum machine_mode mode = GET_MODE (dst);
26488 rtx tmp;
26489
26490 tmp = gen_reg_rtx (mode);
26491
26492 /* Use the PPC ISA 2.05 prtyw/prtyd instruction if we can. */
26493 if (TARGET_CMPB)
26494 {
26495 if (mode == SImode)
26496 {
26497 emit_insn (gen_popcntbsi2 (tmp, src));
26498 emit_insn (gen_paritysi2_cmpb (dst, tmp));
26499 }
26500 else
26501 {
26502 emit_insn (gen_popcntbdi2 (tmp, src));
26503 emit_insn (gen_paritydi2_cmpb (dst, tmp));
26504 }
26505 return;
26506 }
26507
26508 if (mode == SImode)
26509 {
26510 /* Is mult+shift >= shift+xor+shift+xor? */
26511 if (rs6000_cost->mulsi_const >= COSTS_N_INSNS (3))
26512 {
26513 rtx tmp1, tmp2, tmp3, tmp4;
26514
26515 tmp1 = gen_reg_rtx (SImode);
26516 emit_insn (gen_popcntbsi2 (tmp1, src));
26517
26518 tmp2 = gen_reg_rtx (SImode);
26519 emit_insn (gen_lshrsi3 (tmp2, tmp1, GEN_INT (16)));
26520 tmp3 = gen_reg_rtx (SImode);
26521 emit_insn (gen_xorsi3 (tmp3, tmp1, tmp2));
26522
26523 tmp4 = gen_reg_rtx (SImode);
26524 emit_insn (gen_lshrsi3 (tmp4, tmp3, GEN_INT (8)));
26525 emit_insn (gen_xorsi3 (tmp, tmp3, tmp4));
26526 }
26527 else
26528 rs6000_emit_popcount (tmp, src);
26529 emit_insn (gen_andsi3 (dst, tmp, const1_rtx));
26530 }
26531 else
26532 {
26533 /* Is mult+shift >= shift+xor+shift+xor+shift+xor? */
26534 if (rs6000_cost->muldi >= COSTS_N_INSNS (5))
26535 {
26536 rtx tmp1, tmp2, tmp3, tmp4, tmp5, tmp6;
26537
26538 tmp1 = gen_reg_rtx (DImode);
26539 emit_insn (gen_popcntbdi2 (tmp1, src));
26540
26541 tmp2 = gen_reg_rtx (DImode);
26542 emit_insn (gen_lshrdi3 (tmp2, tmp1, GEN_INT (32)));
26543 tmp3 = gen_reg_rtx (DImode);
26544 emit_insn (gen_xordi3 (tmp3, tmp1, tmp2));
26545
26546 tmp4 = gen_reg_rtx (DImode);
26547 emit_insn (gen_lshrdi3 (tmp4, tmp3, GEN_INT (16)));
26548 tmp5 = gen_reg_rtx (DImode);
26549 emit_insn (gen_xordi3 (tmp5, tmp3, tmp4));
26550
26551 tmp6 = gen_reg_rtx (DImode);
26552 emit_insn (gen_lshrdi3 (tmp6, tmp5, GEN_INT (8)));
26553 emit_insn (gen_xordi3 (tmp, tmp5, tmp6));
26554 }
26555 else
26556 rs6000_emit_popcount (tmp, src);
26557 emit_insn (gen_anddi3 (dst, tmp, const1_rtx));
26558 }
26559 }
26560
26561 /* Return an RTX representing where to find the function value of a
26562 function returning MODE. */
26563 static rtx
26564 rs6000_complex_function_value (enum machine_mode mode)
26565 {
26566 unsigned int regno;
26567 rtx r1, r2;
26568 enum machine_mode inner = GET_MODE_INNER (mode);
26569 unsigned int inner_bytes = GET_MODE_SIZE (inner);
26570
26571 if (FLOAT_MODE_P (mode) && TARGET_HARD_FLOAT && TARGET_FPRS)
26572 regno = FP_ARG_RETURN;
26573 else
26574 {
26575 regno = GP_ARG_RETURN;
26576
26577 /* 32-bit is OK since it'll go in r3/r4. */
26578 if (TARGET_32BIT && inner_bytes >= 4)
26579 return gen_rtx_REG (mode, regno);
26580 }
26581
26582 if (inner_bytes >= 8)
26583 return gen_rtx_REG (mode, regno);
26584
26585 r1 = gen_rtx_EXPR_LIST (inner, gen_rtx_REG (inner, regno),
26586 const0_rtx);
26587 r2 = gen_rtx_EXPR_LIST (inner, gen_rtx_REG (inner, regno + 1),
26588 GEN_INT (inner_bytes));
26589 return gen_rtx_PARALLEL (mode, gen_rtvec (2, r1, r2));
26590 }
26591
26592 /* Target hook for TARGET_FUNCTION_VALUE.
26593
26594 On the SPE, both FPs and vectors are returned in r3.
26595
26596 On RS/6000 an integer value is in r3 and a floating-point value is in
26597 fp1, unless -msoft-float. */
26598
26599 rtx
26600 rs6000_function_value (const_tree valtype,
26601 const_tree fn_decl_or_type ATTRIBUTE_UNUSED,
26602 bool outgoing ATTRIBUTE_UNUSED)
26603 {
26604 enum machine_mode mode;
26605 unsigned int regno;
26606
26607 /* Special handling for structs in darwin64. */
26608 if (TARGET_MACHO
26609 && rs6000_darwin64_struct_check_p (TYPE_MODE (valtype), valtype))
26610 {
26611 CUMULATIVE_ARGS valcum;
26612 rtx valret;
26613
26614 valcum.words = 0;
26615 valcum.fregno = FP_ARG_MIN_REG;
26616 valcum.vregno = ALTIVEC_ARG_MIN_REG;
26617 /* Do a trial code generation as if this were going to be passed as
26618 an argument; if any part goes in memory, we return NULL. */
26619 valret = rs6000_darwin64_record_arg (&valcum, valtype, true, true);
26620 if (valret)
26621 return valret;
26622 /* Otherwise fall through to standard ABI rules. */
26623 }
26624
26625 if (TARGET_32BIT && TARGET_POWERPC64 && TYPE_MODE (valtype) == DImode)
26626 {
26627 /* Long long return value need be split in -mpowerpc64, 32bit ABI. */
26628 return gen_rtx_PARALLEL (DImode,
26629 gen_rtvec (2,
26630 gen_rtx_EXPR_LIST (VOIDmode,
26631 gen_rtx_REG (SImode, GP_ARG_RETURN),
26632 const0_rtx),
26633 gen_rtx_EXPR_LIST (VOIDmode,
26634 gen_rtx_REG (SImode,
26635 GP_ARG_RETURN + 1),
26636 GEN_INT (4))));
26637 }
26638 if (TARGET_32BIT && TARGET_POWERPC64 && TYPE_MODE (valtype) == DCmode)
26639 {
26640 return gen_rtx_PARALLEL (DCmode,
26641 gen_rtvec (4,
26642 gen_rtx_EXPR_LIST (VOIDmode,
26643 gen_rtx_REG (SImode, GP_ARG_RETURN),
26644 const0_rtx),
26645 gen_rtx_EXPR_LIST (VOIDmode,
26646 gen_rtx_REG (SImode,
26647 GP_ARG_RETURN + 1),
26648 GEN_INT (4)),
26649 gen_rtx_EXPR_LIST (VOIDmode,
26650 gen_rtx_REG (SImode,
26651 GP_ARG_RETURN + 2),
26652 GEN_INT (8)),
26653 gen_rtx_EXPR_LIST (VOIDmode,
26654 gen_rtx_REG (SImode,
26655 GP_ARG_RETURN + 3),
26656 GEN_INT (12))));
26657 }
26658
26659 mode = TYPE_MODE (valtype);
26660 if ((INTEGRAL_TYPE_P (valtype) && GET_MODE_BITSIZE (mode) < BITS_PER_WORD)
26661 || POINTER_TYPE_P (valtype))
26662 mode = TARGET_32BIT ? SImode : DImode;
26663
26664 if (DECIMAL_FLOAT_MODE_P (mode) && TARGET_HARD_FLOAT && TARGET_FPRS)
26665 /* _Decimal128 must use an even/odd register pair. */
26666 regno = (mode == TDmode) ? FP_ARG_RETURN + 1 : FP_ARG_RETURN;
26667 else if (SCALAR_FLOAT_TYPE_P (valtype) && TARGET_HARD_FLOAT && TARGET_FPRS
26668 && ((TARGET_SINGLE_FLOAT && (mode == SFmode)) || TARGET_DOUBLE_FLOAT))
26669 regno = FP_ARG_RETURN;
26670 else if (TREE_CODE (valtype) == COMPLEX_TYPE
26671 && targetm.calls.split_complex_arg)
26672 return rs6000_complex_function_value (mode);
26673 else if (TREE_CODE (valtype) == VECTOR_TYPE
26674 && TARGET_ALTIVEC && TARGET_ALTIVEC_ABI
26675 && ALTIVEC_VECTOR_MODE (mode))
26676 regno = ALTIVEC_ARG_RETURN;
26677 else if (TREE_CODE (valtype) == VECTOR_TYPE
26678 && TARGET_VSX && TARGET_ALTIVEC_ABI
26679 && VSX_VECTOR_MODE (mode))
26680 regno = ALTIVEC_ARG_RETURN;
26681 else if (TARGET_E500_DOUBLE && TARGET_HARD_FLOAT
26682 && (mode == DFmode || mode == DCmode
26683 || mode == TFmode || mode == TCmode))
26684 return spe_build_register_parallel (mode, GP_ARG_RETURN);
26685 else
26686 regno = GP_ARG_RETURN;
26687
26688 return gen_rtx_REG (mode, regno);
26689 }
26690
26691 /* Define how to find the value returned by a library function
26692 assuming the value has mode MODE. */
26693 rtx
26694 rs6000_libcall_value (enum machine_mode mode)
26695 {
26696 unsigned int regno;
26697
26698 if (TARGET_32BIT && TARGET_POWERPC64 && mode == DImode)
26699 {
26700 /* Long long return value need be split in -mpowerpc64, 32bit ABI. */
26701 return gen_rtx_PARALLEL (DImode,
26702 gen_rtvec (2,
26703 gen_rtx_EXPR_LIST (VOIDmode,
26704 gen_rtx_REG (SImode, GP_ARG_RETURN),
26705 const0_rtx),
26706 gen_rtx_EXPR_LIST (VOIDmode,
26707 gen_rtx_REG (SImode,
26708 GP_ARG_RETURN + 1),
26709 GEN_INT (4))));
26710 }
26711
26712 if (DECIMAL_FLOAT_MODE_P (mode) && TARGET_HARD_FLOAT && TARGET_FPRS)
26713 /* _Decimal128 must use an even/odd register pair. */
26714 regno = (mode == TDmode) ? FP_ARG_RETURN + 1 : FP_ARG_RETURN;
26715 else if (SCALAR_FLOAT_MODE_P (mode)
26716 && TARGET_HARD_FLOAT && TARGET_FPRS
26717 && ((TARGET_SINGLE_FLOAT && mode == SFmode) || TARGET_DOUBLE_FLOAT))
26718 regno = FP_ARG_RETURN;
26719 else if (ALTIVEC_VECTOR_MODE (mode)
26720 && TARGET_ALTIVEC && TARGET_ALTIVEC_ABI)
26721 regno = ALTIVEC_ARG_RETURN;
26722 else if (VSX_VECTOR_MODE (mode)
26723 && TARGET_VSX && TARGET_ALTIVEC_ABI)
26724 regno = ALTIVEC_ARG_RETURN;
26725 else if (COMPLEX_MODE_P (mode) && targetm.calls.split_complex_arg)
26726 return rs6000_complex_function_value (mode);
26727 else if (TARGET_E500_DOUBLE && TARGET_HARD_FLOAT
26728 && (mode == DFmode || mode == DCmode
26729 || mode == TFmode || mode == TCmode))
26730 return spe_build_register_parallel (mode, GP_ARG_RETURN);
26731 else
26732 regno = GP_ARG_RETURN;
26733
26734 return gen_rtx_REG (mode, regno);
26735 }
26736
26737
26738 /* Given FROM and TO register numbers, say whether this elimination is allowed.
26739 Frame pointer elimination is automatically handled.
26740
26741 For the RS/6000, if frame pointer elimination is being done, we would like
26742 to convert ap into fp, not sp.
26743
26744 We need r30 if -mminimal-toc was specified, and there are constant pool
26745 references. */
26746
26747 bool
26748 rs6000_can_eliminate (const int from, const int to)
26749 {
26750 return (from == ARG_POINTER_REGNUM && to == STACK_POINTER_REGNUM
26751 ? ! frame_pointer_needed
26752 : from == RS6000_PIC_OFFSET_TABLE_REGNUM
26753 ? ! TARGET_MINIMAL_TOC || TARGET_NO_TOC || get_pool_size () == 0
26754 : true);
26755 }
26756
26757 /* Define the offset between two registers, FROM to be eliminated and its
26758 replacement TO, at the start of a routine. */
26759 HOST_WIDE_INT
26760 rs6000_initial_elimination_offset (int from, int to)
26761 {
26762 rs6000_stack_t *info = rs6000_stack_info ();
26763 HOST_WIDE_INT offset;
26764
26765 if (from == HARD_FRAME_POINTER_REGNUM && to == STACK_POINTER_REGNUM)
26766 offset = info->push_p ? 0 : -info->total_size;
26767 else if (from == FRAME_POINTER_REGNUM && to == STACK_POINTER_REGNUM)
26768 {
26769 offset = info->push_p ? 0 : -info->total_size;
26770 if (FRAME_GROWS_DOWNWARD)
26771 offset += info->fixed_size + info->vars_size + info->parm_size;
26772 }
26773 else if (from == FRAME_POINTER_REGNUM && to == HARD_FRAME_POINTER_REGNUM)
26774 offset = FRAME_GROWS_DOWNWARD
26775 ? info->fixed_size + info->vars_size + info->parm_size
26776 : 0;
26777 else if (from == ARG_POINTER_REGNUM && to == HARD_FRAME_POINTER_REGNUM)
26778 offset = info->total_size;
26779 else if (from == ARG_POINTER_REGNUM && to == STACK_POINTER_REGNUM)
26780 offset = info->push_p ? info->total_size : 0;
26781 else if (from == RS6000_PIC_OFFSET_TABLE_REGNUM)
26782 offset = 0;
26783 else
26784 gcc_unreachable ();
26785
26786 return offset;
26787 }
26788
26789 static rtx
26790 rs6000_dwarf_register_span (rtx reg)
26791 {
26792 rtx parts[8];
26793 int i, words;
26794 unsigned regno = REGNO (reg);
26795 enum machine_mode mode = GET_MODE (reg);
26796
26797 if (TARGET_SPE
26798 && regno < 32
26799 && (SPE_VECTOR_MODE (GET_MODE (reg))
26800 || (TARGET_E500_DOUBLE && FLOAT_MODE_P (mode)
26801 && mode != SFmode && mode != SDmode && mode != SCmode)))
26802 ;
26803 else
26804 return NULL_RTX;
26805
26806 regno = REGNO (reg);
26807
26808 /* The duality of the SPE register size wreaks all kinds of havoc.
26809 This is a way of distinguishing r0 in 32-bits from r0 in
26810 64-bits. */
26811 words = (GET_MODE_SIZE (mode) + UNITS_PER_FP_WORD - 1) / UNITS_PER_FP_WORD;
26812 gcc_assert (words <= 4);
26813 for (i = 0; i < words; i++, regno++)
26814 {
26815 if (BYTES_BIG_ENDIAN)
26816 {
26817 parts[2 * i] = gen_rtx_REG (SImode, regno + 1200);
26818 parts[2 * i + 1] = gen_rtx_REG (SImode, regno);
26819 }
26820 else
26821 {
26822 parts[2 * i] = gen_rtx_REG (SImode, regno);
26823 parts[2 * i + 1] = gen_rtx_REG (SImode, regno + 1200);
26824 }
26825 }
26826
26827 return gen_rtx_PARALLEL (VOIDmode, gen_rtvec_v (words * 2, parts));
26828 }
26829
26830 /* Fill in sizes for SPE register high parts in table used by unwinder. */
26831
26832 static void
26833 rs6000_init_dwarf_reg_sizes_extra (tree address)
26834 {
26835 if (TARGET_SPE)
26836 {
26837 int i;
26838 enum machine_mode mode = TYPE_MODE (char_type_node);
26839 rtx addr = expand_expr (address, NULL_RTX, VOIDmode, EXPAND_NORMAL);
26840 rtx mem = gen_rtx_MEM (BLKmode, addr);
26841 rtx value = gen_int_mode (4, mode);
26842
26843 for (i = 1201; i < 1232; i++)
26844 {
26845 int column = DWARF_REG_TO_UNWIND_COLUMN (i);
26846 HOST_WIDE_INT offset
26847 = DWARF_FRAME_REGNUM (column) * GET_MODE_SIZE (mode);
26848
26849 emit_move_insn (adjust_address (mem, mode, offset), value);
26850 }
26851 }
26852 }
26853
26854 /* Map internal gcc register numbers to DWARF2 register numbers. */
26855
26856 unsigned int
26857 rs6000_dbx_register_number (unsigned int regno)
26858 {
26859 if (regno <= 63 || write_symbols != DWARF2_DEBUG)
26860 return regno;
26861 if (regno == MQ_REGNO)
26862 return 100;
26863 if (regno == LR_REGNO)
26864 return 108;
26865 if (regno == CTR_REGNO)
26866 return 109;
26867 if (CR_REGNO_P (regno))
26868 return regno - CR0_REGNO + 86;
26869 if (regno == CA_REGNO)
26870 return 101; /* XER */
26871 if (ALTIVEC_REGNO_P (regno))
26872 return regno - FIRST_ALTIVEC_REGNO + 1124;
26873 if (regno == VRSAVE_REGNO)
26874 return 356;
26875 if (regno == VSCR_REGNO)
26876 return 67;
26877 if (regno == SPE_ACC_REGNO)
26878 return 99;
26879 if (regno == SPEFSCR_REGNO)
26880 return 612;
26881 /* SPE high reg number. We get these values of regno from
26882 rs6000_dwarf_register_span. */
26883 gcc_assert (regno >= 1200 && regno < 1232);
26884 return regno;
26885 }
26886
26887 /* target hook eh_return_filter_mode */
26888 static enum machine_mode
26889 rs6000_eh_return_filter_mode (void)
26890 {
26891 return TARGET_32BIT ? SImode : word_mode;
26892 }
26893
26894 /* Target hook for scalar_mode_supported_p. */
26895 static bool
26896 rs6000_scalar_mode_supported_p (enum machine_mode mode)
26897 {
26898 if (DECIMAL_FLOAT_MODE_P (mode))
26899 return default_decimal_float_supported_p ();
26900 else
26901 return default_scalar_mode_supported_p (mode);
26902 }
26903
26904 /* Target hook for vector_mode_supported_p. */
26905 static bool
26906 rs6000_vector_mode_supported_p (enum machine_mode mode)
26907 {
26908
26909 if (TARGET_PAIRED_FLOAT && PAIRED_VECTOR_MODE (mode))
26910 return true;
26911
26912 if (TARGET_SPE && SPE_VECTOR_MODE (mode))
26913 return true;
26914
26915 else if (VECTOR_MEM_ALTIVEC_OR_VSX_P (mode))
26916 return true;
26917
26918 else
26919 return false;
26920 }
26921
26922 /* Target hook for invalid_arg_for_unprototyped_fn. */
26923 static const char *
26924 invalid_arg_for_unprototyped_fn (const_tree typelist, const_tree funcdecl, const_tree val)
26925 {
26926 return (!rs6000_darwin64_abi
26927 && typelist == 0
26928 && TREE_CODE (TREE_TYPE (val)) == VECTOR_TYPE
26929 && (funcdecl == NULL_TREE
26930 || (TREE_CODE (funcdecl) == FUNCTION_DECL
26931 && DECL_BUILT_IN_CLASS (funcdecl) != BUILT_IN_MD)))
26932 ? N_("AltiVec argument passed to unprototyped function")
26933 : NULL;
26934 }
26935
26936 /* For TARGET_SECURE_PLT 32-bit PIC code we can save PIC register
26937 setup by using __stack_chk_fail_local hidden function instead of
26938 calling __stack_chk_fail directly. Otherwise it is better to call
26939 __stack_chk_fail directly. */
26940
26941 static tree
26942 rs6000_stack_protect_fail (void)
26943 {
26944 return (DEFAULT_ABI == ABI_V4 && TARGET_SECURE_PLT && flag_pic)
26945 ? default_hidden_stack_protect_fail ()
26946 : default_external_stack_protect_fail ();
26947 }
26948
26949 void
26950 rs6000_final_prescan_insn (rtx insn, rtx *operand ATTRIBUTE_UNUSED,
26951 int num_operands ATTRIBUTE_UNUSED)
26952 {
26953 if (rs6000_warn_cell_microcode)
26954 {
26955 const char *temp;
26956 int insn_code_number = recog_memoized (insn);
26957 location_t location = locator_location (INSN_LOCATOR (insn));
26958
26959 /* Punt on insns we cannot recognize. */
26960 if (insn_code_number < 0)
26961 return;
26962
26963 temp = get_insn_template (insn_code_number, insn);
26964
26965 if (get_attr_cell_micro (insn) == CELL_MICRO_ALWAYS)
26966 warning_at (location, OPT_mwarn_cell_microcode,
26967 "emitting microcode insn %s\t[%s] #%d",
26968 temp, insn_data[INSN_CODE (insn)].name, INSN_UID (insn));
26969 else if (get_attr_cell_micro (insn) == CELL_MICRO_CONDITIONAL)
26970 warning_at (location, OPT_mwarn_cell_microcode,
26971 "emitting conditional microcode insn %s\t[%s] #%d",
26972 temp, insn_data[INSN_CODE (insn)].name, INSN_UID (insn));
26973 }
26974 }
26975
26976 \f
26977 /* Allocate a stack temp and fixup the address so it meets the particular
26978 memory requirements (either offetable or REG+REG addressing). */
26979
26980 rtx
26981 rs6000_allocate_stack_temp (enum machine_mode mode,
26982 bool offsettable_p,
26983 bool reg_reg_p)
26984 {
26985 rtx stack = assign_stack_temp (mode, GET_MODE_SIZE (mode), 0);
26986 rtx addr = XEXP (stack, 0);
26987 int strict_p = (reload_in_progress || reload_completed);
26988
26989 if (!legitimate_indirect_address_p (addr, strict_p))
26990 {
26991 if (offsettable_p
26992 && !rs6000_legitimate_offset_address_p (mode, addr, strict_p))
26993 stack = replace_equiv_address (stack, copy_addr_to_reg (addr));
26994
26995 else if (reg_reg_p && !legitimate_indexed_address_p (addr, strict_p))
26996 stack = replace_equiv_address (stack, copy_addr_to_reg (addr));
26997 }
26998
26999 return stack;
27000 }
27001
27002 /* Given a memory reference, if it is not a reg or reg+reg addressing, convert
27003 to such a form to deal with memory reference instructions like STFIWX that
27004 only take reg+reg addressing. */
27005
27006 rtx
27007 rs6000_address_for_fpconvert (rtx x)
27008 {
27009 int strict_p = (reload_in_progress || reload_completed);
27010 rtx addr;
27011
27012 gcc_assert (MEM_P (x));
27013 addr = XEXP (x, 0);
27014 if (! legitimate_indirect_address_p (addr, strict_p)
27015 && ! legitimate_indexed_address_p (addr, strict_p))
27016 x = replace_equiv_address (x, copy_addr_to_reg (addr));
27017
27018 return x;
27019 }
27020
27021 /* Expand 32-bit int -> floating point conversions. Return true if
27022 successful. */
27023
27024 void
27025 rs6000_expand_convert_si_to_sfdf (rtx dest, rtx src, bool unsigned_p)
27026 {
27027 enum machine_mode dmode = GET_MODE (dest);
27028 rtx (*func_si) (rtx, rtx, rtx, rtx);
27029 rtx (*func_si_mem) (rtx, rtx);
27030 rtx (*func_di) (rtx, rtx);
27031 rtx reg, stack;
27032
27033 gcc_assert (GET_MODE (src) == SImode);
27034
27035 if (dmode == SFmode)
27036 {
27037 if (unsigned_p)
27038 {
27039 gcc_assert (TARGET_FCFIDUS && TARGET_LFIWZX);
27040 func_si = gen_floatunssisf2_lfiwzx;
27041 func_si_mem = gen_floatunssisf2_lfiwzx_mem;
27042 func_di = gen_floatunsdisf2;
27043 }
27044 else
27045 {
27046 gcc_assert (TARGET_FCFIDS && TARGET_LFIWAX);
27047 func_si = gen_floatsisf2_lfiwax;
27048 func_si_mem = gen_floatsisf2_lfiwax_mem;
27049 func_di = gen_floatdisf2;
27050 }
27051 }
27052
27053 else if (dmode == DFmode)
27054 {
27055 if (unsigned_p)
27056 {
27057 gcc_assert (TARGET_FCFIDU && TARGET_LFIWZX);
27058 func_si = gen_floatunssidf2_lfiwzx;
27059 func_si_mem = gen_floatunssidf2_lfiwzx_mem;
27060 func_di = gen_floatunsdidf2;
27061 }
27062 else
27063 {
27064 gcc_assert (TARGET_FCFID && TARGET_LFIWAX);
27065 func_si = gen_floatsidf2_lfiwax;
27066 func_si_mem = gen_floatsidf2_lfiwax_mem;
27067 func_di = gen_floatdidf2;
27068 }
27069 }
27070
27071 else
27072 gcc_unreachable ();
27073
27074 if (MEM_P (src))
27075 {
27076 src = rs6000_address_for_fpconvert (src);
27077 emit_insn (func_si_mem (dest, src));
27078 }
27079 else if (!TARGET_MFPGPR)
27080 {
27081 reg = gen_reg_rtx (DImode);
27082 stack = rs6000_allocate_stack_temp (SImode, false, true);
27083 emit_insn (func_si (dest, src, stack, reg));
27084 }
27085 else
27086 {
27087 if (!REG_P (src))
27088 src = force_reg (SImode, src);
27089 reg = convert_to_mode (DImode, src, unsigned_p);
27090 emit_insn (func_di (dest, reg));
27091 }
27092 }
27093
27094 #include "gt-rs6000.h"