1 ;; Machine description for SPARC chip for GCC
2 ;; Copyright (C) 1987, 1988, 1989, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
3 ;; 1999, 2000, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
4 ;; Contributed by Michael Tiemann (tiemann@cygnus.com)
5 ;; 64-bit SPARC-V9 support by Michael Tiemann, Jim Wilson, and Doug Evans,
8 ;; This file is part of GCC.
10 ;; GCC is free software; you can redistribute it and/or modify
11 ;; it under the terms of the GNU General Public License as published by
12 ;; the Free Software Foundation; either version 2, or (at your option)
15 ;; GCC is distributed in the hope that it will be useful,
16 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
17 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 ;; GNU General Public License for more details.
20 ;; You should have received a copy of the GNU General Public License
21 ;; along with GCC; see the file COPYING. If not, write to
22 ;; the Free Software Foundation, 59 Temple Place - Suite 330,
23 ;; Boston, MA 02111-1307, USA.
25 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
29 (UNSPEC_UPDATE_RETURN 1)
30 (UNSPEC_LOAD_PCREL_SYM 2)
31 (UNSPEC_MOVE_PIC_LABEL 5)
37 (UNSPEC_EMB_TEXTUHI 13)
38 (UNSPEC_EMB_TEXTHI 14)
39 (UNSPEC_EMB_TEXTULO 15)
47 (UNSPEC_TLSLD_BASE 35)
59 ;; The upper 32 fp regs on the v9 can't hold SFmode values. To deal with this
60 ;; a second register class, EXTRA_FP_REGS, exists for the v9 chip. The name
61 ;; is a bit of a misnomer as it covers all 64 fp regs. The corresponding
62 ;; constraint letter is 'e'. To avoid any confusion, 'e' is used instead of
63 ;; 'f' for all DF/TFmode values, including those that are specific to the v8.
65 ;; Attribute for cpu type.
66 ;; These must match the values for enum processor_type in sparc.h.
73 hypersparc,sparclite86x,
78 (const (symbol_ref "sparc_cpu_attr")))
80 ;; Attribute for the instruction set.
81 ;; At present we only need to distinguish v9/!v9, but for clarity we
82 ;; test TARGET_V8 too.
83 (define_attr "isa" "v7,v8,v9,sparclet"
85 (cond [(symbol_ref "TARGET_V9") (const_string "v9")
86 (symbol_ref "TARGET_V8") (const_string "v8")
87 (symbol_ref "TARGET_SPARCLET") (const_string "sparclet")]
88 (const_string "v7"))))
94 uncond_branch,branch,call,sibcall,call_no_delay_slot,return,
102 fga,fgm_pack,fgm_mul,fgm_pdist,fgm_cmp,
105 multi,savew,flushw,iflush,trap"
106 (const_string "ialu"))
108 ;; True if branch/call has empty delay slot and will emit a nop in it
109 (define_attr "empty_delay_slot" "false,true"
110 (symbol_ref "empty_delay_slot (insn)"))
112 (define_attr "branch_type" "none,icc,fcc,reg"
113 (const_string "none"))
115 (define_attr "pic" "false,true"
116 (symbol_ref "flag_pic != 0"))
118 (define_attr "calls_alloca" "false,true"
119 (symbol_ref "current_function_calls_alloca != 0"))
121 (define_attr "calls_eh_return" "false,true"
122 (symbol_ref "current_function_calls_eh_return !=0 "))
124 (define_attr "leaf_function" "false,true"
125 (symbol_ref "current_function_uses_only_leaf_regs != 0"))
127 (define_attr "delayed_branch" "false,true"
128 (symbol_ref "flag_delayed_branch != 0"))
130 ;; Length (in # of insns).
131 ;; Beware that setting a length greater or equal to 3 for conditional branches
132 ;; has a side-effect (see output_cbranch and output_v9branch).
133 (define_attr "length" ""
134 (cond [(eq_attr "type" "uncond_branch,call")
135 (if_then_else (eq_attr "empty_delay_slot" "true")
138 (eq_attr "type" "sibcall")
139 (if_then_else (eq_attr "leaf_function" "true")
140 (if_then_else (eq_attr "empty_delay_slot" "true")
143 (if_then_else (eq_attr "empty_delay_slot" "true")
146 (eq_attr "branch_type" "icc")
147 (if_then_else (match_operand 0 "noov_compare64_op" "")
148 (if_then_else (lt (pc) (match_dup 1))
149 (if_then_else (lt (minus (match_dup 1) (pc)) (const_int 260000))
150 (if_then_else (eq_attr "empty_delay_slot" "true")
153 (if_then_else (eq_attr "empty_delay_slot" "true")
156 (if_then_else (lt (minus (pc) (match_dup 1)) (const_int 260000))
157 (if_then_else (eq_attr "empty_delay_slot" "true")
160 (if_then_else (eq_attr "empty_delay_slot" "true")
163 (if_then_else (eq_attr "empty_delay_slot" "true")
166 (eq_attr "branch_type" "fcc")
167 (if_then_else (match_operand 0 "fcc0_reg_operand" "")
168 (if_then_else (eq_attr "empty_delay_slot" "true")
169 (if_then_else (eq (symbol_ref "TARGET_V9") (const_int 0))
172 (if_then_else (eq (symbol_ref "TARGET_V9") (const_int 0))
175 (if_then_else (lt (pc) (match_dup 2))
176 (if_then_else (lt (minus (match_dup 2) (pc)) (const_int 260000))
177 (if_then_else (eq_attr "empty_delay_slot" "true")
180 (if_then_else (eq_attr "empty_delay_slot" "true")
183 (if_then_else (lt (minus (pc) (match_dup 2)) (const_int 260000))
184 (if_then_else (eq_attr "empty_delay_slot" "true")
187 (if_then_else (eq_attr "empty_delay_slot" "true")
190 (eq_attr "branch_type" "reg")
191 (if_then_else (lt (pc) (match_dup 2))
192 (if_then_else (lt (minus (match_dup 2) (pc)) (const_int 32000))
193 (if_then_else (eq_attr "empty_delay_slot" "true")
196 (if_then_else (eq_attr "empty_delay_slot" "true")
199 (if_then_else (lt (minus (pc) (match_dup 2)) (const_int 32000))
200 (if_then_else (eq_attr "empty_delay_slot" "true")
203 (if_then_else (eq_attr "empty_delay_slot" "true")
209 (define_attr "fptype" "single,double"
210 (const_string "single"))
212 ;; UltraSPARC-III integer load type.
213 (define_attr "us3load_type" "2cycle,3cycle"
214 (const_string "2cycle"))
216 (define_asm_attributes
217 [(set_attr "length" "2")
218 (set_attr "type" "multi")])
220 ;; Attributes for instruction and branch scheduling
221 (define_attr "tls_call_delay" "false,true"
222 (symbol_ref "tls_call_delay (insn)"))
224 (define_attr "in_call_delay" "false,true"
225 (cond [(eq_attr "type" "uncond_branch,branch,call,sibcall,call_no_delay_slot,multi")
226 (const_string "false")
227 (eq_attr "type" "load,fpload,store,fpstore")
228 (if_then_else (eq_attr "length" "1")
229 (const_string "true")
230 (const_string "false"))]
231 (if_then_else (and (eq_attr "length" "1")
232 (eq_attr "tls_call_delay" "true"))
233 (const_string "true")
234 (const_string "false"))))
236 (define_attr "eligible_for_sibcall_delay" "false,true"
237 (symbol_ref "eligible_for_sibcall_delay (insn)"))
239 (define_attr "eligible_for_return_delay" "false,true"
240 (symbol_ref "eligible_for_return_delay (insn)"))
242 ;; ??? !v9: Should implement the notion of predelay slots for floating-point
243 ;; branches. This would allow us to remove the nop always inserted before
244 ;; a floating point branch.
246 ;; ??? It is OK for fill_simple_delay_slots to put load/store instructions
247 ;; in a delay slot, but it is not OK for fill_eager_delay_slots to do so.
248 ;; This is because doing so will add several pipeline stalls to the path
249 ;; that the load/store did not come from. Unfortunately, there is no way
250 ;; to prevent fill_eager_delay_slots from using load/store without completely
251 ;; disabling them. For the SPEC benchmark set, this is a serious lose,
252 ;; because it prevents us from moving back the final store of inner loops.
254 (define_attr "in_branch_delay" "false,true"
255 (if_then_else (and (eq_attr "type" "!uncond_branch,branch,call,sibcall,call_no_delay_slot,multi")
256 (eq_attr "length" "1"))
257 (const_string "true")
258 (const_string "false")))
260 (define_attr "in_uncond_branch_delay" "false,true"
261 (if_then_else (and (eq_attr "type" "!uncond_branch,branch,call,sibcall,call_no_delay_slot,multi")
262 (eq_attr "length" "1"))
263 (const_string "true")
264 (const_string "false")))
266 (define_attr "in_annul_branch_delay" "false,true"
267 (if_then_else (and (eq_attr "type" "!uncond_branch,branch,call,sibcall,call_no_delay_slot,multi")
268 (eq_attr "length" "1"))
269 (const_string "true")
270 (const_string "false")))
272 (define_delay (eq_attr "type" "call")
273 [(eq_attr "in_call_delay" "true") (nil) (nil)])
275 (define_delay (eq_attr "type" "sibcall")
276 [(eq_attr "eligible_for_sibcall_delay" "true") (nil) (nil)])
278 (define_delay (eq_attr "type" "branch")
279 [(eq_attr "in_branch_delay" "true")
280 (nil) (eq_attr "in_annul_branch_delay" "true")])
282 (define_delay (eq_attr "type" "uncond_branch")
283 [(eq_attr "in_uncond_branch_delay" "true")
286 (define_delay (eq_attr "type" "return")
287 [(eq_attr "eligible_for_return_delay" "true") (nil) (nil)])
289 ;; Include SPARC DFA schedulers
291 (include "cypress.md")
292 (include "supersparc.md")
293 (include "hypersparc.md")
294 (include "sparclet.md")
295 (include "ultra1_2.md")
296 (include "ultra3.md")
299 ;; Compare instructions.
300 ;; This controls RTL generation and register allocation.
302 ;; We generate RTL for comparisons and branches by having the cmpxx
303 ;; patterns store away the operands. Then, the scc and bcc patterns
304 ;; emit RTL for both the compare and the branch.
306 ;; We do this because we want to generate different code for an sne and
307 ;; seq insn. In those cases, if the second operand of the compare is not
308 ;; const0_rtx, we want to compute the xor of the two operands and test
311 ;; We start with the DEFINE_EXPANDs, then the DEFINE_INSNs to match
312 ;; the patterns. Finally, we have the DEFINE_SPLITs for some of the scc
313 ;; insns that actually require more than one machine instruction.
315 ;; Put cmpsi first among compare insns so it matches two CONST_INT operands.
317 (define_expand "cmpsi"
319 (compare:CC (match_operand:SI 0 "compare_operand" "")
320 (match_operand:SI 1 "arith_operand" "")))]
323 if (GET_CODE (operands[0]) == ZERO_EXTRACT && operands[1] != const0_rtx)
324 operands[0] = force_reg (SImode, operands[0]);
326 sparc_compare_op0 = operands[0];
327 sparc_compare_op1 = operands[1];
331 (define_expand "cmpdi"
333 (compare:CCX (match_operand:DI 0 "compare_operand" "")
334 (match_operand:DI 1 "arith_double_operand" "")))]
337 if (GET_CODE (operands[0]) == ZERO_EXTRACT && operands[1] != const0_rtx)
338 operands[0] = force_reg (DImode, operands[0]);
340 sparc_compare_op0 = operands[0];
341 sparc_compare_op1 = operands[1];
345 (define_expand "cmpsf"
346 ;; The 96 here isn't ever used by anyone.
348 (compare:CCFP (match_operand:SF 0 "register_operand" "")
349 (match_operand:SF 1 "register_operand" "")))]
352 sparc_compare_op0 = operands[0];
353 sparc_compare_op1 = operands[1];
357 (define_expand "cmpdf"
358 ;; The 96 here isn't ever used by anyone.
360 (compare:CCFP (match_operand:DF 0 "register_operand" "")
361 (match_operand:DF 1 "register_operand" "")))]
364 sparc_compare_op0 = operands[0];
365 sparc_compare_op1 = operands[1];
369 (define_expand "cmptf"
370 ;; The 96 here isn't ever used by anyone.
372 (compare:CCFP (match_operand:TF 0 "register_operand" "")
373 (match_operand:TF 1 "register_operand" "")))]
376 sparc_compare_op0 = operands[0];
377 sparc_compare_op1 = operands[1];
381 ;; Now the compare DEFINE_INSNs.
383 (define_insn "*cmpsi_insn"
385 (compare:CC (match_operand:SI 0 "register_operand" "r")
386 (match_operand:SI 1 "arith_operand" "rI")))]
389 [(set_attr "type" "compare")])
391 (define_insn "*cmpdi_sp64"
393 (compare:CCX (match_operand:DI 0 "register_operand" "r")
394 (match_operand:DI 1 "arith_double_operand" "rHI")))]
397 [(set_attr "type" "compare")])
399 (define_insn "*cmpsf_fpe"
400 [(set (match_operand:CCFPE 0 "fcc_reg_operand" "=c")
401 (compare:CCFPE (match_operand:SF 1 "register_operand" "f")
402 (match_operand:SF 2 "register_operand" "f")))]
406 return "fcmpes\t%0, %1, %2";
407 return "fcmpes\t%1, %2";
409 [(set_attr "type" "fpcmp")])
411 (define_insn "*cmpdf_fpe"
412 [(set (match_operand:CCFPE 0 "fcc_reg_operand" "=c")
413 (compare:CCFPE (match_operand:DF 1 "register_operand" "e")
414 (match_operand:DF 2 "register_operand" "e")))]
418 return "fcmped\t%0, %1, %2";
419 return "fcmped\t%1, %2";
421 [(set_attr "type" "fpcmp")
422 (set_attr "fptype" "double")])
424 (define_insn "*cmptf_fpe"
425 [(set (match_operand:CCFPE 0 "fcc_reg_operand" "=c")
426 (compare:CCFPE (match_operand:TF 1 "register_operand" "e")
427 (match_operand:TF 2 "register_operand" "e")))]
428 "TARGET_FPU && TARGET_HARD_QUAD"
431 return "fcmpeq\t%0, %1, %2";
432 return "fcmpeq\t%1, %2";
434 [(set_attr "type" "fpcmp")])
436 (define_insn "*cmpsf_fp"
437 [(set (match_operand:CCFP 0 "fcc_reg_operand" "=c")
438 (compare:CCFP (match_operand:SF 1 "register_operand" "f")
439 (match_operand:SF 2 "register_operand" "f")))]
443 return "fcmps\t%0, %1, %2";
444 return "fcmps\t%1, %2";
446 [(set_attr "type" "fpcmp")])
448 (define_insn "*cmpdf_fp"
449 [(set (match_operand:CCFP 0 "fcc_reg_operand" "=c")
450 (compare:CCFP (match_operand:DF 1 "register_operand" "e")
451 (match_operand:DF 2 "register_operand" "e")))]
455 return "fcmpd\t%0, %1, %2";
456 return "fcmpd\t%1, %2";
458 [(set_attr "type" "fpcmp")
459 (set_attr "fptype" "double")])
461 (define_insn "*cmptf_fp"
462 [(set (match_operand:CCFP 0 "fcc_reg_operand" "=c")
463 (compare:CCFP (match_operand:TF 1 "register_operand" "e")
464 (match_operand:TF 2 "register_operand" "e")))]
465 "TARGET_FPU && TARGET_HARD_QUAD"
468 return "fcmpq\t%0, %1, %2";
469 return "fcmpq\t%1, %2";
471 [(set_attr "type" "fpcmp")])
473 ;; Next come the scc insns. For seq, sne, sgeu, and sltu, we can do this
474 ;; without jumps using the addx/subx instructions. For seq/sne on v9 we use
475 ;; the same code as v8 (the addx/subx method has more applications). The
476 ;; exception to this is "reg != 0" which can be done in one instruction on v9
477 ;; (so we do it). For the rest, on v9 we use conditional moves; on v8, we do
480 ;; Seq_special[_xxx] and sne_special[_xxx] clobber the CC reg, because they
481 ;; generate addcc/subcc instructions.
483 (define_expand "seqsi_special"
485 (xor:SI (match_operand:SI 1 "register_operand" "")
486 (match_operand:SI 2 "register_operand" "")))
487 (parallel [(set (match_operand:SI 0 "register_operand" "")
488 (eq:SI (match_dup 3) (const_int 0)))
489 (clobber (reg:CC 100))])]
491 { operands[3] = gen_reg_rtx (SImode); })
493 (define_expand "seqdi_special"
495 (xor:DI (match_operand:DI 1 "register_operand" "")
496 (match_operand:DI 2 "register_operand" "")))
497 (set (match_operand:DI 0 "register_operand" "")
498 (eq:DI (match_dup 3) (const_int 0)))]
500 { operands[3] = gen_reg_rtx (DImode); })
502 (define_expand "snesi_special"
504 (xor:SI (match_operand:SI 1 "register_operand" "")
505 (match_operand:SI 2 "register_operand" "")))
506 (parallel [(set (match_operand:SI 0 "register_operand" "")
507 (ne:SI (match_dup 3) (const_int 0)))
508 (clobber (reg:CC 100))])]
510 { operands[3] = gen_reg_rtx (SImode); })
512 (define_expand "snedi_special"
514 (xor:DI (match_operand:DI 1 "register_operand" "")
515 (match_operand:DI 2 "register_operand" "")))
516 (set (match_operand:DI 0 "register_operand" "")
517 (ne:DI (match_dup 3) (const_int 0)))]
519 { operands[3] = gen_reg_rtx (DImode); })
521 (define_expand "seqdi_special_trunc"
523 (xor:DI (match_operand:DI 1 "register_operand" "")
524 (match_operand:DI 2 "register_operand" "")))
525 (set (match_operand:SI 0 "register_operand" "")
526 (eq:SI (match_dup 3) (const_int 0)))]
528 { operands[3] = gen_reg_rtx (DImode); })
530 (define_expand "snedi_special_trunc"
532 (xor:DI (match_operand:DI 1 "register_operand" "")
533 (match_operand:DI 2 "register_operand" "")))
534 (set (match_operand:SI 0 "register_operand" "")
535 (ne:SI (match_dup 3) (const_int 0)))]
537 { operands[3] = gen_reg_rtx (DImode); })
539 (define_expand "seqsi_special_extend"
541 (xor:SI (match_operand:SI 1 "register_operand" "")
542 (match_operand:SI 2 "register_operand" "")))
543 (parallel [(set (match_operand:DI 0 "register_operand" "")
544 (eq:DI (match_dup 3) (const_int 0)))
545 (clobber (reg:CC 100))])]
547 { operands[3] = gen_reg_rtx (SImode); })
549 (define_expand "snesi_special_extend"
551 (xor:SI (match_operand:SI 1 "register_operand" "")
552 (match_operand:SI 2 "register_operand" "")))
553 (parallel [(set (match_operand:DI 0 "register_operand" "")
554 (ne:DI (match_dup 3) (const_int 0)))
555 (clobber (reg:CC 100))])]
557 { operands[3] = gen_reg_rtx (SImode); })
559 ;; ??? v9: Operand 0 needs a mode, so SImode was chosen.
560 ;; However, the code handles both SImode and DImode.
562 [(set (match_operand:SI 0 "intreg_operand" "")
563 (eq:SI (match_dup 1) (const_int 0)))]
566 if (GET_MODE (sparc_compare_op0) == SImode)
570 if (GET_MODE (operands[0]) == SImode)
571 pat = gen_seqsi_special (operands[0], sparc_compare_op0,
573 else if (! TARGET_ARCH64)
576 pat = gen_seqsi_special_extend (operands[0], sparc_compare_op0,
581 else if (GET_MODE (sparc_compare_op0) == DImode)
587 else if (GET_MODE (operands[0]) == SImode)
588 pat = gen_seqdi_special_trunc (operands[0], sparc_compare_op0,
591 pat = gen_seqdi_special (operands[0], sparc_compare_op0,
596 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
598 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, EQ);
599 emit_jump_insn (gen_sne (operands[0]));
604 if (gen_v9_scc (EQ, operands))
611 ;; ??? v9: Operand 0 needs a mode, so SImode was chosen.
612 ;; However, the code handles both SImode and DImode.
614 [(set (match_operand:SI 0 "intreg_operand" "")
615 (ne:SI (match_dup 1) (const_int 0)))]
618 if (GET_MODE (sparc_compare_op0) == SImode)
622 if (GET_MODE (operands[0]) == SImode)
623 pat = gen_snesi_special (operands[0], sparc_compare_op0,
625 else if (! TARGET_ARCH64)
628 pat = gen_snesi_special_extend (operands[0], sparc_compare_op0,
633 else if (GET_MODE (sparc_compare_op0) == DImode)
639 else if (GET_MODE (operands[0]) == SImode)
640 pat = gen_snedi_special_trunc (operands[0], sparc_compare_op0,
643 pat = gen_snedi_special (operands[0], sparc_compare_op0,
648 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
650 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, NE);
651 emit_jump_insn (gen_sne (operands[0]));
656 if (gen_v9_scc (NE, operands))
664 [(set (match_operand:SI 0 "intreg_operand" "")
665 (gt:SI (match_dup 1) (const_int 0)))]
668 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
670 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, GT);
671 emit_jump_insn (gen_sne (operands[0]));
676 if (gen_v9_scc (GT, operands))
684 [(set (match_operand:SI 0 "intreg_operand" "")
685 (lt:SI (match_dup 1) (const_int 0)))]
688 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
690 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, LT);
691 emit_jump_insn (gen_sne (operands[0]));
696 if (gen_v9_scc (LT, operands))
704 [(set (match_operand:SI 0 "intreg_operand" "")
705 (ge:SI (match_dup 1) (const_int 0)))]
708 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
710 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, GE);
711 emit_jump_insn (gen_sne (operands[0]));
716 if (gen_v9_scc (GE, operands))
724 [(set (match_operand:SI 0 "intreg_operand" "")
725 (le:SI (match_dup 1) (const_int 0)))]
728 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
730 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, LE);
731 emit_jump_insn (gen_sne (operands[0]));
736 if (gen_v9_scc (LE, operands))
743 (define_expand "sgtu"
744 [(set (match_operand:SI 0 "intreg_operand" "")
745 (gtu:SI (match_dup 1) (const_int 0)))]
752 /* We can do ltu easily, so if both operands are registers, swap them and
754 if ((GET_CODE (sparc_compare_op0) == REG
755 || GET_CODE (sparc_compare_op0) == SUBREG)
756 && (GET_CODE (sparc_compare_op1) == REG
757 || GET_CODE (sparc_compare_op1) == SUBREG))
759 tem = sparc_compare_op0;
760 sparc_compare_op0 = sparc_compare_op1;
761 sparc_compare_op1 = tem;
762 pat = gen_sltu (operands[0]);
771 if (gen_v9_scc (GTU, operands))
777 (define_expand "sltu"
778 [(set (match_operand:SI 0 "intreg_operand" "")
779 (ltu:SI (match_dup 1) (const_int 0)))]
784 if (gen_v9_scc (LTU, operands))
787 operands[1] = gen_compare_reg (LTU, sparc_compare_op0, sparc_compare_op1);
790 (define_expand "sgeu"
791 [(set (match_operand:SI 0 "intreg_operand" "")
792 (geu:SI (match_dup 1) (const_int 0)))]
797 if (gen_v9_scc (GEU, operands))
800 operands[1] = gen_compare_reg (GEU, sparc_compare_op0, sparc_compare_op1);
803 (define_expand "sleu"
804 [(set (match_operand:SI 0 "intreg_operand" "")
805 (leu:SI (match_dup 1) (const_int 0)))]
812 /* We can do geu easily, so if both operands are registers, swap them and
814 if ((GET_CODE (sparc_compare_op0) == REG
815 || GET_CODE (sparc_compare_op0) == SUBREG)
816 && (GET_CODE (sparc_compare_op1) == REG
817 || GET_CODE (sparc_compare_op1) == SUBREG))
819 tem = sparc_compare_op0;
820 sparc_compare_op0 = sparc_compare_op1;
821 sparc_compare_op1 = tem;
822 pat = gen_sgeu (operands[0]);
831 if (gen_v9_scc (LEU, operands))
837 ;; Now the DEFINE_INSNs for the scc cases.
839 ;; The SEQ and SNE patterns are special because they can be done
840 ;; without any branching and do not involve a COMPARE. We want
841 ;; them to always use the splitz below so the results can be
844 (define_insn_and_split "*snesi_zero"
845 [(set (match_operand:SI 0 "register_operand" "=r")
846 (ne:SI (match_operand:SI 1 "register_operand" "r")
848 (clobber (reg:CC 100))]
852 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
854 (set (match_dup 0) (ltu:SI (reg:CC 100) (const_int 0)))]
856 [(set_attr "length" "2")])
858 (define_insn_and_split "*neg_snesi_zero"
859 [(set (match_operand:SI 0 "register_operand" "=r")
860 (neg:SI (ne:SI (match_operand:SI 1 "register_operand" "r")
862 (clobber (reg:CC 100))]
866 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
868 (set (match_dup 0) (neg:SI (ltu:SI (reg:CC 100) (const_int 0))))]
870 [(set_attr "length" "2")])
872 (define_insn_and_split "*snesi_zero_extend"
873 [(set (match_operand:DI 0 "register_operand" "=r")
874 (ne:DI (match_operand:SI 1 "register_operand" "r")
876 (clobber (reg:CC 100))]
880 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (minus:SI (const_int 0)
883 (set (match_dup 0) (zero_extend:DI (plus:SI (plus:SI (const_int 0)
885 (ltu:SI (reg:CC_NOOV 100)
888 [(set_attr "length" "2")])
890 (define_insn_and_split "*snedi_zero"
891 [(set (match_operand:DI 0 "register_operand" "=&r")
892 (ne:DI (match_operand:DI 1 "register_operand" "r")
896 "&& ! reg_overlap_mentioned_p (operands[1], operands[0])"
897 [(set (match_dup 0) (const_int 0))
898 (set (match_dup 0) (if_then_else:DI (ne:DI (match_dup 1)
903 [(set_attr "length" "2")])
905 (define_insn_and_split "*neg_snedi_zero"
906 [(set (match_operand:DI 0 "register_operand" "=&r")
907 (neg:DI (ne:DI (match_operand:DI 1 "register_operand" "r")
911 "&& ! reg_overlap_mentioned_p (operands[1], operands[0])"
912 [(set (match_dup 0) (const_int 0))
913 (set (match_dup 0) (if_then_else:DI (ne:DI (match_dup 1)
918 [(set_attr "length" "2")])
920 (define_insn_and_split "*snedi_zero_trunc"
921 [(set (match_operand:SI 0 "register_operand" "=&r")
922 (ne:SI (match_operand:DI 1 "register_operand" "r")
926 "&& ! reg_overlap_mentioned_p (operands[1], operands[0])"
927 [(set (match_dup 0) (const_int 0))
928 (set (match_dup 0) (if_then_else:SI (ne:DI (match_dup 1)
933 [(set_attr "length" "2")])
935 (define_insn_and_split "*seqsi_zero"
936 [(set (match_operand:SI 0 "register_operand" "=r")
937 (eq:SI (match_operand:SI 1 "register_operand" "r")
939 (clobber (reg:CC 100))]
943 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
945 (set (match_dup 0) (geu:SI (reg:CC 100) (const_int 0)))]
947 [(set_attr "length" "2")])
949 (define_insn_and_split "*neg_seqsi_zero"
950 [(set (match_operand:SI 0 "register_operand" "=r")
951 (neg:SI (eq:SI (match_operand:SI 1 "register_operand" "r")
953 (clobber (reg:CC 100))]
957 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
959 (set (match_dup 0) (neg:SI (geu:SI (reg:CC 100) (const_int 0))))]
961 [(set_attr "length" "2")])
963 (define_insn_and_split "*seqsi_zero_extend"
964 [(set (match_operand:DI 0 "register_operand" "=r")
965 (eq:DI (match_operand:SI 1 "register_operand" "r")
967 (clobber (reg:CC 100))]
971 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (minus:SI (const_int 0)
974 (set (match_dup 0) (zero_extend:DI (minus:SI (minus:SI (const_int 0)
976 (ltu:SI (reg:CC_NOOV 100)
979 [(set_attr "length" "2")])
981 (define_insn_and_split "*seqdi_zero"
982 [(set (match_operand:DI 0 "register_operand" "=&r")
983 (eq:DI (match_operand:DI 1 "register_operand" "r")
987 "&& ! reg_overlap_mentioned_p (operands[1], operands[0])"
988 [(set (match_dup 0) (const_int 0))
989 (set (match_dup 0) (if_then_else:DI (eq:DI (match_dup 1)
994 [(set_attr "length" "2")])
996 (define_insn_and_split "*neg_seqdi_zero"
997 [(set (match_operand:DI 0 "register_operand" "=&r")
998 (neg:DI (eq:DI (match_operand:DI 1 "register_operand" "r")
1002 "&& ! reg_overlap_mentioned_p (operands[1], operands[0])"
1003 [(set (match_dup 0) (const_int 0))
1004 (set (match_dup 0) (if_then_else:DI (eq:DI (match_dup 1)
1009 [(set_attr "length" "2")])
1011 (define_insn_and_split "*seqdi_zero_trunc"
1012 [(set (match_operand:SI 0 "register_operand" "=&r")
1013 (eq:SI (match_operand:DI 1 "register_operand" "r")
1017 "&& ! reg_overlap_mentioned_p (operands[1], operands[0])"
1018 [(set (match_dup 0) (const_int 0))
1019 (set (match_dup 0) (if_then_else:SI (eq:DI (match_dup 1)
1024 [(set_attr "length" "2")])
1026 ;; We can also do (x + (i == 0)) and related, so put them in.
1027 ;; ??? The addx/subx insns use the 32 bit carry flag so there are no DImode
1030 (define_insn_and_split "*x_plus_i_ne_0"
1031 [(set (match_operand:SI 0 "register_operand" "=r")
1032 (plus:SI (ne:SI (match_operand:SI 1 "register_operand" "r")
1034 (match_operand:SI 2 "register_operand" "r")))
1035 (clobber (reg:CC 100))]
1039 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
1041 (set (match_dup 0) (plus:SI (ltu:SI (reg:CC 100) (const_int 0))
1044 [(set_attr "length" "2")])
1046 (define_insn_and_split "*x_minus_i_ne_0"
1047 [(set (match_operand:SI 0 "register_operand" "=r")
1048 (minus:SI (match_operand:SI 2 "register_operand" "r")
1049 (ne:SI (match_operand:SI 1 "register_operand" "r")
1051 (clobber (reg:CC 100))]
1055 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
1057 (set (match_dup 0) (minus:SI (match_dup 2)
1058 (ltu:SI (reg:CC 100) (const_int 0))))]
1060 [(set_attr "length" "2")])
1062 (define_insn_and_split "*x_plus_i_eq_0"
1063 [(set (match_operand:SI 0 "register_operand" "=r")
1064 (plus:SI (eq:SI (match_operand:SI 1 "register_operand" "r")
1066 (match_operand:SI 2 "register_operand" "r")))
1067 (clobber (reg:CC 100))]
1071 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
1073 (set (match_dup 0) (plus:SI (geu:SI (reg:CC 100) (const_int 0))
1076 [(set_attr "length" "2")])
1078 (define_insn_and_split "*x_minus_i_eq_0"
1079 [(set (match_operand:SI 0 "register_operand" "=r")
1080 (minus:SI (match_operand:SI 2 "register_operand" "r")
1081 (eq:SI (match_operand:SI 1 "register_operand" "r")
1083 (clobber (reg:CC 100))]
1087 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
1089 (set (match_dup 0) (minus:SI (match_dup 2)
1090 (geu:SI (reg:CC 100) (const_int 0))))]
1092 [(set_attr "length" "2")])
1094 ;; We can also do GEU and LTU directly, but these operate after a compare.
1095 ;; ??? The addx/subx insns use the 32 bit carry flag so there are no DImode
1098 (define_insn "*sltu_insn"
1099 [(set (match_operand:SI 0 "register_operand" "=r")
1100 (ltu:SI (reg:CC 100) (const_int 0)))]
1103 [(set_attr "type" "ialuX")])
1105 (define_insn "*neg_sltu_insn"
1106 [(set (match_operand:SI 0 "register_operand" "=r")
1107 (neg:SI (ltu:SI (reg:CC 100) (const_int 0))))]
1110 [(set_attr "type" "ialuX")])
1112 ;; ??? Combine should canonicalize these next two to the same pattern.
1113 (define_insn "*neg_sltu_minus_x"
1114 [(set (match_operand:SI 0 "register_operand" "=r")
1115 (minus:SI (neg:SI (ltu:SI (reg:CC 100) (const_int 0)))
1116 (match_operand:SI 1 "arith_operand" "rI")))]
1118 "subx\t%%g0, %1, %0"
1119 [(set_attr "type" "ialuX")])
1121 (define_insn "*neg_sltu_plus_x"
1122 [(set (match_operand:SI 0 "register_operand" "=r")
1123 (neg:SI (plus:SI (ltu:SI (reg:CC 100) (const_int 0))
1124 (match_operand:SI 1 "arith_operand" "rI"))))]
1126 "subx\t%%g0, %1, %0"
1127 [(set_attr "type" "ialuX")])
1129 (define_insn "*sgeu_insn"
1130 [(set (match_operand:SI 0 "register_operand" "=r")
1131 (geu:SI (reg:CC 100) (const_int 0)))]
1133 "subx\t%%g0, -1, %0"
1134 [(set_attr "type" "ialuX")])
1136 (define_insn "*neg_sgeu_insn"
1137 [(set (match_operand:SI 0 "register_operand" "=r")
1138 (neg:SI (geu:SI (reg:CC 100) (const_int 0))))]
1140 "addx\t%%g0, -1, %0"
1141 [(set_attr "type" "ialuX")])
1143 ;; We can also do (x + ((unsigned) i >= 0)) and related, so put them in.
1144 ;; ??? The addx/subx insns use the 32 bit carry flag so there are no DImode
1147 (define_insn "*sltu_plus_x"
1148 [(set (match_operand:SI 0 "register_operand" "=r")
1149 (plus:SI (ltu:SI (reg:CC 100) (const_int 0))
1150 (match_operand:SI 1 "arith_operand" "rI")))]
1152 "addx\t%%g0, %1, %0"
1153 [(set_attr "type" "ialuX")])
1155 (define_insn "*sltu_plus_x_plus_y"
1156 [(set (match_operand:SI 0 "register_operand" "=r")
1157 (plus:SI (ltu:SI (reg:CC 100) (const_int 0))
1158 (plus:SI (match_operand:SI 1 "arith_operand" "%r")
1159 (match_operand:SI 2 "arith_operand" "rI"))))]
1162 [(set_attr "type" "ialuX")])
1164 (define_insn "*x_minus_sltu"
1165 [(set (match_operand:SI 0 "register_operand" "=r")
1166 (minus:SI (match_operand:SI 1 "register_operand" "r")
1167 (ltu:SI (reg:CC 100) (const_int 0))))]
1170 [(set_attr "type" "ialuX")])
1172 ;; ??? Combine should canonicalize these next two to the same pattern.
1173 (define_insn "*x_minus_y_minus_sltu"
1174 [(set (match_operand:SI 0 "register_operand" "=r")
1175 (minus:SI (minus:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
1176 (match_operand:SI 2 "arith_operand" "rI"))
1177 (ltu:SI (reg:CC 100) (const_int 0))))]
1180 [(set_attr "type" "ialuX")])
1182 (define_insn "*x_minus_sltu_plus_y"
1183 [(set (match_operand:SI 0 "register_operand" "=r")
1184 (minus:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
1185 (plus:SI (ltu:SI (reg:CC 100) (const_int 0))
1186 (match_operand:SI 2 "arith_operand" "rI"))))]
1189 [(set_attr "type" "ialuX")])
1191 (define_insn "*sgeu_plus_x"
1192 [(set (match_operand:SI 0 "register_operand" "=r")
1193 (plus:SI (geu:SI (reg:CC 100) (const_int 0))
1194 (match_operand:SI 1 "register_operand" "r")))]
1197 [(set_attr "type" "ialuX")])
1199 (define_insn "*x_minus_sgeu"
1200 [(set (match_operand:SI 0 "register_operand" "=r")
1201 (minus:SI (match_operand:SI 1 "register_operand" "r")
1202 (geu:SI (reg:CC 100) (const_int 0))))]
1205 [(set_attr "type" "ialuX")])
1208 [(set (match_operand:SI 0 "register_operand" "")
1209 (match_operator:SI 2 "noov_compare_op"
1210 [(match_operand 1 "icc_or_fcc_reg_operand" "")
1213 && REGNO (operands[1]) == SPARC_ICC_REG
1214 && (GET_MODE (operands[1]) == CCXmode
1215 /* 32 bit LTU/GEU are better implemented using addx/subx. */
1216 || (GET_CODE (operands[2]) != LTU && GET_CODE (operands[2]) != GEU))"
1217 [(set (match_dup 0) (const_int 0))
1219 (if_then_else:SI (match_op_dup:SI 2 [(match_dup 1) (const_int 0)])
1225 ;; These control RTL generation for conditional jump insns
1227 ;; The quad-word fp compare library routines all return nonzero to indicate
1228 ;; true, which is different from the equivalent libgcc routines, so we must
1229 ;; handle them specially here.
1231 (define_expand "beq"
1233 (if_then_else (eq (match_dup 1) (const_int 0))
1234 (label_ref (match_operand 0 "" ""))
1238 if (TARGET_ARCH64 && sparc_compare_op1 == const0_rtx
1239 && GET_CODE (sparc_compare_op0) == REG
1240 && GET_MODE (sparc_compare_op0) == DImode)
1242 emit_v9_brxx_insn (EQ, sparc_compare_op0, operands[0]);
1245 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1247 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, EQ);
1248 emit_jump_insn (gen_bne (operands[0]));
1251 operands[1] = gen_compare_reg (EQ, sparc_compare_op0, sparc_compare_op1);
1254 (define_expand "bne"
1256 (if_then_else (ne (match_dup 1) (const_int 0))
1257 (label_ref (match_operand 0 "" ""))
1261 if (TARGET_ARCH64 && sparc_compare_op1 == const0_rtx
1262 && GET_CODE (sparc_compare_op0) == REG
1263 && GET_MODE (sparc_compare_op0) == DImode)
1265 emit_v9_brxx_insn (NE, sparc_compare_op0, operands[0]);
1268 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1270 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, NE);
1271 emit_jump_insn (gen_bne (operands[0]));
1274 operands[1] = gen_compare_reg (NE, sparc_compare_op0, sparc_compare_op1);
1277 (define_expand "bgt"
1279 (if_then_else (gt (match_dup 1) (const_int 0))
1280 (label_ref (match_operand 0 "" ""))
1284 if (TARGET_ARCH64 && sparc_compare_op1 == const0_rtx
1285 && GET_CODE (sparc_compare_op0) == REG
1286 && GET_MODE (sparc_compare_op0) == DImode)
1288 emit_v9_brxx_insn (GT, sparc_compare_op0, operands[0]);
1291 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1293 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, GT);
1294 emit_jump_insn (gen_bne (operands[0]));
1297 operands[1] = gen_compare_reg (GT, sparc_compare_op0, sparc_compare_op1);
1300 (define_expand "bgtu"
1302 (if_then_else (gtu (match_dup 1) (const_int 0))
1303 (label_ref (match_operand 0 "" ""))
1307 operands[1] = gen_compare_reg (GTU, sparc_compare_op0, sparc_compare_op1);
1310 (define_expand "blt"
1312 (if_then_else (lt (match_dup 1) (const_int 0))
1313 (label_ref (match_operand 0 "" ""))
1317 if (TARGET_ARCH64 && sparc_compare_op1 == const0_rtx
1318 && GET_CODE (sparc_compare_op0) == REG
1319 && GET_MODE (sparc_compare_op0) == DImode)
1321 emit_v9_brxx_insn (LT, sparc_compare_op0, operands[0]);
1324 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1326 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, LT);
1327 emit_jump_insn (gen_bne (operands[0]));
1330 operands[1] = gen_compare_reg (LT, sparc_compare_op0, sparc_compare_op1);
1333 (define_expand "bltu"
1335 (if_then_else (ltu (match_dup 1) (const_int 0))
1336 (label_ref (match_operand 0 "" ""))
1340 operands[1] = gen_compare_reg (LTU, sparc_compare_op0, sparc_compare_op1);
1343 (define_expand "bge"
1345 (if_then_else (ge (match_dup 1) (const_int 0))
1346 (label_ref (match_operand 0 "" ""))
1350 if (TARGET_ARCH64 && sparc_compare_op1 == const0_rtx
1351 && GET_CODE (sparc_compare_op0) == REG
1352 && GET_MODE (sparc_compare_op0) == DImode)
1354 emit_v9_brxx_insn (GE, sparc_compare_op0, operands[0]);
1357 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1359 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, GE);
1360 emit_jump_insn (gen_bne (operands[0]));
1363 operands[1] = gen_compare_reg (GE, sparc_compare_op0, sparc_compare_op1);
1366 (define_expand "bgeu"
1368 (if_then_else (geu (match_dup 1) (const_int 0))
1369 (label_ref (match_operand 0 "" ""))
1373 operands[1] = gen_compare_reg (GEU, sparc_compare_op0, sparc_compare_op1);
1376 (define_expand "ble"
1378 (if_then_else (le (match_dup 1) (const_int 0))
1379 (label_ref (match_operand 0 "" ""))
1383 if (TARGET_ARCH64 && sparc_compare_op1 == const0_rtx
1384 && GET_CODE (sparc_compare_op0) == REG
1385 && GET_MODE (sparc_compare_op0) == DImode)
1387 emit_v9_brxx_insn (LE, sparc_compare_op0, operands[0]);
1390 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1392 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, LE);
1393 emit_jump_insn (gen_bne (operands[0]));
1396 operands[1] = gen_compare_reg (LE, sparc_compare_op0, sparc_compare_op1);
1399 (define_expand "bleu"
1401 (if_then_else (leu (match_dup 1) (const_int 0))
1402 (label_ref (match_operand 0 "" ""))
1406 operands[1] = gen_compare_reg (LEU, sparc_compare_op0, sparc_compare_op1);
1409 (define_expand "bunordered"
1411 (if_then_else (unordered (match_dup 1) (const_int 0))
1412 (label_ref (match_operand 0 "" ""))
1416 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1418 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1,
1420 emit_jump_insn (gen_beq (operands[0]));
1423 operands[1] = gen_compare_reg (UNORDERED, sparc_compare_op0,
1427 (define_expand "bordered"
1429 (if_then_else (ordered (match_dup 1) (const_int 0))
1430 (label_ref (match_operand 0 "" ""))
1434 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1436 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, ORDERED);
1437 emit_jump_insn (gen_bne (operands[0]));
1440 operands[1] = gen_compare_reg (ORDERED, sparc_compare_op0,
1444 (define_expand "bungt"
1446 (if_then_else (ungt (match_dup 1) (const_int 0))
1447 (label_ref (match_operand 0 "" ""))
1451 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1453 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, UNGT);
1454 emit_jump_insn (gen_bgt (operands[0]));
1457 operands[1] = gen_compare_reg (UNGT, sparc_compare_op0, sparc_compare_op1);
1460 (define_expand "bunlt"
1462 (if_then_else (unlt (match_dup 1) (const_int 0))
1463 (label_ref (match_operand 0 "" ""))
1467 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1469 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, UNLT);
1470 emit_jump_insn (gen_bne (operands[0]));
1473 operands[1] = gen_compare_reg (UNLT, sparc_compare_op0, sparc_compare_op1);
1476 (define_expand "buneq"
1478 (if_then_else (uneq (match_dup 1) (const_int 0))
1479 (label_ref (match_operand 0 "" ""))
1483 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1485 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, UNEQ);
1486 emit_jump_insn (gen_beq (operands[0]));
1489 operands[1] = gen_compare_reg (UNEQ, sparc_compare_op0, sparc_compare_op1);
1492 (define_expand "bunge"
1494 (if_then_else (unge (match_dup 1) (const_int 0))
1495 (label_ref (match_operand 0 "" ""))
1499 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1501 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, UNGE);
1502 emit_jump_insn (gen_bne (operands[0]));
1505 operands[1] = gen_compare_reg (UNGE, sparc_compare_op0, sparc_compare_op1);
1508 (define_expand "bunle"
1510 (if_then_else (unle (match_dup 1) (const_int 0))
1511 (label_ref (match_operand 0 "" ""))
1515 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1517 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, UNLE);
1518 emit_jump_insn (gen_bne (operands[0]));
1521 operands[1] = gen_compare_reg (UNLE, sparc_compare_op0, sparc_compare_op1);
1524 (define_expand "bltgt"
1526 (if_then_else (ltgt (match_dup 1) (const_int 0))
1527 (label_ref (match_operand 0 "" ""))
1531 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1533 sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, LTGT);
1534 emit_jump_insn (gen_bne (operands[0]));
1537 operands[1] = gen_compare_reg (LTGT, sparc_compare_op0, sparc_compare_op1);
1540 ;; Now match both normal and inverted jump.
1542 ;; XXX fpcmp nop braindamage
1543 (define_insn "*normal_branch"
1545 (if_then_else (match_operator 0 "noov_compare_op"
1546 [(reg 100) (const_int 0)])
1547 (label_ref (match_operand 1 "" ""))
1551 return output_cbranch (operands[0], operands[1], 1, 0,
1552 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1555 [(set_attr "type" "branch")
1556 (set_attr "branch_type" "icc")])
1558 ;; XXX fpcmp nop braindamage
1559 (define_insn "*inverted_branch"
1561 (if_then_else (match_operator 0 "noov_compare_op"
1562 [(reg 100) (const_int 0)])
1564 (label_ref (match_operand 1 "" ""))))]
1567 return output_cbranch (operands[0], operands[1], 1, 1,
1568 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1571 [(set_attr "type" "branch")
1572 (set_attr "branch_type" "icc")])
1574 ;; XXX fpcmp nop braindamage
1575 (define_insn "*normal_fp_branch"
1577 (if_then_else (match_operator 1 "comparison_operator"
1578 [(match_operand:CCFP 0 "fcc_reg_operand" "c")
1580 (label_ref (match_operand 2 "" ""))
1584 return output_cbranch (operands[1], operands[2], 2, 0,
1585 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1588 [(set_attr "type" "branch")
1589 (set_attr "branch_type" "fcc")])
1591 ;; XXX fpcmp nop braindamage
1592 (define_insn "*inverted_fp_branch"
1594 (if_then_else (match_operator 1 "comparison_operator"
1595 [(match_operand:CCFP 0 "fcc_reg_operand" "c")
1598 (label_ref (match_operand 2 "" ""))))]
1601 return output_cbranch (operands[1], operands[2], 2, 1,
1602 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1605 [(set_attr "type" "branch")
1606 (set_attr "branch_type" "fcc")])
1608 ;; XXX fpcmp nop braindamage
1609 (define_insn "*normal_fpe_branch"
1611 (if_then_else (match_operator 1 "comparison_operator"
1612 [(match_operand:CCFPE 0 "fcc_reg_operand" "c")
1614 (label_ref (match_operand 2 "" ""))
1618 return output_cbranch (operands[1], operands[2], 2, 0,
1619 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1622 [(set_attr "type" "branch")
1623 (set_attr "branch_type" "fcc")])
1625 ;; XXX fpcmp nop braindamage
1626 (define_insn "*inverted_fpe_branch"
1628 (if_then_else (match_operator 1 "comparison_operator"
1629 [(match_operand:CCFPE 0 "fcc_reg_operand" "c")
1632 (label_ref (match_operand 2 "" ""))))]
1635 return output_cbranch (operands[1], operands[2], 2, 1,
1636 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1639 [(set_attr "type" "branch")
1640 (set_attr "branch_type" "fcc")])
1642 ;; SPARC V9-specific jump insns. None of these are guaranteed to be
1643 ;; in the architecture.
1645 ;; There are no 32 bit brreg insns.
1648 (define_insn "*normal_int_branch_sp64"
1650 (if_then_else (match_operator 0 "v9_regcmp_op"
1651 [(match_operand:DI 1 "register_operand" "r")
1653 (label_ref (match_operand 2 "" ""))
1657 return output_v9branch (operands[0], operands[2], 1, 2, 0,
1658 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1661 [(set_attr "type" "branch")
1662 (set_attr "branch_type" "reg")])
1665 (define_insn "*inverted_int_branch_sp64"
1667 (if_then_else (match_operator 0 "v9_regcmp_op"
1668 [(match_operand:DI 1 "register_operand" "r")
1671 (label_ref (match_operand 2 "" ""))))]
1674 return output_v9branch (operands[0], operands[2], 1, 2, 1,
1675 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1678 [(set_attr "type" "branch")
1679 (set_attr "branch_type" "reg")])
1681 ;; Load in operand 0 the (absolute) address of operand 1, which is a symbolic
1682 ;; value subject to a PC-relative relocation. Operand 2 is a helper function
1683 ;; that adds the PC value at the call point to operand 0.
1685 (define_insn "load_pcrel_sym"
1686 [(set (match_operand 0 "register_operand" "=r")
1687 (unspec [(match_operand 1 "symbolic_operand" "")
1688 (match_operand 2 "call_operand_address" "")] UNSPEC_LOAD_PCREL_SYM))
1689 (clobber (reg:SI 15))]
1692 if (flag_delayed_branch)
1693 return "sethi\t%%hi(%a1-4), %0\n\tcall\t%a2\n\t add\t%0, %%lo(%a1+4), %0";
1695 return "sethi\t%%hi(%a1-8), %0\n\tadd\t%0, %%lo(%a1-4), %0\n\tcall\t%a2\n\t nop";
1697 [(set (attr "type") (const_string "multi"))
1698 (set (attr "length")
1699 (if_then_else (eq_attr "delayed_branch" "true")
1703 ;; Move instructions
1705 (define_expand "movqi"
1706 [(set (match_operand:QI 0 "general_operand" "")
1707 (match_operand:QI 1 "general_operand" ""))]
1710 /* Working with CONST_INTs is easier, so convert
1711 a double if needed. */
1712 if (GET_CODE (operands[1]) == CONST_DOUBLE)
1714 operands[1] = GEN_INT (trunc_int_for_mode
1715 (CONST_DOUBLE_LOW (operands[1]), QImode));
1718 /* Handle sets of MEM first. */
1719 if (GET_CODE (operands[0]) == MEM)
1721 if (reg_or_0_operand (operands[1], QImode))
1724 if (! reload_in_progress)
1726 operands[0] = validize_mem (operands[0]);
1727 operands[1] = force_reg (QImode, operands[1]);
1731 /* Fixup TLS cases. */
1732 if (tls_symbolic_operand (operands [1]))
1733 operands[1] = legitimize_tls_address (operands[1]);
1735 /* Fixup PIC cases. */
1738 if (CONSTANT_P (operands[1])
1739 && pic_address_needs_scratch (operands[1]))
1740 operands[1] = legitimize_pic_address (operands[1], QImode, 0);
1742 if (symbolic_operand (operands[1], QImode))
1744 operands[1] = legitimize_pic_address (operands[1],
1746 (reload_in_progress ?
1753 /* All QI constants require only one insn, so proceed. */
1759 (define_insn "*movqi_insn"
1760 [(set (match_operand:QI 0 "nonimmediate_operand" "=r,r,m")
1761 (match_operand:QI 1 "input_operand" "rI,m,rJ"))]
1762 "(register_operand (operands[0], QImode)
1763 || reg_or_0_operand (operands[1], QImode))"
1768 [(set_attr "type" "*,load,store")
1769 (set_attr "us3load_type" "*,3cycle,*")])
1771 (define_expand "movhi"
1772 [(set (match_operand:HI 0 "general_operand" "")
1773 (match_operand:HI 1 "general_operand" ""))]
1776 /* Working with CONST_INTs is easier, so convert
1777 a double if needed. */
1778 if (GET_CODE (operands[1]) == CONST_DOUBLE)
1779 operands[1] = GEN_INT (CONST_DOUBLE_LOW (operands[1]));
1781 /* Handle sets of MEM first. */
1782 if (GET_CODE (operands[0]) == MEM)
1784 if (reg_or_0_operand (operands[1], HImode))
1787 if (! reload_in_progress)
1789 operands[0] = validize_mem (operands[0]);
1790 operands[1] = force_reg (HImode, operands[1]);
1794 /* Fixup TLS cases. */
1795 if (tls_symbolic_operand (operands [1]))
1796 operands[1] = legitimize_tls_address (operands[1]);
1798 /* Fixup PIC cases. */
1801 if (CONSTANT_P (operands[1])
1802 && pic_address_needs_scratch (operands[1]))
1803 operands[1] = legitimize_pic_address (operands[1], HImode, 0);
1805 if (symbolic_operand (operands[1], HImode))
1807 operands[1] = legitimize_pic_address (operands[1],
1809 (reload_in_progress ?
1816 /* This makes sure we will not get rematched due to splittage. */
1817 if (! CONSTANT_P (operands[1]) || input_operand (operands[1], HImode))
1819 else if (CONSTANT_P (operands[1])
1820 && GET_CODE (operands[1]) != HIGH
1821 && GET_CODE (operands[1]) != LO_SUM)
1823 sparc_emit_set_const32 (operands[0], operands[1]);
1830 (define_insn "*movhi_const64_special"
1831 [(set (match_operand:HI 0 "register_operand" "=r")
1832 (match_operand:HI 1 "const64_high_operand" ""))]
1834 "sethi\t%%hi(%a1), %0")
1836 (define_insn "*movhi_insn"
1837 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
1838 (match_operand:HI 1 "input_operand" "rI,K,m,rJ"))]
1839 "(register_operand (operands[0], HImode)
1840 || reg_or_0_operand (operands[1], HImode))"
1843 sethi\t%%hi(%a1), %0
1846 [(set_attr "type" "*,*,load,store")
1847 (set_attr "us3load_type" "*,*,3cycle,*")])
1849 ;; We always work with constants here.
1850 (define_insn "*movhi_lo_sum"
1851 [(set (match_operand:HI 0 "register_operand" "=r")
1852 (ior:HI (match_operand:HI 1 "register_operand" "%r")
1853 (match_operand:HI 2 "small_int" "I")))]
1857 (define_expand "movsi"
1858 [(set (match_operand:SI 0 "general_operand" "")
1859 (match_operand:SI 1 "general_operand" ""))]
1862 /* Working with CONST_INTs is easier, so convert
1863 a double if needed. */
1864 if (GET_CODE (operands[1]) == CONST_DOUBLE)
1865 operands[1] = GEN_INT (CONST_DOUBLE_LOW (operands[1]));
1867 /* Handle sets of MEM first. */
1868 if (GET_CODE (operands[0]) == MEM)
1870 if (reg_or_0_operand (operands[1], SImode))
1873 if (! reload_in_progress)
1875 operands[0] = validize_mem (operands[0]);
1876 operands[1] = force_reg (SImode, operands[1]);
1880 /* Fixup TLS cases. */
1881 if (tls_symbolic_operand (operands [1]))
1882 operands[1] = legitimize_tls_address (operands[1]);
1884 /* Fixup PIC cases. */
1887 if (CONSTANT_P (operands[1])
1888 && pic_address_needs_scratch (operands[1]))
1889 operands[1] = legitimize_pic_address (operands[1], SImode, 0);
1891 if (GET_CODE (operands[1]) == LABEL_REF)
1894 emit_insn (gen_movsi_pic_label_ref (operands[0], operands[1]));
1898 if (symbolic_operand (operands[1], SImode))
1900 operands[1] = legitimize_pic_address (operands[1],
1902 (reload_in_progress ?
1909 /* If we are trying to toss an integer constant into the
1910 FPU registers, force it into memory. */
1911 if (GET_CODE (operands[0]) == REG
1912 && REGNO (operands[0]) >= SPARC_FIRST_FP_REG
1913 && REGNO (operands[0]) <= SPARC_LAST_V9_FP_REG
1914 && CONSTANT_P (operands[1]))
1915 operands[1] = validize_mem (force_const_mem (GET_MODE (operands[0]),
1918 /* This makes sure we will not get rematched due to splittage. */
1919 if (! CONSTANT_P (operands[1]) || input_operand (operands[1], SImode))
1921 else if (CONSTANT_P (operands[1])
1922 && GET_CODE (operands[1]) != HIGH
1923 && GET_CODE (operands[1]) != LO_SUM)
1925 sparc_emit_set_const32 (operands[0], operands[1]);
1932 ;; This is needed to show CSE exactly which bits are set
1933 ;; in a 64-bit register by sethi instructions.
1934 (define_insn "*movsi_const64_special"
1935 [(set (match_operand:SI 0 "register_operand" "=r")
1936 (match_operand:SI 1 "const64_high_operand" ""))]
1938 "sethi\t%%hi(%a1), %0")
1940 (define_insn "*movsi_insn"
1941 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,f,r,r,r,f,m,m,d")
1942 (match_operand:SI 1 "input_operand" "rI,!f,K,J,m,!m,rJ,!f,J"))]
1943 "(register_operand (operands[0], SImode)
1944 || reg_or_0_operand (operands[1], SImode))"
1948 sethi\t%%hi(%a1), %0
1955 [(set_attr "type" "*,fpmove,*,*,load,fpload,store,fpstore,fga")])
1957 (define_insn "*movsi_lo_sum"
1958 [(set (match_operand:SI 0 "register_operand" "=r")
1959 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
1960 (match_operand:SI 2 "immediate_operand" "in")))]
1962 "or\t%1, %%lo(%a2), %0")
1964 (define_insn "*movsi_high"
1965 [(set (match_operand:SI 0 "register_operand" "=r")
1966 (high:SI (match_operand:SI 1 "immediate_operand" "in")))]
1968 "sethi\t%%hi(%a1), %0")
1970 ;; The next two patterns must wrap the SYMBOL_REF in an UNSPEC
1971 ;; so that CSE won't optimize the address computation away.
1972 (define_insn "movsi_lo_sum_pic"
1973 [(set (match_operand:SI 0 "register_operand" "=r")
1974 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
1975 (unspec:SI [(match_operand:SI 2 "immediate_operand" "in")] UNSPEC_MOVE_PIC)))]
1977 "or\t%1, %%lo(%a2), %0")
1979 (define_insn "movsi_high_pic"
1980 [(set (match_operand:SI 0 "register_operand" "=r")
1981 (high:SI (unspec:SI [(match_operand 1 "" "")] UNSPEC_MOVE_PIC)))]
1982 "flag_pic && check_pic (1)"
1983 "sethi\t%%hi(%a1), %0")
1985 (define_expand "movsi_pic_label_ref"
1986 [(set (match_dup 3) (high:SI
1987 (unspec:SI [(match_operand:SI 1 "label_ref_operand" "")
1988 (match_dup 2)] UNSPEC_MOVE_PIC_LABEL)))
1989 (set (match_dup 4) (lo_sum:SI (match_dup 3)
1990 (unspec:SI [(match_dup 1) (match_dup 2)] UNSPEC_MOVE_PIC_LABEL)))
1991 (set (match_operand:SI 0 "register_operand" "=r")
1992 (minus:SI (match_dup 5) (match_dup 4)))]
1995 current_function_uses_pic_offset_table = 1;
1996 operands[2] = gen_rtx_SYMBOL_REF (Pmode, "_GLOBAL_OFFSET_TABLE_");
1999 operands[3] = operands[0];
2000 operands[4] = operands[0];
2004 operands[3] = gen_reg_rtx (SImode);
2005 operands[4] = gen_reg_rtx (SImode);
2007 operands[5] = pic_offset_table_rtx;
2010 (define_insn "*movsi_high_pic_label_ref"
2011 [(set (match_operand:SI 0 "register_operand" "=r")
2013 (unspec:SI [(match_operand:SI 1 "label_ref_operand" "")
2014 (match_operand:SI 2 "" "")] UNSPEC_MOVE_PIC_LABEL)))]
2016 "sethi\t%%hi(%a2-(%a1-.)), %0")
2018 (define_insn "*movsi_lo_sum_pic_label_ref"
2019 [(set (match_operand:SI 0 "register_operand" "=r")
2020 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
2021 (unspec:SI [(match_operand:SI 2 "label_ref_operand" "")
2022 (match_operand:SI 3 "" "")] UNSPEC_MOVE_PIC_LABEL)))]
2024 "or\t%1, %%lo(%a3-(%a2-.)), %0")
2026 (define_expand "movdi"
2027 [(set (match_operand:DI 0 "reg_or_nonsymb_mem_operand" "")
2028 (match_operand:DI 1 "general_operand" ""))]
2031 /* Where possible, convert CONST_DOUBLE into a CONST_INT. */
2032 if (GET_CODE (operands[1]) == CONST_DOUBLE
2033 #if HOST_BITS_PER_WIDE_INT == 32
2034 && ((CONST_DOUBLE_HIGH (operands[1]) == 0
2035 && (CONST_DOUBLE_LOW (operands[1]) & 0x80000000) == 0)
2036 || (CONST_DOUBLE_HIGH (operands[1]) == (HOST_WIDE_INT) 0xffffffff
2037 && (CONST_DOUBLE_LOW (operands[1]) & 0x80000000) != 0))
2040 operands[1] = GEN_INT (CONST_DOUBLE_LOW (operands[1]));
2042 /* Handle MEM cases first. */
2043 if (GET_CODE (operands[0]) == MEM)
2045 /* If it's a REG, we can always do it.
2046 The const zero case is more complex, on v9
2047 we can always perform it. */
2048 if (register_operand (operands[1], DImode)
2050 && (operands[1] == const0_rtx)))
2053 if (! reload_in_progress)
2055 operands[0] = validize_mem (operands[0]);
2056 operands[1] = force_reg (DImode, operands[1]);
2060 /* Fixup TLS cases. */
2061 if (tls_symbolic_operand (operands [1]))
2062 operands[1] = legitimize_tls_address (operands[1]);
2066 if (CONSTANT_P (operands[1])
2067 && pic_address_needs_scratch (operands[1]))
2068 operands[1] = legitimize_pic_address (operands[1], DImode, 0);
2070 if (GET_CODE (operands[1]) == LABEL_REF)
2072 if (! TARGET_ARCH64)
2074 emit_insn (gen_movdi_pic_label_ref (operands[0], operands[1]));
2078 if (symbolic_operand (operands[1], DImode))
2080 operands[1] = legitimize_pic_address (operands[1],
2082 (reload_in_progress ?
2089 /* If we are trying to toss an integer constant into the
2090 FPU registers, force it into memory. */
2091 if (GET_CODE (operands[0]) == REG
2092 && REGNO (operands[0]) >= SPARC_FIRST_FP_REG
2093 && REGNO (operands[0]) <= SPARC_LAST_V9_FP_REG
2094 && CONSTANT_P (operands[1]))
2095 operands[1] = validize_mem (force_const_mem (GET_MODE (operands[0]),
2098 /* This makes sure we will not get rematched due to splittage. */
2099 if (! CONSTANT_P (operands[1]) || input_operand (operands[1], DImode))
2101 else if (TARGET_ARCH64
2102 && CONSTANT_P (operands[1])
2103 && GET_CODE (operands[1]) != HIGH
2104 && GET_CODE (operands[1]) != LO_SUM)
2106 sparc_emit_set_const64 (operands[0], operands[1]);
2114 ;; Be careful, fmovd does not exist when !v9.
2115 ;; We match MEM moves directly when we have correct even
2116 ;; numbered registers, but fall into splits otherwise.
2117 ;; The constraint ordering here is really important to
2118 ;; avoid insane problems in reload, especially for patterns
2121 ;; (set (mem:DI (plus:SI (reg:SI 30 %fp)
2122 ;; (const_int -5016)))
2126 (define_insn "*movdi_insn_sp32_v9"
2127 [(set (match_operand:DI 0 "nonimmediate_operand"
2128 "=T,o,T,U,o,r,r,r,?T,?f,?f,?o,?e,?e,?W")
2129 (match_operand:DI 1 "input_operand"
2130 " J,J,U,T,r,o,i,r, f, T, o, f, e, W, e"))]
2131 "! TARGET_ARCH64 && TARGET_V9
2132 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2149 [(set_attr "type" "store,store,store,load,*,*,*,*,fpstore,fpload,*,*,fpmove,fpload,fpstore")
2150 (set_attr "length" "*,2,*,*,2,2,2,2,*,*,2,2,*,*,*")
2151 (set_attr "fptype" "*,*,*,*,*,*,*,*,*,*,*,*,double,*,*")])
2153 (define_insn "*movdi_insn_sp32"
2154 [(set (match_operand:DI 0 "nonimmediate_operand"
2155 "=o,T,U,o,r,r,r,?T,?f,?f,?o,?f")
2156 (match_operand:DI 1 "input_operand"
2157 " J,U,T,r,o,i,r, f, T, o, f, f"))]
2159 && (register_operand (operands[0], DImode)
2160 || register_operand (operands[1], DImode))"
2174 [(set_attr "type" "store,store,load,*,*,*,*,fpstore,fpload,*,*,*")
2175 (set_attr "length" "2,*,*,2,2,2,2,*,*,2,2,2")])
2177 ;; The following are generated by sparc_emit_set_const64
2178 (define_insn "*movdi_sp64_dbl"
2179 [(set (match_operand:DI 0 "register_operand" "=r")
2180 (match_operand:DI 1 "const64_operand" ""))]
2182 && HOST_BITS_PER_WIDE_INT != 64)"
2185 ;; This is needed to show CSE exactly which bits are set
2186 ;; in a 64-bit register by sethi instructions.
2187 (define_insn "*movdi_const64_special"
2188 [(set (match_operand:DI 0 "register_operand" "=r")
2189 (match_operand:DI 1 "const64_high_operand" ""))]
2191 "sethi\t%%hi(%a1), %0")
2193 (define_insn "*movdi_insn_sp64_novis"
2194 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,r,r,m,?e,?e,?W")
2195 (match_operand:DI 1 "input_operand" "rI,N,J,m,rJ,e,W,e"))]
2196 "TARGET_ARCH64 && ! TARGET_VIS
2197 && (register_operand (operands[0], DImode)
2198 || reg_or_0_operand (operands[1], DImode))"
2201 sethi\t%%hi(%a1), %0
2208 [(set_attr "type" "*,*,*,load,store,fpmove,fpload,fpstore")
2209 (set_attr "fptype" "*,*,*,*,*,double,*,*")])
2211 (define_insn "*movdi_insn_sp64_vis"
2212 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,r,r,m,?e,?e,?W,b")
2213 (match_operand:DI 1 "input_operand" "rI,N,J,m,rJ,e,W,e,J"))]
2214 "TARGET_ARCH64 && TARGET_VIS &&
2215 (register_operand (operands[0], DImode)
2216 || reg_or_0_operand (operands[1], DImode))"
2219 sethi\t%%hi(%a1), %0
2227 [(set_attr "type" "*,*,*,load,store,fpmove,fpload,fpstore,fga")
2228 (set_attr "fptype" "*,*,*,*,*,double,*,*,double")])
2230 (define_expand "movdi_pic_label_ref"
2231 [(set (match_dup 3) (high:DI
2232 (unspec:DI [(match_operand:DI 1 "label_ref_operand" "")
2233 (match_dup 2)] UNSPEC_MOVE_PIC_LABEL)))
2234 (set (match_dup 4) (lo_sum:DI (match_dup 3)
2235 (unspec:DI [(match_dup 1) (match_dup 2)] UNSPEC_MOVE_PIC_LABEL)))
2236 (set (match_operand:DI 0 "register_operand" "=r")
2237 (minus:DI (match_dup 5) (match_dup 4)))]
2238 "TARGET_ARCH64 && flag_pic"
2240 current_function_uses_pic_offset_table = 1;
2241 operands[2] = gen_rtx_SYMBOL_REF (Pmode, "_GLOBAL_OFFSET_TABLE_");
2244 operands[3] = operands[0];
2245 operands[4] = operands[0];
2249 operands[3] = gen_reg_rtx (DImode);
2250 operands[4] = gen_reg_rtx (DImode);
2252 operands[5] = pic_offset_table_rtx;
2255 (define_insn "*movdi_high_pic_label_ref"
2256 [(set (match_operand:DI 0 "register_operand" "=r")
2258 (unspec:DI [(match_operand:DI 1 "label_ref_operand" "")
2259 (match_operand:DI 2 "" "")] UNSPEC_MOVE_PIC_LABEL)))]
2260 "TARGET_ARCH64 && flag_pic"
2261 "sethi\t%%hi(%a2-(%a1-.)), %0")
2263 (define_insn "*movdi_lo_sum_pic_label_ref"
2264 [(set (match_operand:DI 0 "register_operand" "=r")
2265 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2266 (unspec:DI [(match_operand:DI 2 "label_ref_operand" "")
2267 (match_operand:DI 3 "" "")] UNSPEC_MOVE_PIC_LABEL)))]
2268 "TARGET_ARCH64 && flag_pic"
2269 "or\t%1, %%lo(%a3-(%a2-.)), %0")
2271 ;; SPARC-v9 code model support insns. See sparc_emit_set_symbolic_const64
2272 ;; in sparc.c to see what is going on here... PIC stuff comes first.
2274 (define_insn "movdi_lo_sum_pic"
2275 [(set (match_operand:DI 0 "register_operand" "=r")
2276 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2277 (unspec:DI [(match_operand:DI 2 "immediate_operand" "in")] UNSPEC_MOVE_PIC)))]
2278 "TARGET_ARCH64 && flag_pic"
2279 "or\t%1, %%lo(%a2), %0")
2281 (define_insn "movdi_high_pic"
2282 [(set (match_operand:DI 0 "register_operand" "=r")
2283 (high:DI (unspec:DI [(match_operand 1 "" "")] UNSPEC_MOVE_PIC)))]
2284 "TARGET_ARCH64 && flag_pic && check_pic (1)"
2285 "sethi\t%%hi(%a1), %0")
2287 (define_insn "*sethi_di_medlow_embmedany_pic"
2288 [(set (match_operand:DI 0 "register_operand" "=r")
2289 (high:DI (match_operand:DI 1 "sp64_medium_pic_operand" "")))]
2290 "(TARGET_CM_MEDLOW || TARGET_CM_EMBMEDANY) && check_pic (1)"
2291 "sethi\t%%hi(%a1), %0")
2293 (define_insn "*sethi_di_medlow"
2294 [(set (match_operand:DI 0 "register_operand" "=r")
2295 (high:DI (match_operand:DI 1 "symbolic_operand" "")))]
2296 "TARGET_CM_MEDLOW && check_pic (1)"
2297 "sethi\t%%hi(%a1), %0")
2299 (define_insn "*losum_di_medlow"
2300 [(set (match_operand:DI 0 "register_operand" "=r")
2301 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2302 (match_operand:DI 2 "symbolic_operand" "")))]
2304 "or\t%1, %%lo(%a2), %0")
2306 (define_insn "seth44"
2307 [(set (match_operand:DI 0 "register_operand" "=r")
2308 (high:DI (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")] UNSPEC_SETH44)))]
2310 "sethi\t%%h44(%a1), %0")
2312 (define_insn "setm44"
2313 [(set (match_operand:DI 0 "register_operand" "=r")
2314 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2315 (unspec:DI [(match_operand:DI 2 "symbolic_operand" "")] UNSPEC_SETM44)))]
2317 "or\t%1, %%m44(%a2), %0")
2319 (define_insn "setl44"
2320 [(set (match_operand:DI 0 "register_operand" "=r")
2321 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2322 (match_operand:DI 2 "symbolic_operand" "")))]
2324 "or\t%1, %%l44(%a2), %0")
2326 (define_insn "sethh"
2327 [(set (match_operand:DI 0 "register_operand" "=r")
2328 (high:DI (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")] UNSPEC_SETHH)))]
2330 "sethi\t%%hh(%a1), %0")
2332 (define_insn "setlm"
2333 [(set (match_operand:DI 0 "register_operand" "=r")
2334 (high:DI (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")] UNSPEC_SETLM)))]
2336 "sethi\t%%lm(%a1), %0")
2338 (define_insn "sethm"
2339 [(set (match_operand:DI 0 "register_operand" "=r")
2340 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2341 (unspec:DI [(match_operand:DI 2 "symbolic_operand" "")] UNSPEC_EMB_SETHM)))]
2343 "or\t%1, %%hm(%a2), %0")
2345 (define_insn "setlo"
2346 [(set (match_operand:DI 0 "register_operand" "=r")
2347 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2348 (match_operand:DI 2 "symbolic_operand" "")))]
2350 "or\t%1, %%lo(%a2), %0")
2352 (define_insn "embmedany_sethi"
2353 [(set (match_operand:DI 0 "register_operand" "=r")
2354 (high:DI (unspec:DI [(match_operand:DI 1 "data_segment_operand" "")] UNSPEC_EMB_HISUM)))]
2355 "TARGET_CM_EMBMEDANY && check_pic (1)"
2356 "sethi\t%%hi(%a1), %0")
2358 (define_insn "embmedany_losum"
2359 [(set (match_operand:DI 0 "register_operand" "=r")
2360 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2361 (match_operand:DI 2 "data_segment_operand" "")))]
2362 "TARGET_CM_EMBMEDANY"
2363 "add\t%1, %%lo(%a2), %0")
2365 (define_insn "embmedany_brsum"
2366 [(set (match_operand:DI 0 "register_operand" "=r")
2367 (unspec:DI [(match_operand:DI 1 "register_operand" "r")] UNSPEC_EMB_HISUM))]
2368 "TARGET_CM_EMBMEDANY"
2371 (define_insn "embmedany_textuhi"
2372 [(set (match_operand:DI 0 "register_operand" "=r")
2373 (high:DI (unspec:DI [(match_operand:DI 1 "text_segment_operand" "")] UNSPEC_EMB_TEXTUHI)))]
2374 "TARGET_CM_EMBMEDANY && check_pic (1)"
2375 "sethi\t%%uhi(%a1), %0")
2377 (define_insn "embmedany_texthi"
2378 [(set (match_operand:DI 0 "register_operand" "=r")
2379 (high:DI (unspec:DI [(match_operand:DI 1 "text_segment_operand" "")] UNSPEC_EMB_TEXTHI)))]
2380 "TARGET_CM_EMBMEDANY && check_pic (1)"
2381 "sethi\t%%hi(%a1), %0")
2383 (define_insn "embmedany_textulo"
2384 [(set (match_operand:DI 0 "register_operand" "=r")
2385 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2386 (unspec:DI [(match_operand:DI 2 "text_segment_operand" "")] UNSPEC_EMB_TEXTULO)))]
2387 "TARGET_CM_EMBMEDANY"
2388 "or\t%1, %%ulo(%a2), %0")
2390 (define_insn "embmedany_textlo"
2391 [(set (match_operand:DI 0 "register_operand" "=r")
2392 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2393 (match_operand:DI 2 "text_segment_operand" "")))]
2394 "TARGET_CM_EMBMEDANY"
2395 "or\t%1, %%lo(%a2), %0")
2397 ;; Now some patterns to help reload out a bit.
2398 (define_expand "reload_indi"
2399 [(parallel [(match_operand:DI 0 "register_operand" "=r")
2400 (match_operand:DI 1 "immediate_operand" "")
2401 (match_operand:TI 2 "register_operand" "=&r")])]
2403 || TARGET_CM_EMBMEDANY)
2406 sparc_emit_set_symbolic_const64 (operands[0], operands[1], operands[2]);
2410 (define_expand "reload_outdi"
2411 [(parallel [(match_operand:DI 0 "register_operand" "=r")
2412 (match_operand:DI 1 "immediate_operand" "")
2413 (match_operand:TI 2 "register_operand" "=&r")])]
2415 || TARGET_CM_EMBMEDANY)
2418 sparc_emit_set_symbolic_const64 (operands[0], operands[1], operands[2]);
2422 ;; Split up putting CONSTs and REGs into DI regs when !arch64
2424 [(set (match_operand:DI 0 "register_operand" "")
2425 (match_operand:DI 1 "const_int_operand" ""))]
2426 "! TARGET_ARCH64 && reload_completed"
2427 [(clobber (const_int 0))]
2429 #if HOST_BITS_PER_WIDE_INT == 32
2430 emit_insn (gen_movsi (gen_highpart (SImode, operands[0]),
2431 (INTVAL (operands[1]) < 0) ?
2434 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]),
2437 unsigned int low, high;
2439 low = trunc_int_for_mode (INTVAL (operands[1]), SImode);
2440 high = trunc_int_for_mode (INTVAL (operands[1]) >> 32, SImode);
2441 emit_insn (gen_movsi (gen_highpart (SImode, operands[0]), GEN_INT (high)));
2443 /* Slick... but this trick loses if this subreg constant part
2444 can be done in one insn. */
2445 if (low == high && (low & 0x3ff) != 0 && low + 0x1000 >= 0x2000)
2446 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]),
2447 gen_highpart (SImode, operands[0])));
2449 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]), GEN_INT (low)));
2455 [(set (match_operand:DI 0 "register_operand" "")
2456 (match_operand:DI 1 "const_double_operand" ""))]
2460 && ((GET_CODE (operands[0]) == REG
2461 && REGNO (operands[0]) < 32)
2462 || (GET_CODE (operands[0]) == SUBREG
2463 && GET_CODE (SUBREG_REG (operands[0])) == REG
2464 && REGNO (SUBREG_REG (operands[0])) < 32))))"
2465 [(clobber (const_int 0))]
2467 emit_insn (gen_movsi (gen_highpart (SImode, operands[0]),
2468 GEN_INT (CONST_DOUBLE_HIGH (operands[1]))));
2470 /* Slick... but this trick loses if this subreg constant part
2471 can be done in one insn. */
2472 if (CONST_DOUBLE_LOW (operands[1]) == CONST_DOUBLE_HIGH (operands[1])
2473 && !(SPARC_SETHI32_P (CONST_DOUBLE_HIGH (operands[1]))
2474 || SPARC_SIMM13_P (CONST_DOUBLE_HIGH (operands[1]))))
2476 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]),
2477 gen_highpart (SImode, operands[0])));
2481 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]),
2482 GEN_INT (CONST_DOUBLE_LOW (operands[1]))));
2488 [(set (match_operand:DI 0 "register_operand" "")
2489 (match_operand:DI 1 "register_operand" ""))]
2493 && ((GET_CODE (operands[0]) == REG
2494 && REGNO (operands[0]) < 32)
2495 || (GET_CODE (operands[0]) == SUBREG
2496 && GET_CODE (SUBREG_REG (operands[0])) == REG
2497 && REGNO (SUBREG_REG (operands[0])) < 32))))"
2498 [(clobber (const_int 0))]
2500 rtx set_dest = operands[0];
2501 rtx set_src = operands[1];
2505 dest1 = gen_highpart (SImode, set_dest);
2506 dest2 = gen_lowpart (SImode, set_dest);
2507 src1 = gen_highpart (SImode, set_src);
2508 src2 = gen_lowpart (SImode, set_src);
2510 /* Now emit using the real source and destination we found, swapping
2511 the order if we detect overlap. */
2512 if (reg_overlap_mentioned_p (dest1, src2))
2514 emit_insn (gen_movsi (dest2, src2));
2515 emit_insn (gen_movsi (dest1, src1));
2519 emit_insn (gen_movsi (dest1, src1));
2520 emit_insn (gen_movsi (dest2, src2));
2525 ;; Now handle the cases of memory moves from/to non-even
2526 ;; DI mode register pairs.
2528 [(set (match_operand:DI 0 "register_operand" "")
2529 (match_operand:DI 1 "memory_operand" ""))]
2532 && sparc_splitdi_legitimate (operands[0], operands[1]))"
2533 [(clobber (const_int 0))]
2535 rtx word0 = adjust_address (operands[1], SImode, 0);
2536 rtx word1 = adjust_address (operands[1], SImode, 4);
2537 rtx high_part = gen_highpart (SImode, operands[0]);
2538 rtx low_part = gen_lowpart (SImode, operands[0]);
2540 if (reg_overlap_mentioned_p (high_part, word1))
2542 emit_insn (gen_movsi (low_part, word1));
2543 emit_insn (gen_movsi (high_part, word0));
2547 emit_insn (gen_movsi (high_part, word0));
2548 emit_insn (gen_movsi (low_part, word1));
2554 [(set (match_operand:DI 0 "memory_operand" "")
2555 (match_operand:DI 1 "register_operand" ""))]
2558 && sparc_splitdi_legitimate (operands[1], operands[0]))"
2559 [(clobber (const_int 0))]
2561 emit_insn (gen_movsi (adjust_address (operands[0], SImode, 0),
2562 gen_highpart (SImode, operands[1])));
2563 emit_insn (gen_movsi (adjust_address (operands[0], SImode, 4),
2564 gen_lowpart (SImode, operands[1])));
2569 [(set (match_operand:DI 0 "memory_operand" "")
2574 && ! mem_min_alignment (operands[0], 8)))
2575 && offsettable_memref_p (operands[0])"
2576 [(clobber (const_int 0))]
2578 emit_insn (gen_movsi (adjust_address (operands[0], SImode, 0), const0_rtx));
2579 emit_insn (gen_movsi (adjust_address (operands[0], SImode, 4), const0_rtx));
2583 ;; Floating point move insns
2585 (define_insn "*movsf_insn_novis"
2586 [(set (match_operand:SF 0 "nonimmediate_operand" "=f,*r,*r,*r,*r,*r,f,m,m")
2587 (match_operand:SF 1 "input_operand" "f,G,Q,*rR,S,m,m,f,*rG"))]
2588 "(TARGET_FPU && ! TARGET_VIS)
2589 && (register_operand (operands[0], SFmode)
2590 || register_operand (operands[1], SFmode)
2591 || fp_zero_operand (operands[1], SFmode))"
2593 if (GET_CODE (operands[1]) == CONST_DOUBLE
2594 && (which_alternative == 2
2595 || which_alternative == 3
2596 || which_alternative == 4))
2601 REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
2602 REAL_VALUE_TO_TARGET_SINGLE (r, i);
2603 operands[1] = GEN_INT (i);
2606 switch (which_alternative)
2609 return "fmovs\t%1, %0";
2613 return "sethi\t%%hi(%a1), %0";
2615 return "mov\t%1, %0";
2620 return "ld\t%1, %0";
2623 return "st\t%r1, %0";
2628 [(set_attr "type" "fpmove,*,*,*,*,load,fpload,fpstore,store")])
2630 (define_insn "*movsf_insn_vis"
2631 [(set (match_operand:SF 0 "nonimmediate_operand" "=f,f,*r,*r,*r,*r,*r,f,m,m")
2632 (match_operand:SF 1 "input_operand" "f,G,G,Q,*rR,S,m,m,f,*rG"))]
2633 "(TARGET_FPU && TARGET_VIS)
2634 && (register_operand (operands[0], SFmode)
2635 || register_operand (operands[1], SFmode)
2636 || fp_zero_operand (operands[1], SFmode))"
2638 if (GET_CODE (operands[1]) == CONST_DOUBLE
2639 && (which_alternative == 3
2640 || which_alternative == 4
2641 || which_alternative == 5))
2646 REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
2647 REAL_VALUE_TO_TARGET_SINGLE (r, i);
2648 operands[1] = GEN_INT (i);
2651 switch (which_alternative)
2654 return "fmovs\t%1, %0";
2656 return "fzeros\t%0";
2660 return "sethi\t%%hi(%a1), %0";
2662 return "mov\t%1, %0";
2667 return "ld\t%1, %0";
2670 return "st\t%r1, %0";
2675 [(set_attr "type" "fpmove,fga,*,*,*,*,load,fpload,fpstore,store")])
2677 ;; Exactly the same as above, except that all `f' cases are deleted.
2678 ;; This is necessary to prevent reload from ever trying to use a `f' reg
2681 (define_insn "*movsf_no_f_insn"
2682 [(set (match_operand:SF 0 "nonimmediate_operand" "=r,r,r,r,r,m")
2683 (match_operand:SF 1 "input_operand" "G,Q,rR,S,m,rG"))]
2685 && (register_operand (operands[0], SFmode)
2686 || register_operand (operands[1], SFmode)
2687 || fp_zero_operand (operands[1], SFmode))"
2689 if (GET_CODE (operands[1]) == CONST_DOUBLE
2690 && (which_alternative == 1
2691 || which_alternative == 2
2692 || which_alternative == 3))
2697 REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
2698 REAL_VALUE_TO_TARGET_SINGLE (r, i);
2699 operands[1] = GEN_INT (i);
2702 switch (which_alternative)
2707 return "sethi\t%%hi(%a1), %0";
2709 return "mov\t%1, %0";
2713 return "ld\t%1, %0";
2715 return "st\t%r1, %0";
2720 [(set_attr "type" "*,*,*,*,load,store")])
2722 (define_insn "*movsf_lo_sum"
2723 [(set (match_operand:SF 0 "register_operand" "=r")
2724 (lo_sum:SF (match_operand:SF 1 "register_operand" "r")
2725 (match_operand:SF 2 "const_double_operand" "S")))]
2726 "fp_high_losum_p (operands[2])"
2731 REAL_VALUE_FROM_CONST_DOUBLE (r, operands[2]);
2732 REAL_VALUE_TO_TARGET_SINGLE (r, i);
2733 operands[2] = GEN_INT (i);
2734 return "or\t%1, %%lo(%a2), %0";
2737 (define_insn "*movsf_high"
2738 [(set (match_operand:SF 0 "register_operand" "=r")
2739 (high:SF (match_operand:SF 1 "const_double_operand" "S")))]
2740 "fp_high_losum_p (operands[1])"
2745 REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
2746 REAL_VALUE_TO_TARGET_SINGLE (r, i);
2747 operands[1] = GEN_INT (i);
2748 return "sethi\t%%hi(%1), %0";
2752 [(set (match_operand:SF 0 "register_operand" "")
2753 (match_operand:SF 1 "const_double_operand" ""))]
2754 "fp_high_losum_p (operands[1])
2755 && (GET_CODE (operands[0]) == REG
2756 && REGNO (operands[0]) < 32)"
2757 [(set (match_dup 0) (high:SF (match_dup 1)))
2758 (set (match_dup 0) (lo_sum:SF (match_dup 0) (match_dup 1)))])
2760 (define_expand "movsf"
2761 [(set (match_operand:SF 0 "general_operand" "")
2762 (match_operand:SF 1 "general_operand" ""))]
2765 /* Force SFmode constants into memory. */
2766 if (GET_CODE (operands[0]) == REG
2767 && CONSTANT_P (operands[1]))
2769 /* emit_group_store will send such bogosity to us when it is
2770 not storing directly into memory. So fix this up to avoid
2771 crashes in output_constant_pool. */
2772 if (operands [1] == const0_rtx)
2773 operands[1] = CONST0_RTX (SFmode);
2775 if (TARGET_VIS && fp_zero_operand (operands[1], SFmode))
2778 /* We are able to build any SF constant in integer registers
2779 with at most 2 instructions. */
2780 if (REGNO (operands[0]) < 32)
2783 operands[1] = validize_mem (force_const_mem (GET_MODE (operands[0]),
2787 /* Handle sets of MEM first. */
2788 if (GET_CODE (operands[0]) == MEM)
2790 if (register_operand (operands[1], SFmode)
2791 || fp_zero_operand (operands[1], SFmode))
2794 if (! reload_in_progress)
2796 operands[0] = validize_mem (operands[0]);
2797 operands[1] = force_reg (SFmode, operands[1]);
2801 /* Fixup PIC cases. */
2804 if (CONSTANT_P (operands[1])
2805 && pic_address_needs_scratch (operands[1]))
2806 operands[1] = legitimize_pic_address (operands[1], SFmode, 0);
2808 if (symbolic_operand (operands[1], SFmode))
2810 operands[1] = legitimize_pic_address (operands[1],
2812 (reload_in_progress ?
2822 (define_expand "movdf"
2823 [(set (match_operand:DF 0 "general_operand" "")
2824 (match_operand:DF 1 "general_operand" ""))]
2827 /* Force DFmode constants into memory. */
2828 if (GET_CODE (operands[0]) == REG
2829 && CONSTANT_P (operands[1]))
2831 /* emit_group_store will send such bogosity to us when it is
2832 not storing directly into memory. So fix this up to avoid
2833 crashes in output_constant_pool. */
2834 if (operands [1] == const0_rtx)
2835 operands[1] = CONST0_RTX (DFmode);
2837 if ((TARGET_VIS || REGNO (operands[0]) < 32)
2838 && fp_zero_operand (operands[1], DFmode))
2841 /* We are able to build any DF constant in integer registers. */
2842 if (REGNO (operands[0]) < 32
2843 && (reload_completed || reload_in_progress))
2846 operands[1] = validize_mem (force_const_mem (GET_MODE (operands[0]),
2850 /* Handle MEM cases first. */
2851 if (GET_CODE (operands[0]) == MEM)
2853 if (register_operand (operands[1], DFmode)
2854 || fp_zero_operand (operands[1], DFmode))
2857 if (! reload_in_progress)
2859 operands[0] = validize_mem (operands[0]);
2860 operands[1] = force_reg (DFmode, operands[1]);
2864 /* Fixup PIC cases. */
2867 if (CONSTANT_P (operands[1])
2868 && pic_address_needs_scratch (operands[1]))
2869 operands[1] = legitimize_pic_address (operands[1], DFmode, 0);
2871 if (symbolic_operand (operands[1], DFmode))
2873 operands[1] = legitimize_pic_address (operands[1],
2875 (reload_in_progress ?
2885 ;; Be careful, fmovd does not exist when !v9.
2886 (define_insn "*movdf_insn_sp32"
2887 [(set (match_operand:DF 0 "nonimmediate_operand" "=e,W,U,T,o,e,*r,o,e,o")
2888 (match_operand:DF 1 "input_operand" "W#F,e,T,U,G,e,*rFo,*r,o#F,e"))]
2891 && (register_operand (operands[0], DFmode)
2892 || register_operand (operands[1], DFmode)
2893 || fp_zero_operand (operands[1], DFmode))"
2905 [(set_attr "type" "fpload,fpstore,load,store,*,*,*,*,*,*")
2906 (set_attr "length" "*,*,*,*,2,2,2,2,2,2")])
2908 (define_insn "*movdf_no_e_insn_sp32"
2909 [(set (match_operand:DF 0 "nonimmediate_operand" "=U,T,o,r,o")
2910 (match_operand:DF 1 "input_operand" "T,U,G,ro,r"))]
2914 && (register_operand (operands[0], DFmode)
2915 || register_operand (operands[1], DFmode)
2916 || fp_zero_operand (operands[1], DFmode))"
2923 [(set_attr "type" "load,store,*,*,*")
2924 (set_attr "length" "*,*,2,2,2")])
2926 (define_insn "*movdf_no_e_insn_v9_sp32"
2927 [(set (match_operand:DF 0 "nonimmediate_operand" "=U,T,T,r,o")
2928 (match_operand:DF 1 "input_operand" "T,U,G,ro,rG"))]
2932 && (register_operand (operands[0], DFmode)
2933 || register_operand (operands[1], DFmode)
2934 || fp_zero_operand (operands[1], DFmode))"
2941 [(set_attr "type" "load,store,store,*,*")
2942 (set_attr "length" "*,*,*,2,2")])
2944 ;; We have available v9 double floats but not 64-bit
2945 ;; integer registers and no VIS.
2946 (define_insn "*movdf_insn_v9only_novis"
2947 [(set (match_operand:DF 0 "nonimmediate_operand" "=e,e,T,W,U,T,f,*r,o")
2948 (match_operand:DF 1 "input_operand" "e,W#F,G,e,T,U,o#F,*roF,*rGf"))]
2953 && (register_operand (operands[0], DFmode)
2954 || register_operand (operands[1], DFmode)
2955 || fp_zero_operand (operands[1], DFmode))"
2966 [(set_attr "type" "fpmove,load,store,store,load,store,*,*,*")
2967 (set_attr "length" "*,*,*,*,*,*,2,2,2")
2968 (set_attr "fptype" "double,*,*,*,*,*,*,*,*")])
2970 ;; We have available v9 double floats but not 64-bit
2971 ;; integer registers but we have VIS.
2972 (define_insn "*movdf_insn_v9only_vis"
2973 [(set (match_operand:DF 0 "nonimmediate_operand" "=e,e,e,T,W,U,T,f,*r,o")
2974 (match_operand:DF 1 "input_operand" "G,e,W#F,G,e,T,U,o#F,*roGF,*rGf"))]
2978 && (register_operand (operands[0], DFmode)
2979 || register_operand (operands[1], DFmode)
2980 || fp_zero_operand (operands[1], DFmode))"
2992 [(set_attr "type" "fga,fpmove,load,store,store,load,store,*,*,*")
2993 (set_attr "length" "*,*,*,*,*,*,*,2,2,2")
2994 (set_attr "fptype" "double,double,*,*,*,*,*,*,*,*")])
2996 ;; We have available both v9 double floats and 64-bit
2997 ;; integer registers. No VIS though.
2998 (define_insn "*movdf_insn_sp64_novis"
2999 [(set (match_operand:DF 0 "nonimmediate_operand" "=e,e,W,*r,*r,m,*r")
3000 (match_operand:DF 1 "input_operand" "e,W#F,e,*rG,m,*rG,F"))]
3004 && (register_operand (operands[0], DFmode)
3005 || register_operand (operands[1], DFmode)
3006 || fp_zero_operand (operands[1], DFmode))"
3015 [(set_attr "type" "fpmove,load,store,*,load,store,*")
3016 (set_attr "length" "*,*,*,*,*,*,2")
3017 (set_attr "fptype" "double,*,*,*,*,*,*")])
3019 ;; We have available both v9 double floats and 64-bit
3020 ;; integer registers. And we have VIS.
3021 (define_insn "*movdf_insn_sp64_vis"
3022 [(set (match_operand:DF 0 "nonimmediate_operand" "=e,e,e,W,*r,*r,m,*r")
3023 (match_operand:DF 1 "input_operand" "G,e,W#F,e,*rG,m,*rG,F"))]
3027 && (register_operand (operands[0], DFmode)
3028 || register_operand (operands[1], DFmode)
3029 || fp_zero_operand (operands[1], DFmode))"
3039 [(set_attr "type" "fga,fpmove,load,store,*,load,store,*")
3040 (set_attr "length" "*,*,*,*,*,*,*,2")
3041 (set_attr "fptype" "double,double,*,*,*,*,*,*")])
3043 (define_insn "*movdf_no_e_insn_sp64"
3044 [(set (match_operand:DF 0 "nonimmediate_operand" "=r,r,m")
3045 (match_operand:DF 1 "input_operand" "r,m,rG"))]
3048 && (register_operand (operands[0], DFmode)
3049 || register_operand (operands[1], DFmode)
3050 || fp_zero_operand (operands[1], DFmode))"
3055 [(set_attr "type" "*,load,store")])
3058 [(set (match_operand:DF 0 "register_operand" "")
3059 (match_operand:DF 1 "const_double_operand" ""))]
3061 && (GET_CODE (operands[0]) == REG
3062 && REGNO (operands[0]) < 32)
3063 && ! fp_zero_operand(operands[1], DFmode)
3064 && reload_completed"
3065 [(clobber (const_int 0))]
3070 REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
3071 REAL_VALUE_TO_TARGET_DOUBLE (r, l);
3072 operands[0] = gen_rtx_raw_REG (DImode, REGNO (operands[0]));
3076 #if HOST_BITS_PER_WIDE_INT == 64
3079 val = ((HOST_WIDE_INT)(unsigned long)l[1] |
3080 ((HOST_WIDE_INT)(unsigned long)l[0] << 32));
3081 emit_insn (gen_movdi (operands[0], GEN_INT (val)));
3083 emit_insn (gen_movdi (operands[0],
3084 immed_double_const (l[1], l[0], DImode)));
3089 emit_insn (gen_movsi (gen_highpart (SImode, operands[0]),
3092 /* Slick... but this trick loses if this subreg constant part
3093 can be done in one insn. */
3095 && !(SPARC_SETHI32_P (l[0])
3096 || SPARC_SIMM13_P (l[0])))
3098 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]),
3099 gen_highpart (SImode, operands[0])));
3103 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]),
3110 ;; Ok, now the splits to handle all the multi insn and
3111 ;; mis-aligned memory address cases.
3112 ;; In these splits please take note that we must be
3113 ;; careful when V9 but not ARCH64 because the integer
3114 ;; register DFmode cases must be handled.
3116 [(set (match_operand:DF 0 "register_operand" "")
3117 (match_operand:DF 1 "register_operand" ""))]
3120 && ((GET_CODE (operands[0]) == REG
3121 && REGNO (operands[0]) < 32)
3122 || (GET_CODE (operands[0]) == SUBREG
3123 && GET_CODE (SUBREG_REG (operands[0])) == REG
3124 && REGNO (SUBREG_REG (operands[0])) < 32))))
3125 && reload_completed"
3126 [(clobber (const_int 0))]
3128 rtx set_dest = operands[0];
3129 rtx set_src = operands[1];
3133 dest1 = gen_highpart (SFmode, set_dest);
3134 dest2 = gen_lowpart (SFmode, set_dest);
3135 src1 = gen_highpart (SFmode, set_src);
3136 src2 = gen_lowpart (SFmode, set_src);
3138 /* Now emit using the real source and destination we found, swapping
3139 the order if we detect overlap. */
3140 if (reg_overlap_mentioned_p (dest1, src2))
3142 emit_insn (gen_movsf (dest2, src2));
3143 emit_insn (gen_movsf (dest1, src1));
3147 emit_insn (gen_movsf (dest1, src1));
3148 emit_insn (gen_movsf (dest2, src2));
3154 [(set (match_operand:DF 0 "register_operand" "")
3155 (match_operand:DF 1 "memory_operand" ""))]
3158 && (((REGNO (operands[0]) % 2) != 0)
3159 || ! mem_min_alignment (operands[1], 8))
3160 && offsettable_memref_p (operands[1])"
3161 [(clobber (const_int 0))]
3163 rtx word0 = adjust_address (operands[1], SFmode, 0);
3164 rtx word1 = adjust_address (operands[1], SFmode, 4);
3166 if (reg_overlap_mentioned_p (gen_highpart (SFmode, operands[0]), word1))
3168 emit_insn (gen_movsf (gen_lowpart (SFmode, operands[0]),
3170 emit_insn (gen_movsf (gen_highpart (SFmode, operands[0]),
3175 emit_insn (gen_movsf (gen_highpart (SFmode, operands[0]),
3177 emit_insn (gen_movsf (gen_lowpart (SFmode, operands[0]),
3184 [(set (match_operand:DF 0 "memory_operand" "")
3185 (match_operand:DF 1 "register_operand" ""))]
3188 && (((REGNO (operands[1]) % 2) != 0)
3189 || ! mem_min_alignment (operands[0], 8))
3190 && offsettable_memref_p (operands[0])"
3191 [(clobber (const_int 0))]
3193 rtx word0 = adjust_address (operands[0], SFmode, 0);
3194 rtx word1 = adjust_address (operands[0], SFmode, 4);
3196 emit_insn (gen_movsf (word0,
3197 gen_highpart (SFmode, operands[1])));
3198 emit_insn (gen_movsf (word1,
3199 gen_lowpart (SFmode, operands[1])));
3204 [(set (match_operand:DF 0 "memory_operand" "")
3205 (match_operand:DF 1 "fp_zero_operand" ""))]
3209 && ! mem_min_alignment (operands[0], 8)))
3210 && offsettable_memref_p (operands[0])"
3211 [(clobber (const_int 0))]
3215 dest1 = adjust_address (operands[0], SFmode, 0);
3216 dest2 = adjust_address (operands[0], SFmode, 4);
3218 emit_insn (gen_movsf (dest1, CONST0_RTX (SFmode)));
3219 emit_insn (gen_movsf (dest2, CONST0_RTX (SFmode)));
3224 [(set (match_operand:DF 0 "register_operand" "")
3225 (match_operand:DF 1 "fp_zero_operand" ""))]
3228 && ((GET_CODE (operands[0]) == REG
3229 && REGNO (operands[0]) < 32)
3230 || (GET_CODE (operands[0]) == SUBREG
3231 && GET_CODE (SUBREG_REG (operands[0])) == REG
3232 && REGNO (SUBREG_REG (operands[0])) < 32))"
3233 [(clobber (const_int 0))]
3235 rtx set_dest = operands[0];
3238 dest1 = gen_highpart (SFmode, set_dest);
3239 dest2 = gen_lowpart (SFmode, set_dest);
3240 emit_insn (gen_movsf (dest1, CONST0_RTX (SFmode)));
3241 emit_insn (gen_movsf (dest2, CONST0_RTX (SFmode)));
3245 (define_expand "movtf"
3246 [(set (match_operand:TF 0 "general_operand" "")
3247 (match_operand:TF 1 "general_operand" ""))]
3250 /* Force TFmode constants into memory. */
3251 if (GET_CODE (operands[0]) == REG
3252 && CONSTANT_P (operands[1]))
3254 /* emit_group_store will send such bogosity to us when it is
3255 not storing directly into memory. So fix this up to avoid
3256 crashes in output_constant_pool. */
3257 if (operands [1] == const0_rtx)
3258 operands[1] = CONST0_RTX (TFmode);
3260 if (TARGET_VIS && fp_zero_operand (operands[1], TFmode))
3263 operands[1] = validize_mem (force_const_mem (GET_MODE (operands[0]),
3267 /* Handle MEM cases first, note that only v9 guarantees
3268 full 16-byte alignment for quads. */
3269 if (GET_CODE (operands[0]) == MEM)
3271 if (register_operand (operands[1], TFmode)
3272 || fp_zero_operand (operands[1], TFmode))
3275 if (! reload_in_progress)
3277 operands[0] = validize_mem (operands[0]);
3278 operands[1] = force_reg (TFmode, operands[1]);
3282 /* Fixup PIC cases. */
3285 if (CONSTANT_P (operands[1])
3286 && pic_address_needs_scratch (operands[1]))
3287 operands[1] = legitimize_pic_address (operands[1], TFmode, 0);
3289 if (symbolic_operand (operands[1], TFmode))
3291 operands[1] = legitimize_pic_address (operands[1],
3293 (reload_in_progress ?
3303 ;; Be careful, fmovq and {st,ld}{x,q} do not exist when !arch64 so
3304 ;; we must split them all. :-(
3305 (define_insn "*movtf_insn_sp32"
3306 [(set (match_operand:TF 0 "nonimmediate_operand" "=e,o,U,r")
3307 (match_operand:TF 1 "input_operand" "oe,GeUr,o,roG"))]
3311 && (register_operand (operands[0], TFmode)
3312 || register_operand (operands[1], TFmode)
3313 || fp_zero_operand (operands[1], TFmode))"
3315 [(set_attr "length" "4")])
3317 (define_insn "*movtf_insn_vis_sp32"
3318 [(set (match_operand:TF 0 "nonimmediate_operand" "=e,o,U,r")
3319 (match_operand:TF 1 "input_operand" "Goe,GeUr,o,roG"))]
3323 && (register_operand (operands[0], TFmode)
3324 || register_operand (operands[1], TFmode)
3325 || fp_zero_operand (operands[1], TFmode))"
3327 [(set_attr "length" "4")])
3329 ;; Exactly the same as above, except that all `e' cases are deleted.
3330 ;; This is necessary to prevent reload from ever trying to use a `e' reg
3333 (define_insn "*movtf_no_e_insn_sp32"
3334 [(set (match_operand:TF 0 "nonimmediate_operand" "=o,U,o,r,o")
3335 (match_operand:TF 1 "input_operand" "G,o,U,roG,r"))]
3338 && (register_operand (operands[0], TFmode)
3339 || register_operand (operands[1], TFmode)
3340 || fp_zero_operand (operands[1], TFmode))"
3342 [(set_attr "length" "4")])
3344 ;; Now handle the float reg cases directly when arch64,
3345 ;; hard_quad, and proper reg number alignment are all true.
3346 (define_insn "*movtf_insn_hq_sp64"
3347 [(set (match_operand:TF 0 "nonimmediate_operand" "=e,e,m,o,r")
3348 (match_operand:TF 1 "input_operand" "e,m,e,Gr,roG"))]
3353 && (register_operand (operands[0], TFmode)
3354 || register_operand (operands[1], TFmode)
3355 || fp_zero_operand (operands[1], TFmode))"
3362 [(set_attr "type" "fpmove,fpload,fpstore,*,*")
3363 (set_attr "length" "*,*,*,2,2")])
3365 (define_insn "*movtf_insn_hq_vis_sp64"
3366 [(set (match_operand:TF 0 "nonimmediate_operand" "=e,e,m,eo,r,o")
3367 (match_operand:TF 1 "input_operand" "e,m,e,G,roG,r"))]
3372 && (register_operand (operands[0], TFmode)
3373 || register_operand (operands[1], TFmode)
3374 || fp_zero_operand (operands[1], TFmode))"
3382 [(set_attr "type" "fpmove,fpload,fpstore,*,*,*")
3383 (set_attr "length" "*,*,*,2,2,2")])
3385 ;; Now we allow the integer register cases even when
3386 ;; only arch64 is true.
3387 (define_insn "*movtf_insn_sp64"
3388 [(set (match_operand:TF 0 "nonimmediate_operand" "=e,o,r")
3389 (match_operand:TF 1 "input_operand" "oe,Ger,orG"))]
3393 && ! TARGET_HARD_QUAD
3394 && (register_operand (operands[0], TFmode)
3395 || register_operand (operands[1], TFmode)
3396 || fp_zero_operand (operands[1], TFmode))"
3398 [(set_attr "length" "2")])
3400 (define_insn "*movtf_insn_vis_sp64"
3401 [(set (match_operand:TF 0 "nonimmediate_operand" "=e,o,r")
3402 (match_operand:TF 1 "input_operand" "Goe,Ger,orG"))]
3406 && ! TARGET_HARD_QUAD
3407 && (register_operand (operands[0], TFmode)
3408 || register_operand (operands[1], TFmode)
3409 || fp_zero_operand (operands[1], TFmode))"
3411 [(set_attr "length" "2")])
3413 (define_insn "*movtf_no_e_insn_sp64"
3414 [(set (match_operand:TF 0 "nonimmediate_operand" "=r,o")
3415 (match_operand:TF 1 "input_operand" "orG,rG"))]
3418 && (register_operand (operands[0], TFmode)
3419 || register_operand (operands[1], TFmode)
3420 || fp_zero_operand (operands[1], TFmode))"
3422 [(set_attr "length" "2")])
3424 ;; Now all the splits to handle multi-insn TF mode moves.
3426 [(set (match_operand:TF 0 "register_operand" "")
3427 (match_operand:TF 1 "register_operand" ""))]
3431 && ! TARGET_HARD_QUAD)
3432 || ! fp_register_operand (operands[0], TFmode))"
3433 [(clobber (const_int 0))]
3435 rtx set_dest = operands[0];
3436 rtx set_src = operands[1];
3440 dest1 = gen_df_reg (set_dest, 0);
3441 dest2 = gen_df_reg (set_dest, 1);
3442 src1 = gen_df_reg (set_src, 0);
3443 src2 = gen_df_reg (set_src, 1);
3445 /* Now emit using the real source and destination we found, swapping
3446 the order if we detect overlap. */
3447 if (reg_overlap_mentioned_p (dest1, src2))
3449 emit_insn (gen_movdf (dest2, src2));
3450 emit_insn (gen_movdf (dest1, src1));
3454 emit_insn (gen_movdf (dest1, src1));
3455 emit_insn (gen_movdf (dest2, src2));
3461 [(set (match_operand:TF 0 "nonimmediate_operand" "")
3462 (match_operand:TF 1 "fp_zero_operand" ""))]
3464 [(clobber (const_int 0))]
3466 rtx set_dest = operands[0];
3469 switch (GET_CODE (set_dest))
3472 dest1 = gen_df_reg (set_dest, 0);
3473 dest2 = gen_df_reg (set_dest, 1);
3476 dest1 = adjust_address (set_dest, DFmode, 0);
3477 dest2 = adjust_address (set_dest, DFmode, 8);
3483 emit_insn (gen_movdf (dest1, CONST0_RTX (DFmode)));
3484 emit_insn (gen_movdf (dest2, CONST0_RTX (DFmode)));
3489 [(set (match_operand:TF 0 "register_operand" "")
3490 (match_operand:TF 1 "memory_operand" ""))]
3492 && offsettable_memref_p (operands[1])
3494 || ! TARGET_HARD_QUAD
3495 || ! fp_register_operand (operands[0], TFmode)))"
3496 [(clobber (const_int 0))]
3498 rtx word0 = adjust_address (operands[1], DFmode, 0);
3499 rtx word1 = adjust_address (operands[1], DFmode, 8);
3500 rtx set_dest, dest1, dest2;
3502 set_dest = operands[0];
3504 dest1 = gen_df_reg (set_dest, 0);
3505 dest2 = gen_df_reg (set_dest, 1);
3507 /* Now output, ordering such that we don't clobber any registers
3508 mentioned in the address. */
3509 if (reg_overlap_mentioned_p (dest1, word1))
3512 emit_insn (gen_movdf (dest2, word1));
3513 emit_insn (gen_movdf (dest1, word0));
3517 emit_insn (gen_movdf (dest1, word0));
3518 emit_insn (gen_movdf (dest2, word1));
3524 [(set (match_operand:TF 0 "memory_operand" "")
3525 (match_operand:TF 1 "register_operand" ""))]
3527 && offsettable_memref_p (operands[0])
3529 || ! TARGET_HARD_QUAD
3530 || ! fp_register_operand (operands[1], TFmode)))"
3531 [(clobber (const_int 0))]
3533 rtx set_src = operands[1];
3535 emit_insn (gen_movdf (adjust_address (operands[0], DFmode, 0),
3536 gen_df_reg (set_src, 0)));
3537 emit_insn (gen_movdf (adjust_address (operands[0], DFmode, 8),
3538 gen_df_reg (set_src, 1)));
3542 ;; SPARC V9 conditional move instructions.
3544 ;; We can handle larger constants here for some flavors, but for now we keep
3545 ;; it simple and only allow those constants supported by all flavors.
3546 ;; Note that emit_conditional_move canonicalizes operands 2,3 so that operand
3547 ;; 3 contains the constant if one is present, but we handle either for
3548 ;; generality (sparc.c puts a constant in operand 2).
3550 (define_expand "movqicc"
3551 [(set (match_operand:QI 0 "register_operand" "")
3552 (if_then_else:QI (match_operand 1 "comparison_operator" "")
3553 (match_operand:QI 2 "arith10_operand" "")
3554 (match_operand:QI 3 "arith10_operand" "")))]
3557 enum rtx_code code = GET_CODE (operands[1]);
3559 if (GET_MODE (sparc_compare_op0) == DImode
3563 if (sparc_compare_op1 == const0_rtx
3564 && GET_CODE (sparc_compare_op0) == REG
3565 && GET_MODE (sparc_compare_op0) == DImode
3566 && v9_regcmp_p (code))
3568 operands[1] = gen_rtx_fmt_ee (code, DImode,
3569 sparc_compare_op0, sparc_compare_op1);
3573 rtx cc_reg = gen_compare_reg (code,
3574 sparc_compare_op0, sparc_compare_op1);
3575 operands[1] = gen_rtx_fmt_ee (code, GET_MODE (cc_reg), cc_reg, const0_rtx);
3579 (define_expand "movhicc"
3580 [(set (match_operand:HI 0 "register_operand" "")
3581 (if_then_else:HI (match_operand 1 "comparison_operator" "")
3582 (match_operand:HI 2 "arith10_operand" "")
3583 (match_operand:HI 3 "arith10_operand" "")))]
3586 enum rtx_code code = GET_CODE (operands[1]);
3588 if (GET_MODE (sparc_compare_op0) == DImode
3592 if (sparc_compare_op1 == const0_rtx
3593 && GET_CODE (sparc_compare_op0) == REG
3594 && GET_MODE (sparc_compare_op0) == DImode
3595 && v9_regcmp_p (code))
3597 operands[1] = gen_rtx_fmt_ee (code, DImode,
3598 sparc_compare_op0, sparc_compare_op1);
3602 rtx cc_reg = gen_compare_reg (code,
3603 sparc_compare_op0, sparc_compare_op1);
3604 operands[1] = gen_rtx_fmt_ee (code, GET_MODE (cc_reg), cc_reg, const0_rtx);
3608 (define_expand "movsicc"
3609 [(set (match_operand:SI 0 "register_operand" "")
3610 (if_then_else:SI (match_operand 1 "comparison_operator" "")
3611 (match_operand:SI 2 "arith10_operand" "")
3612 (match_operand:SI 3 "arith10_operand" "")))]
3615 enum rtx_code code = GET_CODE (operands[1]);
3616 enum machine_mode op0_mode = GET_MODE (sparc_compare_op0);
3618 if (sparc_compare_op1 == const0_rtx
3619 && GET_CODE (sparc_compare_op0) == REG
3620 && (TARGET_ARCH64 && op0_mode == DImode && v9_regcmp_p (code)))
3622 operands[1] = gen_rtx_fmt_ee (code, op0_mode,
3623 sparc_compare_op0, sparc_compare_op1);
3627 rtx cc_reg = gen_compare_reg (code,
3628 sparc_compare_op0, sparc_compare_op1);
3629 operands[1] = gen_rtx_fmt_ee (code, GET_MODE (cc_reg),
3630 cc_reg, const0_rtx);
3634 (define_expand "movdicc"
3635 [(set (match_operand:DI 0 "register_operand" "")
3636 (if_then_else:DI (match_operand 1 "comparison_operator" "")
3637 (match_operand:DI 2 "arith10_double_operand" "")
3638 (match_operand:DI 3 "arith10_double_operand" "")))]
3641 enum rtx_code code = GET_CODE (operands[1]);
3643 if (sparc_compare_op1 == const0_rtx
3644 && GET_CODE (sparc_compare_op0) == REG
3645 && GET_MODE (sparc_compare_op0) == DImode
3646 && v9_regcmp_p (code))
3648 operands[1] = gen_rtx_fmt_ee (code, DImode,
3649 sparc_compare_op0, sparc_compare_op1);
3653 rtx cc_reg = gen_compare_reg (code,
3654 sparc_compare_op0, sparc_compare_op1);
3655 operands[1] = gen_rtx_fmt_ee (code, GET_MODE (cc_reg),
3656 cc_reg, const0_rtx);
3660 (define_expand "movsfcc"
3661 [(set (match_operand:SF 0 "register_operand" "")
3662 (if_then_else:SF (match_operand 1 "comparison_operator" "")
3663 (match_operand:SF 2 "register_operand" "")
3664 (match_operand:SF 3 "register_operand" "")))]
3665 "TARGET_V9 && TARGET_FPU"
3667 enum rtx_code code = GET_CODE (operands[1]);
3669 if (GET_MODE (sparc_compare_op0) == DImode
3673 if (sparc_compare_op1 == const0_rtx
3674 && GET_CODE (sparc_compare_op0) == REG
3675 && GET_MODE (sparc_compare_op0) == DImode
3676 && v9_regcmp_p (code))
3678 operands[1] = gen_rtx_fmt_ee (code, DImode,
3679 sparc_compare_op0, sparc_compare_op1);
3683 rtx cc_reg = gen_compare_reg (code,
3684 sparc_compare_op0, sparc_compare_op1);
3685 operands[1] = gen_rtx_fmt_ee (code, GET_MODE (cc_reg), cc_reg, const0_rtx);
3689 (define_expand "movdfcc"
3690 [(set (match_operand:DF 0 "register_operand" "")
3691 (if_then_else:DF (match_operand 1 "comparison_operator" "")
3692 (match_operand:DF 2 "register_operand" "")
3693 (match_operand:DF 3 "register_operand" "")))]
3694 "TARGET_V9 && TARGET_FPU"
3696 enum rtx_code code = GET_CODE (operands[1]);
3698 if (GET_MODE (sparc_compare_op0) == DImode
3702 if (sparc_compare_op1 == const0_rtx
3703 && GET_CODE (sparc_compare_op0) == REG
3704 && GET_MODE (sparc_compare_op0) == DImode
3705 && v9_regcmp_p (code))
3707 operands[1] = gen_rtx_fmt_ee (code, DImode,
3708 sparc_compare_op0, sparc_compare_op1);
3712 rtx cc_reg = gen_compare_reg (code,
3713 sparc_compare_op0, sparc_compare_op1);
3714 operands[1] = gen_rtx_fmt_ee (code, GET_MODE (cc_reg), cc_reg, const0_rtx);
3718 (define_expand "movtfcc"
3719 [(set (match_operand:TF 0 "register_operand" "")
3720 (if_then_else:TF (match_operand 1 "comparison_operator" "")
3721 (match_operand:TF 2 "register_operand" "")
3722 (match_operand:TF 3 "register_operand" "")))]
3723 "TARGET_V9 && TARGET_FPU"
3725 enum rtx_code code = GET_CODE (operands[1]);
3727 if (GET_MODE (sparc_compare_op0) == DImode
3731 if (sparc_compare_op1 == const0_rtx
3732 && GET_CODE (sparc_compare_op0) == REG
3733 && GET_MODE (sparc_compare_op0) == DImode
3734 && v9_regcmp_p (code))
3736 operands[1] = gen_rtx_fmt_ee (code, DImode,
3737 sparc_compare_op0, sparc_compare_op1);
3741 rtx cc_reg = gen_compare_reg (code,
3742 sparc_compare_op0, sparc_compare_op1);
3743 operands[1] = gen_rtx_fmt_ee (code, GET_MODE (cc_reg), cc_reg, const0_rtx);
3747 ;; Conditional move define_insns.
3749 (define_insn "*movqi_cc_sp64"
3750 [(set (match_operand:QI 0 "register_operand" "=r,r")
3751 (if_then_else:QI (match_operator 1 "comparison_operator"
3752 [(match_operand 2 "icc_or_fcc_reg_operand" "X,X")
3754 (match_operand:QI 3 "arith11_operand" "rL,0")
3755 (match_operand:QI 4 "arith11_operand" "0,rL")))]
3759 mov%c1\t%x2, %4, %0"
3760 [(set_attr "type" "cmove")])
3762 (define_insn "*movhi_cc_sp64"
3763 [(set (match_operand:HI 0 "register_operand" "=r,r")
3764 (if_then_else:HI (match_operator 1 "comparison_operator"
3765 [(match_operand 2 "icc_or_fcc_reg_operand" "X,X")
3767 (match_operand:HI 3 "arith11_operand" "rL,0")
3768 (match_operand:HI 4 "arith11_operand" "0,rL")))]
3772 mov%c1\t%x2, %4, %0"
3773 [(set_attr "type" "cmove")])
3775 (define_insn "*movsi_cc_sp64"
3776 [(set (match_operand:SI 0 "register_operand" "=r,r")
3777 (if_then_else:SI (match_operator 1 "comparison_operator"
3778 [(match_operand 2 "icc_or_fcc_reg_operand" "X,X")
3780 (match_operand:SI 3 "arith11_operand" "rL,0")
3781 (match_operand:SI 4 "arith11_operand" "0,rL")))]
3785 mov%c1\t%x2, %4, %0"
3786 [(set_attr "type" "cmove")])
3788 ;; ??? The constraints of operands 3,4 need work.
3789 (define_insn "*movdi_cc_sp64"
3790 [(set (match_operand:DI 0 "register_operand" "=r,r")
3791 (if_then_else:DI (match_operator 1 "comparison_operator"
3792 [(match_operand 2 "icc_or_fcc_reg_operand" "X,X")
3794 (match_operand:DI 3 "arith11_double_operand" "rLH,0")
3795 (match_operand:DI 4 "arith11_double_operand" "0,rLH")))]
3799 mov%c1\t%x2, %4, %0"
3800 [(set_attr "type" "cmove")])
3802 (define_insn "*movdi_cc_sp64_trunc"
3803 [(set (match_operand:SI 0 "register_operand" "=r,r")
3804 (if_then_else:SI (match_operator 1 "comparison_operator"
3805 [(match_operand 2 "icc_or_fcc_reg_operand" "X,X")
3807 (match_operand:SI 3 "arith11_double_operand" "rLH,0")
3808 (match_operand:SI 4 "arith11_double_operand" "0,rLH")))]
3812 mov%c1\t%x2, %4, %0"
3813 [(set_attr "type" "cmove")])
3815 (define_insn "*movsf_cc_sp64"
3816 [(set (match_operand:SF 0 "register_operand" "=f,f")
3817 (if_then_else:SF (match_operator 1 "comparison_operator"
3818 [(match_operand 2 "icc_or_fcc_reg_operand" "X,X")
3820 (match_operand:SF 3 "register_operand" "f,0")
3821 (match_operand:SF 4 "register_operand" "0,f")))]
3822 "TARGET_V9 && TARGET_FPU"
3824 fmovs%C1\t%x2, %3, %0
3825 fmovs%c1\t%x2, %4, %0"
3826 [(set_attr "type" "fpcmove")])
3828 (define_insn "movdf_cc_sp64"
3829 [(set (match_operand:DF 0 "register_operand" "=e,e")
3830 (if_then_else:DF (match_operator 1 "comparison_operator"
3831 [(match_operand 2 "icc_or_fcc_reg_operand" "X,X")
3833 (match_operand:DF 3 "register_operand" "e,0")
3834 (match_operand:DF 4 "register_operand" "0,e")))]
3835 "TARGET_V9 && TARGET_FPU"
3837 fmovd%C1\t%x2, %3, %0
3838 fmovd%c1\t%x2, %4, %0"
3839 [(set_attr "type" "fpcmove")
3840 (set_attr "fptype" "double")])
3842 (define_insn "*movtf_cc_hq_sp64"
3843 [(set (match_operand:TF 0 "register_operand" "=e,e")
3844 (if_then_else:TF (match_operator 1 "comparison_operator"
3845 [(match_operand 2 "icc_or_fcc_reg_operand" "X,X")
3847 (match_operand:TF 3 "register_operand" "e,0")
3848 (match_operand:TF 4 "register_operand" "0,e")))]
3849 "TARGET_V9 && TARGET_FPU && TARGET_HARD_QUAD"
3851 fmovq%C1\t%x2, %3, %0
3852 fmovq%c1\t%x2, %4, %0"
3853 [(set_attr "type" "fpcmove")])
3855 (define_insn_and_split "*movtf_cc_sp64"
3856 [(set (match_operand:TF 0 "register_operand" "=e,e")
3857 (if_then_else:TF (match_operator 1 "comparison_operator"
3858 [(match_operand 2 "icc_or_fcc_reg_operand" "X,X")
3860 (match_operand:TF 3 "register_operand" "e,0")
3861 (match_operand:TF 4 "register_operand" "0,e")))]
3862 "TARGET_V9 && TARGET_FPU && !TARGET_HARD_QUAD"
3864 "&& reload_completed"
3865 [(clobber (const_int 0))]
3867 rtx set_dest = operands[0];
3868 rtx set_srca = operands[3];
3869 rtx set_srcb = operands[4];
3870 int third = rtx_equal_p (set_dest, set_srca);
3872 rtx srca1, srca2, srcb1, srcb2;
3874 dest1 = gen_df_reg (set_dest, 0);
3875 dest2 = gen_df_reg (set_dest, 1);
3876 srca1 = gen_df_reg (set_srca, 0);
3877 srca2 = gen_df_reg (set_srca, 1);
3878 srcb1 = gen_df_reg (set_srcb, 0);
3879 srcb2 = gen_df_reg (set_srcb, 1);
3881 /* Now emit using the real source and destination we found, swapping
3882 the order if we detect overlap. */
3883 if ((third && reg_overlap_mentioned_p (dest1, srcb2))
3884 || (!third && reg_overlap_mentioned_p (dest1, srca2)))
3886 emit_insn (gen_movdf_cc_sp64 (dest2, operands[1], operands[2], srca2, srcb2));
3887 emit_insn (gen_movdf_cc_sp64 (dest1, operands[1], operands[2], srca1, srcb1));
3891 emit_insn (gen_movdf_cc_sp64 (dest1, operands[1], operands[2], srca1, srcb1));
3892 emit_insn (gen_movdf_cc_sp64 (dest2, operands[1], operands[2], srca2, srcb2));
3896 [(set_attr "length" "2")])
3898 (define_insn "*movqi_cc_reg_sp64"
3899 [(set (match_operand:QI 0 "register_operand" "=r,r")
3900 (if_then_else:QI (match_operator 1 "v9_regcmp_op"
3901 [(match_operand:DI 2 "register_operand" "r,r")
3903 (match_operand:QI 3 "arith10_operand" "rM,0")
3904 (match_operand:QI 4 "arith10_operand" "0,rM")))]
3907 movr%D1\t%2, %r3, %0
3908 movr%d1\t%2, %r4, %0"
3909 [(set_attr "type" "cmove")])
3911 (define_insn "*movhi_cc_reg_sp64"
3912 [(set (match_operand:HI 0 "register_operand" "=r,r")
3913 (if_then_else:HI (match_operator 1 "v9_regcmp_op"
3914 [(match_operand:DI 2 "register_operand" "r,r")
3916 (match_operand:HI 3 "arith10_operand" "rM,0")
3917 (match_operand:HI 4 "arith10_operand" "0,rM")))]
3920 movr%D1\t%2, %r3, %0
3921 movr%d1\t%2, %r4, %0"
3922 [(set_attr "type" "cmove")])
3924 (define_insn "*movsi_cc_reg_sp64"
3925 [(set (match_operand:SI 0 "register_operand" "=r,r")
3926 (if_then_else:SI (match_operator 1 "v9_regcmp_op"
3927 [(match_operand:DI 2 "register_operand" "r,r")
3929 (match_operand:SI 3 "arith10_operand" "rM,0")
3930 (match_operand:SI 4 "arith10_operand" "0,rM")))]
3933 movr%D1\t%2, %r3, %0
3934 movr%d1\t%2, %r4, %0"
3935 [(set_attr "type" "cmove")])
3937 ;; ??? The constraints of operands 3,4 need work.
3938 (define_insn "*movdi_cc_reg_sp64"
3939 [(set (match_operand:DI 0 "register_operand" "=r,r")
3940 (if_then_else:DI (match_operator 1 "v9_regcmp_op"
3941 [(match_operand:DI 2 "register_operand" "r,r")
3943 (match_operand:DI 3 "arith10_double_operand" "rMH,0")
3944 (match_operand:DI 4 "arith10_double_operand" "0,rMH")))]
3947 movr%D1\t%2, %r3, %0
3948 movr%d1\t%2, %r4, %0"
3949 [(set_attr "type" "cmove")])
3951 (define_insn "*movdi_cc_reg_sp64_trunc"
3952 [(set (match_operand:SI 0 "register_operand" "=r,r")
3953 (if_then_else:SI (match_operator 1 "v9_regcmp_op"
3954 [(match_operand:DI 2 "register_operand" "r,r")
3956 (match_operand:SI 3 "arith10_double_operand" "rMH,0")
3957 (match_operand:SI 4 "arith10_double_operand" "0,rMH")))]
3960 movr%D1\t%2, %r3, %0
3961 movr%d1\t%2, %r4, %0"
3962 [(set_attr "type" "cmove")])
3964 (define_insn "*movsf_cc_reg_sp64"
3965 [(set (match_operand:SF 0 "register_operand" "=f,f")
3966 (if_then_else:SF (match_operator 1 "v9_regcmp_op"
3967 [(match_operand:DI 2 "register_operand" "r,r")
3969 (match_operand:SF 3 "register_operand" "f,0")
3970 (match_operand:SF 4 "register_operand" "0,f")))]
3971 "TARGET_ARCH64 && TARGET_FPU"
3973 fmovrs%D1\t%2, %3, %0
3974 fmovrs%d1\t%2, %4, %0"
3975 [(set_attr "type" "fpcrmove")])
3977 (define_insn "movdf_cc_reg_sp64"
3978 [(set (match_operand:DF 0 "register_operand" "=e,e")
3979 (if_then_else:DF (match_operator 1 "v9_regcmp_op"
3980 [(match_operand:DI 2 "register_operand" "r,r")
3982 (match_operand:DF 3 "register_operand" "e,0")
3983 (match_operand:DF 4 "register_operand" "0,e")))]
3984 "TARGET_ARCH64 && TARGET_FPU"
3986 fmovrd%D1\t%2, %3, %0
3987 fmovrd%d1\t%2, %4, %0"
3988 [(set_attr "type" "fpcrmove")
3989 (set_attr "fptype" "double")])
3991 (define_insn "*movtf_cc_reg_hq_sp64"
3992 [(set (match_operand:TF 0 "register_operand" "=e,e")
3993 (if_then_else:TF (match_operator 1 "v9_regcmp_op"
3994 [(match_operand:DI 2 "register_operand" "r,r")
3996 (match_operand:TF 3 "register_operand" "e,0")
3997 (match_operand:TF 4 "register_operand" "0,e")))]
3998 "TARGET_ARCH64 && TARGET_FPU && TARGET_HARD_QUAD"
4000 fmovrq%D1\t%2, %3, %0
4001 fmovrq%d1\t%2, %4, %0"
4002 [(set_attr "type" "fpcrmove")])
4004 (define_insn_and_split "*movtf_cc_reg_sp64"
4005 [(set (match_operand:TF 0 "register_operand" "=e,e")
4006 (if_then_else:TF (match_operator 1 "v9_regcmp_op"
4007 [(match_operand:DI 2 "register_operand" "r,r")
4009 (match_operand:TF 3 "register_operand" "e,0")
4010 (match_operand:TF 4 "register_operand" "0,e")))]
4011 "TARGET_ARCH64 && TARGET_FPU && ! TARGET_HARD_QUAD"
4013 "&& reload_completed"
4014 [(clobber (const_int 0))]
4016 rtx set_dest = operands[0];
4017 rtx set_srca = operands[3];
4018 rtx set_srcb = operands[4];
4019 int third = rtx_equal_p (set_dest, set_srca);
4021 rtx srca1, srca2, srcb1, srcb2;
4023 dest1 = gen_df_reg (set_dest, 0);
4024 dest2 = gen_df_reg (set_dest, 1);
4025 srca1 = gen_df_reg (set_srca, 0);
4026 srca2 = gen_df_reg (set_srca, 1);
4027 srcb1 = gen_df_reg (set_srcb, 0);
4028 srcb2 = gen_df_reg (set_srcb, 1);
4030 /* Now emit using the real source and destination we found, swapping
4031 the order if we detect overlap. */
4032 if ((third && reg_overlap_mentioned_p (dest1, srcb2))
4033 || (!third && reg_overlap_mentioned_p (dest1, srca2)))
4035 emit_insn (gen_movdf_cc_reg_sp64 (dest2, operands[1], operands[2], srca2, srcb2));
4036 emit_insn (gen_movdf_cc_reg_sp64 (dest1, operands[1], operands[2], srca1, srcb1));
4040 emit_insn (gen_movdf_cc_reg_sp64 (dest1, operands[1], operands[2], srca1, srcb1));
4041 emit_insn (gen_movdf_cc_reg_sp64 (dest2, operands[1], operands[2], srca2, srcb2));
4045 [(set_attr "length" "2")])
4048 ;;- zero extension instructions
4050 ;; These patterns originally accepted general_operands, however, slightly
4051 ;; better code is generated by only accepting register_operands, and then
4052 ;; letting combine generate the ldu[hb] insns.
4054 (define_expand "zero_extendhisi2"
4055 [(set (match_operand:SI 0 "register_operand" "")
4056 (zero_extend:SI (match_operand:HI 1 "register_operand" "")))]
4059 rtx temp = gen_reg_rtx (SImode);
4060 rtx shift_16 = GEN_INT (16);
4061 int op1_subbyte = 0;
4063 if (GET_CODE (operand1) == SUBREG)
4065 op1_subbyte = SUBREG_BYTE (operand1);
4066 op1_subbyte /= GET_MODE_SIZE (SImode);
4067 op1_subbyte *= GET_MODE_SIZE (SImode);
4068 operand1 = XEXP (operand1, 0);
4071 emit_insn (gen_ashlsi3 (temp, gen_rtx_SUBREG (SImode, operand1, op1_subbyte),
4073 emit_insn (gen_lshrsi3 (operand0, temp, shift_16));
4077 (define_insn "*zero_extendhisi2_insn"
4078 [(set (match_operand:SI 0 "register_operand" "=r")
4079 (zero_extend:SI (match_operand:HI 1 "memory_operand" "m")))]
4082 [(set_attr "type" "load")
4083 (set_attr "us3load_type" "3cycle")])
4085 (define_expand "zero_extendqihi2"
4086 [(set (match_operand:HI 0 "register_operand" "")
4087 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))]
4091 (define_insn "*zero_extendqihi2_insn"
4092 [(set (match_operand:HI 0 "register_operand" "=r,r")
4093 (zero_extend:HI (match_operand:QI 1 "input_operand" "r,m")))]
4094 "GET_CODE (operands[1]) != CONST_INT"
4098 [(set_attr "type" "*,load")
4099 (set_attr "us3load_type" "*,3cycle")])
4101 (define_expand "zero_extendqisi2"
4102 [(set (match_operand:SI 0 "register_operand" "")
4103 (zero_extend:SI (match_operand:QI 1 "register_operand" "")))]
4107 (define_insn "*zero_extendqisi2_insn"
4108 [(set (match_operand:SI 0 "register_operand" "=r,r")
4109 (zero_extend:SI (match_operand:QI 1 "input_operand" "r,m")))]
4110 "GET_CODE (operands[1]) != CONST_INT"
4114 [(set_attr "type" "*,load")
4115 (set_attr "us3load_type" "*,3cycle")])
4117 (define_expand "zero_extendqidi2"
4118 [(set (match_operand:DI 0 "register_operand" "")
4119 (zero_extend:DI (match_operand:QI 1 "register_operand" "")))]
4123 (define_insn "*zero_extendqidi2_insn"
4124 [(set (match_operand:DI 0 "register_operand" "=r,r")
4125 (zero_extend:DI (match_operand:QI 1 "input_operand" "r,m")))]
4126 "TARGET_ARCH64 && GET_CODE (operands[1]) != CONST_INT"
4130 [(set_attr "type" "*,load")
4131 (set_attr "us3load_type" "*,3cycle")])
4133 (define_expand "zero_extendhidi2"
4134 [(set (match_operand:DI 0 "register_operand" "")
4135 (zero_extend:DI (match_operand:HI 1 "register_operand" "")))]
4138 rtx temp = gen_reg_rtx (DImode);
4139 rtx shift_48 = GEN_INT (48);
4140 int op1_subbyte = 0;
4142 if (GET_CODE (operand1) == SUBREG)
4144 op1_subbyte = SUBREG_BYTE (operand1);
4145 op1_subbyte /= GET_MODE_SIZE (DImode);
4146 op1_subbyte *= GET_MODE_SIZE (DImode);
4147 operand1 = XEXP (operand1, 0);
4150 emit_insn (gen_ashldi3 (temp, gen_rtx_SUBREG (DImode, operand1, op1_subbyte),
4152 emit_insn (gen_lshrdi3 (operand0, temp, shift_48));
4156 (define_insn "*zero_extendhidi2_insn"
4157 [(set (match_operand:DI 0 "register_operand" "=r")
4158 (zero_extend:DI (match_operand:HI 1 "memory_operand" "m")))]
4161 [(set_attr "type" "load")
4162 (set_attr "us3load_type" "3cycle")])
4165 ;; ??? Write truncdisi pattern using sra?
4167 (define_expand "zero_extendsidi2"
4168 [(set (match_operand:DI 0 "register_operand" "")
4169 (zero_extend:DI (match_operand:SI 1 "register_operand" "")))]
4173 (define_insn "*zero_extendsidi2_insn_sp64"
4174 [(set (match_operand:DI 0 "register_operand" "=r,r")
4175 (zero_extend:DI (match_operand:SI 1 "input_operand" "r,m")))]
4176 "TARGET_ARCH64 && GET_CODE (operands[1]) != CONST_INT"
4180 [(set_attr "type" "shift,load")])
4182 (define_insn_and_split "*zero_extendsidi2_insn_sp32"
4183 [(set (match_operand:DI 0 "register_operand" "=r")
4184 (zero_extend:DI (match_operand:SI 1 "register_operand" "r")))]
4187 "&& reload_completed"
4188 [(set (match_dup 2) (match_dup 3))
4189 (set (match_dup 4) (match_dup 5))]
4193 dest1 = gen_highpart (SImode, operands[0]);
4194 dest2 = gen_lowpart (SImode, operands[0]);
4196 /* Swap the order in case of overlap. */
4197 if (REGNO (dest1) == REGNO (operands[1]))
4199 operands[2] = dest2;
4200 operands[3] = operands[1];
4201 operands[4] = dest1;
4202 operands[5] = const0_rtx;
4206 operands[2] = dest1;
4207 operands[3] = const0_rtx;
4208 operands[4] = dest2;
4209 operands[5] = operands[1];
4212 [(set_attr "length" "2")])
4214 ;; Simplify comparisons of extended values.
4216 (define_insn "*cmp_zero_extendqisi2"
4218 (compare:CC (zero_extend:SI (match_operand:QI 0 "register_operand" "r"))
4221 "andcc\t%0, 0xff, %%g0"
4222 [(set_attr "type" "compare")])
4224 (define_insn "*cmp_zero_qi"
4226 (compare:CC (match_operand:QI 0 "register_operand" "r")
4229 "andcc\t%0, 0xff, %%g0"
4230 [(set_attr "type" "compare")])
4232 (define_insn "*cmp_zero_extendqisi2_set"
4234 (compare:CC (zero_extend:SI (match_operand:QI 1 "register_operand" "r"))
4236 (set (match_operand:SI 0 "register_operand" "=r")
4237 (zero_extend:SI (match_dup 1)))]
4239 "andcc\t%1, 0xff, %0"
4240 [(set_attr "type" "compare")])
4242 (define_insn "*cmp_zero_extendqisi2_andcc_set"
4244 (compare:CC (and:SI (match_operand:SI 1 "register_operand" "r")
4247 (set (match_operand:SI 0 "register_operand" "=r")
4248 (zero_extend:SI (subreg:QI (match_dup 1) 0)))]
4250 "andcc\t%1, 0xff, %0"
4251 [(set_attr "type" "compare")])
4253 (define_insn "*cmp_zero_extendqidi2"
4255 (compare:CCX (zero_extend:DI (match_operand:QI 0 "register_operand" "r"))
4258 "andcc\t%0, 0xff, %%g0"
4259 [(set_attr "type" "compare")])
4261 (define_insn "*cmp_zero_qi_sp64"
4263 (compare:CCX (match_operand:QI 0 "register_operand" "r")
4266 "andcc\t%0, 0xff, %%g0"
4267 [(set_attr "type" "compare")])
4269 (define_insn "*cmp_zero_extendqidi2_set"
4271 (compare:CCX (zero_extend:DI (match_operand:QI 1 "register_operand" "r"))
4273 (set (match_operand:DI 0 "register_operand" "=r")
4274 (zero_extend:DI (match_dup 1)))]
4276 "andcc\t%1, 0xff, %0"
4277 [(set_attr "type" "compare")])
4279 (define_insn "*cmp_zero_extendqidi2_andcc_set"
4281 (compare:CCX (and:DI (match_operand:DI 1 "register_operand" "r")
4284 (set (match_operand:DI 0 "register_operand" "=r")
4285 (zero_extend:DI (subreg:QI (match_dup 1) 0)))]
4287 "andcc\t%1, 0xff, %0"
4288 [(set_attr "type" "compare")])
4290 ;; Similarly, handle {SI,DI}->QI mode truncation followed by a compare.
4292 (define_insn "*cmp_siqi_trunc"
4294 (compare:CC (subreg:QI (match_operand:SI 0 "register_operand" "r") 3)
4297 "andcc\t%0, 0xff, %%g0"
4298 [(set_attr "type" "compare")])
4300 (define_insn "*cmp_siqi_trunc_set"
4302 (compare:CC (subreg:QI (match_operand:SI 1 "register_operand" "r") 3)
4304 (set (match_operand:QI 0 "register_operand" "=r")
4305 (subreg:QI (match_dup 1) 3))]
4307 "andcc\t%1, 0xff, %0"
4308 [(set_attr "type" "compare")])
4310 (define_insn "*cmp_diqi_trunc"
4312 (compare:CC (subreg:QI (match_operand:DI 0 "register_operand" "r") 7)
4315 "andcc\t%0, 0xff, %%g0"
4316 [(set_attr "type" "compare")])
4318 (define_insn "*cmp_diqi_trunc_set"
4320 (compare:CC (subreg:QI (match_operand:DI 1 "register_operand" "r") 7)
4322 (set (match_operand:QI 0 "register_operand" "=r")
4323 (subreg:QI (match_dup 1) 7))]
4325 "andcc\t%1, 0xff, %0"
4326 [(set_attr "type" "compare")])
4328 ;;- sign extension instructions
4330 ;; These patterns originally accepted general_operands, however, slightly
4331 ;; better code is generated by only accepting register_operands, and then
4332 ;; letting combine generate the lds[hb] insns.
4334 (define_expand "extendhisi2"
4335 [(set (match_operand:SI 0 "register_operand" "")
4336 (sign_extend:SI (match_operand:HI 1 "register_operand" "")))]
4339 rtx temp = gen_reg_rtx (SImode);
4340 rtx shift_16 = GEN_INT (16);
4341 int op1_subbyte = 0;
4343 if (GET_CODE (operand1) == SUBREG)
4345 op1_subbyte = SUBREG_BYTE (operand1);
4346 op1_subbyte /= GET_MODE_SIZE (SImode);
4347 op1_subbyte *= GET_MODE_SIZE (SImode);
4348 operand1 = XEXP (operand1, 0);
4351 emit_insn (gen_ashlsi3 (temp, gen_rtx_SUBREG (SImode, operand1, op1_subbyte),
4353 emit_insn (gen_ashrsi3 (operand0, temp, shift_16));
4357 (define_insn "*sign_extendhisi2_insn"
4358 [(set (match_operand:SI 0 "register_operand" "=r")
4359 (sign_extend:SI (match_operand:HI 1 "memory_operand" "m")))]
4362 [(set_attr "type" "sload")
4363 (set_attr "us3load_type" "3cycle")])
4365 (define_expand "extendqihi2"
4366 [(set (match_operand:HI 0 "register_operand" "")
4367 (sign_extend:HI (match_operand:QI 1 "register_operand" "")))]
4370 rtx temp = gen_reg_rtx (SImode);
4371 rtx shift_24 = GEN_INT (24);
4372 int op1_subbyte = 0;
4373 int op0_subbyte = 0;
4375 if (GET_CODE (operand1) == SUBREG)
4377 op1_subbyte = SUBREG_BYTE (operand1);
4378 op1_subbyte /= GET_MODE_SIZE (SImode);
4379 op1_subbyte *= GET_MODE_SIZE (SImode);
4380 operand1 = XEXP (operand1, 0);
4382 if (GET_CODE (operand0) == SUBREG)
4384 op0_subbyte = SUBREG_BYTE (operand0);
4385 op0_subbyte /= GET_MODE_SIZE (SImode);
4386 op0_subbyte *= GET_MODE_SIZE (SImode);
4387 operand0 = XEXP (operand0, 0);
4389 emit_insn (gen_ashlsi3 (temp, gen_rtx_SUBREG (SImode, operand1, op1_subbyte),
4391 if (GET_MODE (operand0) != SImode)
4392 operand0 = gen_rtx_SUBREG (SImode, operand0, op0_subbyte);
4393 emit_insn (gen_ashrsi3 (operand0, temp, shift_24));
4397 (define_insn "*sign_extendqihi2_insn"
4398 [(set (match_operand:HI 0 "register_operand" "=r")
4399 (sign_extend:HI (match_operand:QI 1 "memory_operand" "m")))]
4402 [(set_attr "type" "sload")
4403 (set_attr "us3load_type" "3cycle")])
4405 (define_expand "extendqisi2"
4406 [(set (match_operand:SI 0 "register_operand" "")
4407 (sign_extend:SI (match_operand:QI 1 "register_operand" "")))]
4410 rtx temp = gen_reg_rtx (SImode);
4411 rtx shift_24 = GEN_INT (24);
4412 int op1_subbyte = 0;
4414 if (GET_CODE (operand1) == SUBREG)
4416 op1_subbyte = SUBREG_BYTE (operand1);
4417 op1_subbyte /= GET_MODE_SIZE (SImode);
4418 op1_subbyte *= GET_MODE_SIZE (SImode);
4419 operand1 = XEXP (operand1, 0);
4422 emit_insn (gen_ashlsi3 (temp, gen_rtx_SUBREG (SImode, operand1, op1_subbyte),
4424 emit_insn (gen_ashrsi3 (operand0, temp, shift_24));
4428 (define_insn "*sign_extendqisi2_insn"
4429 [(set (match_operand:SI 0 "register_operand" "=r")
4430 (sign_extend:SI (match_operand:QI 1 "memory_operand" "m")))]
4433 [(set_attr "type" "sload")
4434 (set_attr "us3load_type" "3cycle")])
4436 (define_expand "extendqidi2"
4437 [(set (match_operand:DI 0 "register_operand" "")
4438 (sign_extend:DI (match_operand:QI 1 "register_operand" "")))]
4441 rtx temp = gen_reg_rtx (DImode);
4442 rtx shift_56 = GEN_INT (56);
4443 int op1_subbyte = 0;
4445 if (GET_CODE (operand1) == SUBREG)
4447 op1_subbyte = SUBREG_BYTE (operand1);
4448 op1_subbyte /= GET_MODE_SIZE (DImode);
4449 op1_subbyte *= GET_MODE_SIZE (DImode);
4450 operand1 = XEXP (operand1, 0);
4453 emit_insn (gen_ashldi3 (temp, gen_rtx_SUBREG (DImode, operand1, op1_subbyte),
4455 emit_insn (gen_ashrdi3 (operand0, temp, shift_56));
4459 (define_insn "*sign_extendqidi2_insn"
4460 [(set (match_operand:DI 0 "register_operand" "=r")
4461 (sign_extend:DI (match_operand:QI 1 "memory_operand" "m")))]
4464 [(set_attr "type" "sload")
4465 (set_attr "us3load_type" "3cycle")])
4467 (define_expand "extendhidi2"
4468 [(set (match_operand:DI 0 "register_operand" "")
4469 (sign_extend:DI (match_operand:HI 1 "register_operand" "")))]
4472 rtx temp = gen_reg_rtx (DImode);
4473 rtx shift_48 = GEN_INT (48);
4474 int op1_subbyte = 0;
4476 if (GET_CODE (operand1) == SUBREG)
4478 op1_subbyte = SUBREG_BYTE (operand1);
4479 op1_subbyte /= GET_MODE_SIZE (DImode);
4480 op1_subbyte *= GET_MODE_SIZE (DImode);
4481 operand1 = XEXP (operand1, 0);
4484 emit_insn (gen_ashldi3 (temp, gen_rtx_SUBREG (DImode, operand1, op1_subbyte),
4486 emit_insn (gen_ashrdi3 (operand0, temp, shift_48));
4490 (define_insn "*sign_extendhidi2_insn"
4491 [(set (match_operand:DI 0 "register_operand" "=r")
4492 (sign_extend:DI (match_operand:HI 1 "memory_operand" "m")))]
4495 [(set_attr "type" "sload")
4496 (set_attr "us3load_type" "3cycle")])
4498 (define_expand "extendsidi2"
4499 [(set (match_operand:DI 0 "register_operand" "")
4500 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))]
4504 (define_insn "*sign_extendsidi2_insn"
4505 [(set (match_operand:DI 0 "register_operand" "=r,r")
4506 (sign_extend:DI (match_operand:SI 1 "input_operand" "r,m")))]
4511 [(set_attr "type" "shift,sload")
4512 (set_attr "us3load_type" "*,3cycle")])
4514 ;; Special pattern for optimizing bit-field compares. This is needed
4515 ;; because combine uses this as a canonical form.
4517 (define_insn "*cmp_zero_extract"
4520 (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
4521 (match_operand:SI 1 "small_int_or_double" "n")
4522 (match_operand:SI 2 "small_int_or_double" "n"))
4524 "(GET_CODE (operands[2]) == CONST_INT
4525 && INTVAL (operands[2]) > 19)
4526 || (GET_CODE (operands[2]) == CONST_DOUBLE
4527 && CONST_DOUBLE_LOW (operands[2]) > 19)"
4529 int len = (GET_CODE (operands[1]) == CONST_INT
4530 ? INTVAL (operands[1])
4531 : CONST_DOUBLE_LOW (operands[1]));
4533 (GET_CODE (operands[2]) == CONST_INT
4534 ? INTVAL (operands[2])
4535 : CONST_DOUBLE_LOW (operands[2])) - len;
4536 HOST_WIDE_INT mask = ((1 << len) - 1) << pos;
4538 operands[1] = GEN_INT (mask);
4539 return "andcc\t%0, %1, %%g0";
4541 [(set_attr "type" "compare")])
4543 (define_insn "*cmp_zero_extract_sp64"
4546 (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
4547 (match_operand:SI 1 "small_int_or_double" "n")
4548 (match_operand:SI 2 "small_int_or_double" "n"))
4551 && ((GET_CODE (operands[2]) == CONST_INT
4552 && INTVAL (operands[2]) > 51)
4553 || (GET_CODE (operands[2]) == CONST_DOUBLE
4554 && CONST_DOUBLE_LOW (operands[2]) > 51))"
4556 int len = (GET_CODE (operands[1]) == CONST_INT
4557 ? INTVAL (operands[1])
4558 : CONST_DOUBLE_LOW (operands[1]));
4560 (GET_CODE (operands[2]) == CONST_INT
4561 ? INTVAL (operands[2])
4562 : CONST_DOUBLE_LOW (operands[2])) - len;
4563 HOST_WIDE_INT mask = (((unsigned HOST_WIDE_INT) 1 << len) - 1) << pos;
4565 operands[1] = GEN_INT (mask);
4566 return "andcc\t%0, %1, %%g0";
4568 [(set_attr "type" "compare")])
4570 ;; Conversions between float, double and long double.
4572 (define_insn "extendsfdf2"
4573 [(set (match_operand:DF 0 "register_operand" "=e")
4575 (match_operand:SF 1 "register_operand" "f")))]
4578 [(set_attr "type" "fp")
4579 (set_attr "fptype" "double")])
4581 (define_expand "extendsftf2"
4582 [(set (match_operand:TF 0 "nonimmediate_operand" "")
4584 (match_operand:SF 1 "register_operand" "")))]
4585 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
4586 "emit_tfmode_cvt (FLOAT_EXTEND, operands); DONE;")
4588 (define_insn "*extendsftf2_hq"
4589 [(set (match_operand:TF 0 "register_operand" "=e")
4591 (match_operand:SF 1 "register_operand" "f")))]
4592 "TARGET_FPU && TARGET_HARD_QUAD"
4594 [(set_attr "type" "fp")])
4596 (define_expand "extenddftf2"
4597 [(set (match_operand:TF 0 "nonimmediate_operand" "")
4599 (match_operand:DF 1 "register_operand" "")))]
4600 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
4601 "emit_tfmode_cvt (FLOAT_EXTEND, operands); DONE;")
4603 (define_insn "*extenddftf2_hq"
4604 [(set (match_operand:TF 0 "register_operand" "=e")
4606 (match_operand:DF 1 "register_operand" "e")))]
4607 "TARGET_FPU && TARGET_HARD_QUAD"
4609 [(set_attr "type" "fp")])
4611 (define_insn "truncdfsf2"
4612 [(set (match_operand:SF 0 "register_operand" "=f")
4614 (match_operand:DF 1 "register_operand" "e")))]
4617 [(set_attr "type" "fp")
4618 (set_attr "fptype" "double")])
4620 (define_expand "trunctfsf2"
4621 [(set (match_operand:SF 0 "register_operand" "")
4623 (match_operand:TF 1 "general_operand" "")))]
4624 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
4625 "emit_tfmode_cvt (FLOAT_TRUNCATE, operands); DONE;")
4627 (define_insn "*trunctfsf2_hq"
4628 [(set (match_operand:SF 0 "register_operand" "=f")
4630 (match_operand:TF 1 "register_operand" "e")))]
4631 "TARGET_FPU && TARGET_HARD_QUAD"
4633 [(set_attr "type" "fp")])
4635 (define_expand "trunctfdf2"
4636 [(set (match_operand:DF 0 "register_operand" "")
4638 (match_operand:TF 1 "general_operand" "")))]
4639 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
4640 "emit_tfmode_cvt (FLOAT_TRUNCATE, operands); DONE;")
4642 (define_insn "*trunctfdf2_hq"
4643 [(set (match_operand:DF 0 "register_operand" "=e")
4645 (match_operand:TF 1 "register_operand" "e")))]
4646 "TARGET_FPU && TARGET_HARD_QUAD"
4648 [(set_attr "type" "fp")])
4650 ;; Conversion between fixed point and floating point.
4652 (define_insn "floatsisf2"
4653 [(set (match_operand:SF 0 "register_operand" "=f")
4654 (float:SF (match_operand:SI 1 "register_operand" "f")))]
4657 [(set_attr "type" "fp")
4658 (set_attr "fptype" "double")])
4660 (define_insn "floatsidf2"
4661 [(set (match_operand:DF 0 "register_operand" "=e")
4662 (float:DF (match_operand:SI 1 "register_operand" "f")))]
4665 [(set_attr "type" "fp")
4666 (set_attr "fptype" "double")])
4668 (define_expand "floatsitf2"
4669 [(set (match_operand:TF 0 "nonimmediate_operand" "")
4670 (float:TF (match_operand:SI 1 "register_operand" "")))]
4671 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
4672 "emit_tfmode_cvt (FLOAT, operands); DONE;")
4674 (define_insn "*floatsitf2_hq"
4675 [(set (match_operand:TF 0 "register_operand" "=e")
4676 (float:TF (match_operand:SI 1 "register_operand" "f")))]
4677 "TARGET_FPU && TARGET_HARD_QUAD"
4679 [(set_attr "type" "fp")])
4681 (define_expand "floatunssitf2"
4682 [(set (match_operand:TF 0 "nonimmediate_operand" "")
4683 (unsigned_float:TF (match_operand:SI 1 "register_operand" "")))]
4684 "TARGET_FPU && TARGET_ARCH64 && ! TARGET_HARD_QUAD"
4685 "emit_tfmode_cvt (UNSIGNED_FLOAT, operands); DONE;")
4687 ;; Now the same for 64 bit sources.
4689 (define_insn "floatdisf2"
4690 [(set (match_operand:SF 0 "register_operand" "=f")
4691 (float:SF (match_operand:DI 1 "register_operand" "e")))]
4692 "TARGET_V9 && TARGET_FPU"
4694 [(set_attr "type" "fp")
4695 (set_attr "fptype" "double")])
4697 (define_expand "floatunsdisf2"
4698 [(use (match_operand:SF 0 "register_operand" ""))
4699 (use (match_operand:DI 1 "general_operand" ""))]
4700 "TARGET_ARCH64 && TARGET_FPU"
4701 "sparc_emit_floatunsdi (operands, SFmode); DONE;")
4703 (define_insn "floatdidf2"
4704 [(set (match_operand:DF 0 "register_operand" "=e")
4705 (float:DF (match_operand:DI 1 "register_operand" "e")))]
4706 "TARGET_V9 && TARGET_FPU"
4708 [(set_attr "type" "fp")
4709 (set_attr "fptype" "double")])
4711 (define_expand "floatunsdidf2"
4712 [(use (match_operand:DF 0 "register_operand" ""))
4713 (use (match_operand:DI 1 "general_operand" ""))]
4714 "TARGET_ARCH64 && TARGET_FPU"
4715 "sparc_emit_floatunsdi (operands, DFmode); DONE;")
4717 (define_expand "floatditf2"
4718 [(set (match_operand:TF 0 "nonimmediate_operand" "")
4719 (float:TF (match_operand:DI 1 "register_operand" "")))]
4720 "TARGET_FPU && TARGET_V9 && (TARGET_HARD_QUAD || TARGET_ARCH64)"
4721 "emit_tfmode_cvt (FLOAT, operands); DONE;")
4723 (define_insn "*floatditf2_hq"
4724 [(set (match_operand:TF 0 "register_operand" "=e")
4725 (float:TF (match_operand:DI 1 "register_operand" "e")))]
4726 "TARGET_V9 && TARGET_FPU && TARGET_HARD_QUAD"
4728 [(set_attr "type" "fp")])
4730 (define_expand "floatunsditf2"
4731 [(set (match_operand:TF 0 "nonimmediate_operand" "")
4732 (unsigned_float:TF (match_operand:DI 1 "register_operand" "")))]
4733 "TARGET_FPU && TARGET_ARCH64 && ! TARGET_HARD_QUAD"
4734 "emit_tfmode_cvt (UNSIGNED_FLOAT, operands); DONE;")
4736 ;; Convert a float to an actual integer.
4737 ;; Truncation is performed as part of the conversion.
4739 (define_insn "fix_truncsfsi2"
4740 [(set (match_operand:SI 0 "register_operand" "=f")
4741 (fix:SI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
4744 [(set_attr "type" "fp")
4745 (set_attr "fptype" "double")])
4747 (define_insn "fix_truncdfsi2"
4748 [(set (match_operand:SI 0 "register_operand" "=f")
4749 (fix:SI (fix:DF (match_operand:DF 1 "register_operand" "e"))))]
4752 [(set_attr "type" "fp")
4753 (set_attr "fptype" "double")])
4755 (define_expand "fix_trunctfsi2"
4756 [(set (match_operand:SI 0 "register_operand" "")
4757 (fix:SI (match_operand:TF 1 "general_operand" "")))]
4758 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
4759 "emit_tfmode_cvt (FIX, operands); DONE;")
4761 (define_insn "*fix_trunctfsi2_hq"
4762 [(set (match_operand:SI 0 "register_operand" "=f")
4763 (fix:SI (match_operand:TF 1 "register_operand" "e")))]
4764 "TARGET_FPU && TARGET_HARD_QUAD"
4766 [(set_attr "type" "fp")])
4768 (define_expand "fixuns_trunctfsi2"
4769 [(set (match_operand:SI 0 "register_operand" "")
4770 (unsigned_fix:SI (match_operand:TF 1 "general_operand" "")))]
4771 "TARGET_FPU && TARGET_ARCH64 && ! TARGET_HARD_QUAD"
4772 "emit_tfmode_cvt (UNSIGNED_FIX, operands); DONE;")
4774 ;; Now the same, for V9 targets
4776 (define_insn "fix_truncsfdi2"
4777 [(set (match_operand:DI 0 "register_operand" "=e")
4778 (fix:DI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
4779 "TARGET_V9 && TARGET_FPU"
4781 [(set_attr "type" "fp")
4782 (set_attr "fptype" "double")])
4784 (define_expand "fixuns_truncsfdi2"
4785 [(use (match_operand:DI 0 "register_operand" ""))
4786 (use (match_operand:SF 1 "general_operand" ""))]
4787 "TARGET_ARCH64 && TARGET_FPU"
4788 "sparc_emit_fixunsdi (operands, SFmode); DONE;")
4790 (define_insn "fix_truncdfdi2"
4791 [(set (match_operand:DI 0 "register_operand" "=e")
4792 (fix:DI (fix:DF (match_operand:DF 1 "register_operand" "e"))))]
4793 "TARGET_V9 && TARGET_FPU"
4795 [(set_attr "type" "fp")
4796 (set_attr "fptype" "double")])
4798 (define_expand "fixuns_truncdfdi2"
4799 [(use (match_operand:DI 0 "register_operand" ""))
4800 (use (match_operand:DF 1 "general_operand" ""))]
4801 "TARGET_ARCH64 && TARGET_FPU"
4802 "sparc_emit_fixunsdi (operands, DFmode); DONE;")
4804 (define_expand "fix_trunctfdi2"
4805 [(set (match_operand:DI 0 "register_operand" "")
4806 (fix:DI (match_operand:TF 1 "general_operand" "")))]
4807 "TARGET_V9 && TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
4808 "emit_tfmode_cvt (FIX, operands); DONE;")
4810 (define_insn "*fix_trunctfdi2_hq"
4811 [(set (match_operand:DI 0 "register_operand" "=e")
4812 (fix:DI (match_operand:TF 1 "register_operand" "e")))]
4813 "TARGET_V9 && TARGET_FPU && TARGET_HARD_QUAD"
4815 [(set_attr "type" "fp")])
4817 (define_expand "fixuns_trunctfdi2"
4818 [(set (match_operand:DI 0 "register_operand" "")
4819 (unsigned_fix:DI (match_operand:TF 1 "general_operand" "")))]
4820 "TARGET_FPU && TARGET_ARCH64 && ! TARGET_HARD_QUAD"
4821 "emit_tfmode_cvt (UNSIGNED_FIX, operands); DONE;")
4823 ;;- arithmetic instructions
4825 (define_expand "adddi3"
4826 [(set (match_operand:DI 0 "register_operand" "")
4827 (plus:DI (match_operand:DI 1 "register_operand" "")
4828 (match_operand:DI 2 "arith_double_add_operand" "")))]
4831 if (! TARGET_ARCH64)
4833 emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2,
4834 gen_rtx_SET (VOIDmode, operands[0],
4835 gen_rtx_PLUS (DImode, operands[1],
4837 gen_rtx_CLOBBER (VOIDmode,
4838 gen_rtx_REG (CCmode, SPARC_ICC_REG)))));
4843 (define_insn_and_split "adddi3_insn_sp32"
4844 [(set (match_operand:DI 0 "register_operand" "=r")
4845 (plus:DI (match_operand:DI 1 "arith_double_operand" "%r")
4846 (match_operand:DI 2 "arith_double_operand" "rHI")))
4847 (clobber (reg:CC 100))]
4850 "&& reload_completed"
4851 [(parallel [(set (reg:CC_NOOV 100)
4852 (compare:CC_NOOV (plus:SI (match_dup 4)
4856 (plus:SI (match_dup 4) (match_dup 5)))])
4858 (plus:SI (plus:SI (match_dup 7)
4860 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))]
4862 operands[3] = gen_lowpart (SImode, operands[0]);
4863 operands[4] = gen_lowpart (SImode, operands[1]);
4864 operands[5] = gen_lowpart (SImode, operands[2]);
4865 operands[6] = gen_highpart (SImode, operands[0]);
4866 operands[7] = gen_highpart_mode (SImode, DImode, operands[1]);
4867 #if HOST_BITS_PER_WIDE_INT == 32
4868 if (GET_CODE (operands[2]) == CONST_INT)
4870 if (INTVAL (operands[2]) < 0)
4871 operands[8] = constm1_rtx;
4873 operands[8] = const0_rtx;
4877 operands[8] = gen_highpart_mode (SImode, DImode, operands[2]);
4879 [(set_attr "length" "2")])
4882 [(set (match_operand:DI 0 "register_operand" "")
4883 (minus:DI (match_operand:DI 1 "arith_double_operand" "")
4884 (match_operand:DI 2 "arith_double_operand" "")))
4885 (clobber (reg:CC 100))]
4886 "! TARGET_ARCH64 && reload_completed"
4887 [(parallel [(set (reg:CC_NOOV 100)
4888 (compare:CC_NOOV (minus:SI (match_dup 4)
4892 (minus:SI (match_dup 4) (match_dup 5)))])
4894 (minus:SI (minus:SI (match_dup 7)
4896 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))]
4898 operands[3] = gen_lowpart (SImode, operands[0]);
4899 operands[4] = gen_lowpart (SImode, operands[1]);
4900 operands[5] = gen_lowpart (SImode, operands[2]);
4901 operands[6] = gen_highpart (SImode, operands[0]);
4902 operands[7] = gen_highpart (SImode, operands[1]);
4903 #if HOST_BITS_PER_WIDE_INT == 32
4904 if (GET_CODE (operands[2]) == CONST_INT)
4906 if (INTVAL (operands[2]) < 0)
4907 operands[8] = constm1_rtx;
4909 operands[8] = const0_rtx;
4913 operands[8] = gen_highpart_mode (SImode, DImode, operands[2]);
4916 ;; LTU here means "carry set"
4918 [(set (match_operand:SI 0 "register_operand" "=r")
4919 (plus:SI (plus:SI (match_operand:SI 1 "arith_operand" "%r")
4920 (match_operand:SI 2 "arith_operand" "rI"))
4921 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))]
4924 [(set_attr "type" "ialuX")])
4926 (define_insn_and_split "*addx_extend_sp32"
4927 [(set (match_operand:DI 0 "register_operand" "=r")
4928 (zero_extend:DI (plus:SI (plus:SI
4929 (match_operand:SI 1 "reg_or_0_operand" "%rJ")
4930 (match_operand:SI 2 "arith_operand" "rI"))
4931 (ltu:SI (reg:CC_NOOV 100) (const_int 0)))))]
4934 "&& reload_completed"
4935 [(set (match_dup 3) (plus:SI (plus:SI (match_dup 1) (match_dup 2))
4936 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))
4937 (set (match_dup 4) (const_int 0))]
4938 "operands[3] = gen_lowpart (SImode, operands[0]);
4939 operands[4] = gen_highpart_mode (SImode, DImode, operands[1]);"
4940 [(set_attr "length" "2")])
4942 (define_insn "*addx_extend_sp64"
4943 [(set (match_operand:DI 0 "register_operand" "=r")
4944 (zero_extend:DI (plus:SI (plus:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ")
4945 (match_operand:SI 2 "arith_operand" "rI"))
4946 (ltu:SI (reg:CC_NOOV 100) (const_int 0)))))]
4949 [(set_attr "type" "ialuX")])
4952 [(set (match_operand:SI 0 "register_operand" "=r")
4953 (minus:SI (minus:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
4954 (match_operand:SI 2 "arith_operand" "rI"))
4955 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))]
4958 [(set_attr "type" "ialuX")])
4960 (define_insn "*subx_extend_sp64"
4961 [(set (match_operand:DI 0 "register_operand" "=r")
4962 (zero_extend:DI (minus:SI (minus:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
4963 (match_operand:SI 2 "arith_operand" "rI"))
4964 (ltu:SI (reg:CC_NOOV 100) (const_int 0)))))]
4967 [(set_attr "type" "ialuX")])
4969 (define_insn_and_split "*subx_extend"
4970 [(set (match_operand:DI 0 "register_operand" "=r")
4971 (zero_extend:DI (minus:SI (minus:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
4972 (match_operand:SI 2 "arith_operand" "rI"))
4973 (ltu:SI (reg:CC_NOOV 100) (const_int 0)))))]
4976 "&& reload_completed"
4977 [(set (match_dup 3) (minus:SI (minus:SI (match_dup 1) (match_dup 2))
4978 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))
4979 (set (match_dup 4) (const_int 0))]
4980 "operands[3] = gen_lowpart (SImode, operands[0]);
4981 operands[4] = gen_highpart (SImode, operands[0]);"
4982 [(set_attr "length" "2")])
4984 (define_insn_and_split ""
4985 [(set (match_operand:DI 0 "register_operand" "=r")
4986 (plus:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
4987 (match_operand:DI 2 "register_operand" "r")))
4988 (clobber (reg:CC 100))]
4991 "&& reload_completed"
4992 [(parallel [(set (reg:CC_NOOV 100)
4993 (compare:CC_NOOV (plus:SI (match_dup 3) (match_dup 1))
4995 (set (match_dup 5) (plus:SI (match_dup 3) (match_dup 1)))])
4997 (plus:SI (plus:SI (match_dup 4) (const_int 0))
4998 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))]
4999 "operands[3] = gen_lowpart (SImode, operands[2]);
5000 operands[4] = gen_highpart (SImode, operands[2]);
5001 operands[5] = gen_lowpart (SImode, operands[0]);
5002 operands[6] = gen_highpart (SImode, operands[0]);"
5003 [(set_attr "length" "2")])
5005 (define_insn "*adddi3_sp64"
5006 [(set (match_operand:DI 0 "register_operand" "=r,r")
5007 (plus:DI (match_operand:DI 1 "register_operand" "%r,r")
5008 (match_operand:DI 2 "arith_double_add_operand" "rHI,O")))]
5014 (define_insn "addsi3"
5015 [(set (match_operand:SI 0 "register_operand" "=r,r,d")
5016 (plus:SI (match_operand:SI 1 "register_operand" "%r,r,d")
5017 (match_operand:SI 2 "arith_add_operand" "rI,O,d")))]
5022 fpadd32s\t%1, %2, %0"
5023 [(set_attr "type" "*,*,fga")])
5025 (define_insn "*cmp_cc_plus"
5026 [(set (reg:CC_NOOV 100)
5027 (compare:CC_NOOV (plus:SI (match_operand:SI 0 "arith_operand" "%r")
5028 (match_operand:SI 1 "arith_operand" "rI"))
5031 "addcc\t%0, %1, %%g0"
5032 [(set_attr "type" "compare")])
5034 (define_insn "*cmp_ccx_plus"
5035 [(set (reg:CCX_NOOV 100)
5036 (compare:CCX_NOOV (plus:DI (match_operand:DI 0 "arith_double_operand" "%r")
5037 (match_operand:DI 1 "arith_double_operand" "rHI"))
5040 "addcc\t%0, %1, %%g0"
5041 [(set_attr "type" "compare")])
5043 (define_insn "*cmp_cc_plus_set"
5044 [(set (reg:CC_NOOV 100)
5045 (compare:CC_NOOV (plus:SI (match_operand:SI 1 "arith_operand" "%r")
5046 (match_operand:SI 2 "arith_operand" "rI"))
5048 (set (match_operand:SI 0 "register_operand" "=r")
5049 (plus:SI (match_dup 1) (match_dup 2)))]
5052 [(set_attr "type" "compare")])
5054 (define_insn "*cmp_ccx_plus_set"
5055 [(set (reg:CCX_NOOV 100)
5056 (compare:CCX_NOOV (plus:DI (match_operand:DI 1 "arith_double_operand" "%r")
5057 (match_operand:DI 2 "arith_double_operand" "rHI"))
5059 (set (match_operand:DI 0 "register_operand" "=r")
5060 (plus:DI (match_dup 1) (match_dup 2)))]
5063 [(set_attr "type" "compare")])
5065 (define_expand "subdi3"
5066 [(set (match_operand:DI 0 "register_operand" "")
5067 (minus:DI (match_operand:DI 1 "register_operand" "")
5068 (match_operand:DI 2 "arith_double_add_operand" "")))]
5071 if (! TARGET_ARCH64)
5073 emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2,
5074 gen_rtx_SET (VOIDmode, operands[0],
5075 gen_rtx_MINUS (DImode, operands[1],
5077 gen_rtx_CLOBBER (VOIDmode,
5078 gen_rtx_REG (CCmode, SPARC_ICC_REG)))));
5083 (define_insn_and_split "*subdi3_sp32"
5084 [(set (match_operand:DI 0 "register_operand" "=r")
5085 (minus:DI (match_operand:DI 1 "register_operand" "r")
5086 (match_operand:DI 2 "arith_double_operand" "rHI")))
5087 (clobber (reg:CC 100))]
5090 "&& reload_completed
5091 && (GET_CODE (operands[2]) == CONST_INT
5092 || GET_CODE (operands[2]) == CONST_DOUBLE)"
5093 [(clobber (const_int 0))]
5097 highp = gen_highpart_mode (SImode, DImode, operands[2]);
5098 lowp = gen_lowpart (SImode, operands[2]);
5099 if ((lowp == const0_rtx)
5100 && (operands[0] == operands[1]))
5102 emit_insn (gen_rtx_SET (VOIDmode,
5103 gen_highpart (SImode, operands[0]),
5104 gen_rtx_MINUS (SImode,
5105 gen_highpart_mode (SImode, DImode,
5111 emit_insn (gen_cmp_minus_cc_set (gen_lowpart (SImode, operands[0]),
5112 gen_lowpart (SImode, operands[1]),
5114 emit_insn (gen_subx (gen_highpart (SImode, operands[0]),
5115 gen_highpart_mode (SImode, DImode, operands[1]),
5120 [(set_attr "length" "2")])
5123 [(set (match_operand:DI 0 "register_operand" "")
5124 (minus:DI (match_operand:DI 1 "register_operand" "")
5125 (match_operand:DI 2 "register_operand" "")))
5126 (clobber (reg:CC 100))]
5128 && reload_completed"
5129 [(clobber (const_int 0))]
5131 emit_insn (gen_cmp_minus_cc_set (gen_lowpart (SImode, operands[0]),
5132 gen_lowpart (SImode, operands[1]),
5133 gen_lowpart (SImode, operands[2])));
5134 emit_insn (gen_subx (gen_highpart (SImode, operands[0]),
5135 gen_highpart (SImode, operands[1]),
5136 gen_highpart (SImode, operands[2])));
5140 (define_insn_and_split ""
5141 [(set (match_operand:DI 0 "register_operand" "=r")
5142 (minus:DI (match_operand:DI 1 "register_operand" "r")
5143 (zero_extend:DI (match_operand:SI 2 "register_operand" "r"))))
5144 (clobber (reg:CC 100))]
5147 "&& reload_completed"
5148 [(parallel [(set (reg:CC_NOOV 100)
5149 (compare:CC_NOOV (minus:SI (match_dup 3) (match_dup 2))
5151 (set (match_dup 5) (minus:SI (match_dup 3) (match_dup 2)))])
5153 (minus:SI (minus:SI (match_dup 4) (const_int 0))
5154 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))]
5155 "operands[3] = gen_lowpart (SImode, operands[1]);
5156 operands[4] = gen_highpart (SImode, operands[1]);
5157 operands[5] = gen_lowpart (SImode, operands[0]);
5158 operands[6] = gen_highpart (SImode, operands[0]);"
5159 [(set_attr "length" "2")])
5161 (define_insn "*subdi3_sp64"
5162 [(set (match_operand:DI 0 "register_operand" "=r,r")
5163 (minus:DI (match_operand:DI 1 "register_operand" "r,r")
5164 (match_operand:DI 2 "arith_double_add_operand" "rHI,O")))]
5170 (define_insn "subsi3"
5171 [(set (match_operand:SI 0 "register_operand" "=r,r,d")
5172 (minus:SI (match_operand:SI 1 "register_operand" "r,r,d")
5173 (match_operand:SI 2 "arith_add_operand" "rI,O,d")))]
5178 fpsub32s\t%1, %2, %0"
5179 [(set_attr "type" "*,*,fga")])
5181 (define_insn "*cmp_minus_cc"
5182 [(set (reg:CC_NOOV 100)
5183 (compare:CC_NOOV (minus:SI (match_operand:SI 0 "reg_or_0_operand" "rJ")
5184 (match_operand:SI 1 "arith_operand" "rI"))
5187 "subcc\t%r0, %1, %%g0"
5188 [(set_attr "type" "compare")])
5190 (define_insn "*cmp_minus_ccx"
5191 [(set (reg:CCX_NOOV 100)
5192 (compare:CCX_NOOV (minus:DI (match_operand:DI 0 "register_operand" "r")
5193 (match_operand:DI 1 "arith_double_operand" "rHI"))
5196 "subcc\t%0, %1, %%g0"
5197 [(set_attr "type" "compare")])
5199 (define_insn "cmp_minus_cc_set"
5200 [(set (reg:CC_NOOV 100)
5201 (compare:CC_NOOV (minus:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
5202 (match_operand:SI 2 "arith_operand" "rI"))
5204 (set (match_operand:SI 0 "register_operand" "=r")
5205 (minus:SI (match_dup 1) (match_dup 2)))]
5207 "subcc\t%r1, %2, %0"
5208 [(set_attr "type" "compare")])
5210 (define_insn "*cmp_minus_ccx_set"
5211 [(set (reg:CCX_NOOV 100)
5212 (compare:CCX_NOOV (minus:DI (match_operand:DI 1 "register_operand" "r")
5213 (match_operand:DI 2 "arith_double_operand" "rHI"))
5215 (set (match_operand:DI 0 "register_operand" "=r")
5216 (minus:DI (match_dup 1) (match_dup 2)))]
5219 [(set_attr "type" "compare")])
5221 ;; Integer Multiply/Divide.
5223 ;; The 32 bit multiply/divide instructions are deprecated on v9, but at
5224 ;; least in UltraSPARC I, II and IIi it is a win tick-wise.
5226 (define_insn "mulsi3"
5227 [(set (match_operand:SI 0 "register_operand" "=r")
5228 (mult:SI (match_operand:SI 1 "arith_operand" "%r")
5229 (match_operand:SI 2 "arith_operand" "rI")))]
5232 [(set_attr "type" "imul")])
5234 (define_expand "muldi3"
5235 [(set (match_operand:DI 0 "register_operand" "=r")
5236 (mult:DI (match_operand:DI 1 "arith_double_operand" "%r")
5237 (match_operand:DI 2 "arith_double_operand" "rHI")))]
5238 "TARGET_ARCH64 || TARGET_V8PLUS"
5242 emit_insn (gen_muldi3_v8plus (operands[0], operands[1], operands[2]));
5247 (define_insn "*muldi3_sp64"
5248 [(set (match_operand:DI 0 "register_operand" "=r")
5249 (mult:DI (match_operand:DI 1 "arith_double_operand" "%r")
5250 (match_operand:DI 2 "arith_double_operand" "rHI")))]
5253 [(set_attr "type" "imul")])
5255 ;; V8plus wide multiply.
5257 (define_insn "muldi3_v8plus"
5258 [(set (match_operand:DI 0 "register_operand" "=r,h")
5259 (mult:DI (match_operand:DI 1 "arith_double_operand" "%r,0")
5260 (match_operand:DI 2 "arith_double_operand" "rI,rI")))
5261 (clobber (match_scratch:SI 3 "=&h,X"))
5262 (clobber (match_scratch:SI 4 "=&h,X"))]
5265 if (sparc_check_64 (operands[1], insn) <= 0)
5266 output_asm_insn ("srl\t%L1, 0, %L1", operands);
5267 if (which_alternative == 1)
5268 output_asm_insn ("sllx\t%H1, 32, %H1", operands);
5269 if (GET_CODE (operands[2]) == CONST_INT)
5271 if (which_alternative == 1)
5272 return "or\t%L1, %H1, %H1\n\tmulx\t%H1, %2, %L0\;srlx\t%L0, 32, %H0";
5274 return "sllx\t%H1, 32, %3\n\tor\t%L1, %3, %3\n\tmulx\t%3, %2, %3\n\tsrlx\t%3, 32, %H0\n\tmov\t%3, %L0";
5276 else if (rtx_equal_p (operands[1], operands[2]))
5278 if (which_alternative == 1)
5279 return "or\t%L1, %H1, %H1\n\tmulx\t%H1, %H1, %L0\;srlx\t%L0, 32, %H0";
5281 return "sllx\t%H1, 32, %3\n\tor\t%L1, %3, %3\n\tmulx\t%3, %3, %3\n\tsrlx\t%3, 32, %H0\n\tmov\t%3, %L0";
5283 if (sparc_check_64 (operands[2], insn) <= 0)
5284 output_asm_insn ("srl\t%L2, 0, %L2", operands);
5285 if (which_alternative == 1)
5286 return "or\t%L1, %H1, %H1\n\tsllx\t%H2, 32, %L1\n\tor\t%L2, %L1, %L1\n\tmulx\t%H1, %L1, %L0\;srlx\t%L0, 32, %H0";
5288 return "sllx\t%H1, 32, %3\n\tsllx\t%H2, 32, %4\n\tor\t%L1, %3, %3\n\tor\t%L2, %4, %4\n\tmulx\t%3, %4, %3\n\tsrlx\t%3, 32, %H0\n\tmov\t%3, %L0";
5290 [(set_attr "type" "multi")
5291 (set_attr "length" "9,8")])
5293 (define_insn "*cmp_mul_set"
5295 (compare:CC (mult:SI (match_operand:SI 1 "arith_operand" "%r")
5296 (match_operand:SI 2 "arith_operand" "rI"))
5298 (set (match_operand:SI 0 "register_operand" "=r")
5299 (mult:SI (match_dup 1) (match_dup 2)))]
5300 "TARGET_V8 || TARGET_SPARCLITE || TARGET_DEPRECATED_V8_INSNS"
5301 "smulcc\t%1, %2, %0"
5302 [(set_attr "type" "imul")])
5304 (define_expand "mulsidi3"
5305 [(set (match_operand:DI 0 "register_operand" "")
5306 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" ""))
5307 (sign_extend:DI (match_operand:SI 2 "arith_operand" ""))))]
5310 if (CONSTANT_P (operands[2]))
5313 emit_insn (gen_const_mulsidi3_v8plus (operands[0], operands[1],
5315 else if (TARGET_ARCH32)
5316 emit_insn (gen_const_mulsidi3_sp32 (operands[0], operands[1],
5319 emit_insn (gen_const_mulsidi3_sp64 (operands[0], operands[1],
5325 emit_insn (gen_mulsidi3_v8plus (operands[0], operands[1], operands[2]));
5330 ;; V9 puts the 64 bit product in a 64 bit register. Only out or global
5331 ;; registers can hold 64 bit values in the V8plus environment.
5333 (define_insn "mulsidi3_v8plus"
5334 [(set (match_operand:DI 0 "register_operand" "=h,r")
5335 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
5336 (sign_extend:DI (match_operand:SI 2 "register_operand" "r,r"))))
5337 (clobber (match_scratch:SI 3 "=X,&h"))]
5340 smul\t%1, %2, %L0\n\tsrlx\t%L0, 32, %H0
5341 smul\t%1, %2, %3\n\tsrlx\t%3, 32, %H0\n\tmov\t%3, %L0"
5342 [(set_attr "type" "multi")
5343 (set_attr "length" "2,3")])
5346 (define_insn "const_mulsidi3_v8plus"
5347 [(set (match_operand:DI 0 "register_operand" "=h,r")
5348 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
5349 (match_operand:DI 2 "small_int" "I,I")))
5350 (clobber (match_scratch:SI 3 "=X,&h"))]
5353 smul\t%1, %2, %L0\n\tsrlx\t%L0, 32, %H0
5354 smul\t%1, %2, %3\n\tsrlx\t%3, 32, %H0\n\tmov\t%3, %L0"
5355 [(set_attr "type" "multi")
5356 (set_attr "length" "2,3")])
5359 (define_insn "*mulsidi3_sp32"
5360 [(set (match_operand:DI 0 "register_operand" "=r")
5361 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
5362 (sign_extend:DI (match_operand:SI 2 "register_operand" "r"))))]
5365 return TARGET_SPARCLET
5366 ? "smuld\t%1, %2, %L0"
5367 : "smul\t%1, %2, %L0\n\trd\t%%y, %H0";
5370 (if_then_else (eq_attr "isa" "sparclet")
5371 (const_string "imul") (const_string "multi")))
5372 (set (attr "length")
5373 (if_then_else (eq_attr "isa" "sparclet")
5374 (const_int 1) (const_int 2)))])
5376 (define_insn "*mulsidi3_sp64"
5377 [(set (match_operand:DI 0 "register_operand" "=r")
5378 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
5379 (sign_extend:DI (match_operand:SI 2 "register_operand" "r"))))]
5380 "TARGET_DEPRECATED_V8_INSNS && TARGET_ARCH64"
5382 [(set_attr "type" "imul")])
5384 ;; Extra pattern, because sign_extend of a constant isn't valid.
5387 (define_insn "const_mulsidi3_sp32"
5388 [(set (match_operand:DI 0 "register_operand" "=r")
5389 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
5390 (match_operand:DI 2 "small_int" "I")))]
5393 return TARGET_SPARCLET
5394 ? "smuld\t%1, %2, %L0"
5395 : "smul\t%1, %2, %L0\n\trd\t%%y, %H0";
5398 (if_then_else (eq_attr "isa" "sparclet")
5399 (const_string "imul") (const_string "multi")))
5400 (set (attr "length")
5401 (if_then_else (eq_attr "isa" "sparclet")
5402 (const_int 1) (const_int 2)))])
5404 (define_insn "const_mulsidi3_sp64"
5405 [(set (match_operand:DI 0 "register_operand" "=r")
5406 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
5407 (match_operand:DI 2 "small_int" "I")))]
5408 "TARGET_DEPRECATED_V8_INSNS && TARGET_ARCH64"
5410 [(set_attr "type" "imul")])
5412 (define_expand "smulsi3_highpart"
5413 [(set (match_operand:SI 0 "register_operand" "")
5415 (lshiftrt:DI (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" ""))
5416 (sign_extend:DI (match_operand:SI 2 "arith_operand" "")))
5418 "TARGET_HARD_MUL && TARGET_ARCH32"
5420 if (CONSTANT_P (operands[2]))
5424 emit_insn (gen_const_smulsi3_highpart_v8plus (operands[0],
5430 emit_insn (gen_const_smulsi3_highpart (operands[0], operands[1], operands[2]));
5435 emit_insn (gen_smulsi3_highpart_v8plus (operands[0], operands[1],
5436 operands[2], GEN_INT (32)));
5442 (define_insn "smulsi3_highpart_v8plus"
5443 [(set (match_operand:SI 0 "register_operand" "=h,r")
5445 (lshiftrt:DI (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
5446 (sign_extend:DI (match_operand:SI 2 "register_operand" "r,r")))
5447 (match_operand:SI 3 "const_int_operand" "i,i"))))
5448 (clobber (match_scratch:SI 4 "=X,&h"))]
5451 smul\t%1, %2, %0\;srlx\t%0, %3, %0
5452 smul\t%1, %2, %4\;srlx\t%4, %3, %0"
5453 [(set_attr "type" "multi")
5454 (set_attr "length" "2")])
5456 ;; The combiner changes TRUNCATE in the previous pattern to SUBREG.
5459 [(set (match_operand:SI 0 "register_operand" "=h,r")
5462 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
5463 (sign_extend:DI (match_operand:SI 2 "register_operand" "r,r")))
5464 (match_operand:SI 3 "const_int_operand" "i,i"))
5466 (clobber (match_scratch:SI 4 "=X,&h"))]
5469 smul\t%1, %2, %0\n\tsrlx\t%0, %3, %0
5470 smul\t%1, %2, %4\n\tsrlx\t%4, %3, %0"
5471 [(set_attr "type" "multi")
5472 (set_attr "length" "2")])
5475 (define_insn "const_smulsi3_highpart_v8plus"
5476 [(set (match_operand:SI 0 "register_operand" "=h,r")
5478 (lshiftrt:DI (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
5479 (match_operand:DI 2 "small_int" "i,i"))
5480 (match_operand:SI 3 "const_int_operand" "i,i"))))
5481 (clobber (match_scratch:SI 4 "=X,&h"))]
5484 smul\t%1, %2, %0\n\tsrlx\t%0, %3, %0
5485 smul\t%1, %2, %4\n\tsrlx\t%4, %3, %0"
5486 [(set_attr "type" "multi")
5487 (set_attr "length" "2")])
5490 (define_insn "*smulsi3_highpart_sp32"
5491 [(set (match_operand:SI 0 "register_operand" "=r")
5493 (lshiftrt:DI (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
5494 (sign_extend:DI (match_operand:SI 2 "register_operand" "r")))
5497 "smul\t%1, %2, %%g0\n\trd\t%%y, %0"
5498 [(set_attr "type" "multi")
5499 (set_attr "length" "2")])
5502 (define_insn "const_smulsi3_highpart"
5503 [(set (match_operand:SI 0 "register_operand" "=r")
5505 (lshiftrt:DI (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
5506 (match_operand:DI 2 "small_int" "i"))
5509 "smul\t%1, %2, %%g0\n\trd\t%%y, %0"
5510 [(set_attr "type" "multi")
5511 (set_attr "length" "2")])
5513 (define_expand "umulsidi3"
5514 [(set (match_operand:DI 0 "register_operand" "")
5515 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" ""))
5516 (zero_extend:DI (match_operand:SI 2 "uns_arith_operand" ""))))]
5519 if (CONSTANT_P (operands[2]))
5522 emit_insn (gen_const_umulsidi3_v8plus (operands[0], operands[1],
5524 else if (TARGET_ARCH32)
5525 emit_insn (gen_const_umulsidi3_sp32 (operands[0], operands[1],
5528 emit_insn (gen_const_umulsidi3_sp64 (operands[0], operands[1],
5534 emit_insn (gen_umulsidi3_v8plus (operands[0], operands[1], operands[2]));
5540 (define_insn "umulsidi3_v8plus"
5541 [(set (match_operand:DI 0 "register_operand" "=h,r")
5542 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
5543 (zero_extend:DI (match_operand:SI 2 "register_operand" "r,r"))))
5544 (clobber (match_scratch:SI 3 "=X,&h"))]
5547 umul\t%1, %2, %L0\n\tsrlx\t%L0, 32, %H0
5548 umul\t%1, %2, %3\n\tsrlx\t%3, 32, %H0\n\tmov\t%3, %L0"
5549 [(set_attr "type" "multi")
5550 (set_attr "length" "2,3")])
5553 (define_insn "*umulsidi3_sp32"
5554 [(set (match_operand:DI 0 "register_operand" "=r")
5555 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
5556 (zero_extend:DI (match_operand:SI 2 "register_operand" "r"))))]
5559 return TARGET_SPARCLET
5560 ? "umuld\t%1, %2, %L0"
5561 : "umul\t%1, %2, %L0\n\trd\t%%y, %H0";
5564 (if_then_else (eq_attr "isa" "sparclet")
5565 (const_string "imul") (const_string "multi")))
5566 (set (attr "length")
5567 (if_then_else (eq_attr "isa" "sparclet")
5568 (const_int 1) (const_int 2)))])
5570 (define_insn "*umulsidi3_sp64"
5571 [(set (match_operand:DI 0 "register_operand" "=r")
5572 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
5573 (zero_extend:DI (match_operand:SI 2 "register_operand" "r"))))]
5574 "TARGET_DEPRECATED_V8_INSNS && TARGET_ARCH64"
5576 [(set_attr "type" "imul")])
5578 ;; Extra pattern, because sign_extend of a constant isn't valid.
5581 (define_insn "const_umulsidi3_sp32"
5582 [(set (match_operand:DI 0 "register_operand" "=r")
5583 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
5584 (match_operand:DI 2 "uns_small_int" "")))]
5587 return TARGET_SPARCLET
5588 ? "umuld\t%1, %s2, %L0"
5589 : "umul\t%1, %s2, %L0\n\trd\t%%y, %H0";
5592 (if_then_else (eq_attr "isa" "sparclet")
5593 (const_string "imul") (const_string "multi")))
5594 (set (attr "length")
5595 (if_then_else (eq_attr "isa" "sparclet")
5596 (const_int 1) (const_int 2)))])
5598 (define_insn "const_umulsidi3_sp64"
5599 [(set (match_operand:DI 0 "register_operand" "=r")
5600 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
5601 (match_operand:DI 2 "uns_small_int" "")))]
5602 "TARGET_DEPRECATED_V8_INSNS && TARGET_ARCH64"
5604 [(set_attr "type" "imul")])
5607 (define_insn "const_umulsidi3_v8plus"
5608 [(set (match_operand:DI 0 "register_operand" "=h,r")
5609 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
5610 (match_operand:DI 2 "uns_small_int" "")))
5611 (clobber (match_scratch:SI 3 "=X,h"))]
5614 umul\t%1, %s2, %L0\n\tsrlx\t%L0, 32, %H0
5615 umul\t%1, %s2, %3\n\tsrlx\t%3, 32, %H0\n\tmov\t%3, %L0"
5616 [(set_attr "type" "multi")
5617 (set_attr "length" "2,3")])
5619 (define_expand "umulsi3_highpart"
5620 [(set (match_operand:SI 0 "register_operand" "")
5622 (lshiftrt:DI (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" ""))
5623 (zero_extend:DI (match_operand:SI 2 "uns_arith_operand" "")))
5625 "TARGET_HARD_MUL && TARGET_ARCH32"
5627 if (CONSTANT_P (operands[2]))
5631 emit_insn (gen_const_umulsi3_highpart_v8plus (operands[0],
5637 emit_insn (gen_const_umulsi3_highpart (operands[0], operands[1], operands[2]));
5642 emit_insn (gen_umulsi3_highpart_v8plus (operands[0], operands[1],
5643 operands[2], GEN_INT (32)));
5649 (define_insn "umulsi3_highpart_v8plus"
5650 [(set (match_operand:SI 0 "register_operand" "=h,r")
5652 (lshiftrt:DI (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
5653 (zero_extend:DI (match_operand:SI 2 "register_operand" "r,r")))
5654 (match_operand:SI 3 "const_int_operand" "i,i"))))
5655 (clobber (match_scratch:SI 4 "=X,h"))]
5658 umul\t%1, %2, %0\n\tsrlx\t%0, %3, %0
5659 umul\t%1, %2, %4\n\tsrlx\t%4, %3, %0"
5660 [(set_attr "type" "multi")
5661 (set_attr "length" "2")])
5664 (define_insn "const_umulsi3_highpart_v8plus"
5665 [(set (match_operand:SI 0 "register_operand" "=h,r")
5667 (lshiftrt:DI (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
5668 (match_operand:DI 2 "uns_small_int" ""))
5669 (match_operand:SI 3 "const_int_operand" "i,i"))))
5670 (clobber (match_scratch:SI 4 "=X,h"))]
5673 umul\t%1, %s2, %0\n\tsrlx\t%0, %3, %0
5674 umul\t%1, %s2, %4\n\tsrlx\t%4, %3, %0"
5675 [(set_attr "type" "multi")
5676 (set_attr "length" "2")])
5679 (define_insn "*umulsi3_highpart_sp32"
5680 [(set (match_operand:SI 0 "register_operand" "=r")
5682 (lshiftrt:DI (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
5683 (zero_extend:DI (match_operand:SI 2 "register_operand" "r")))
5686 "umul\t%1, %2, %%g0\n\trd\t%%y, %0"
5687 [(set_attr "type" "multi")
5688 (set_attr "length" "2")])
5691 (define_insn "const_umulsi3_highpart"
5692 [(set (match_operand:SI 0 "register_operand" "=r")
5694 (lshiftrt:DI (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
5695 (match_operand:DI 2 "uns_small_int" ""))
5698 "umul\t%1, %s2, %%g0\n\trd\t%%y, %0"
5699 [(set_attr "type" "multi")
5700 (set_attr "length" "2")])
5702 ;; The v8 architecture specifies that there must be 3 instructions between
5703 ;; a y register write and a use of it for correct results.
5705 (define_expand "divsi3"
5706 [(parallel [(set (match_operand:SI 0 "register_operand" "=r,r")
5707 (div:SI (match_operand:SI 1 "register_operand" "r,r")
5708 (match_operand:SI 2 "input_operand" "rI,m")))
5709 (clobber (match_scratch:SI 3 "=&r,&r"))])]
5710 "TARGET_V8 || TARGET_DEPRECATED_V8_INSNS"
5714 operands[3] = gen_reg_rtx(SImode);
5715 emit_insn (gen_ashrsi3 (operands[3], operands[1], GEN_INT (31)));
5716 emit_insn (gen_divsi3_sp64 (operands[0], operands[1], operands[2],
5722 (define_insn "divsi3_sp32"
5723 [(set (match_operand:SI 0 "register_operand" "=r,r")
5724 (div:SI (match_operand:SI 1 "register_operand" "r,r")
5725 (match_operand:SI 2 "input_operand" "rI,m")))
5726 (clobber (match_scratch:SI 3 "=&r,&r"))]
5727 "(TARGET_V8 || TARGET_DEPRECATED_V8_INSNS)
5730 if (which_alternative == 0)
5732 return "sra\t%1, 31, %3\n\twr\t%3, 0, %%y\n\tsdiv\t%1, %2, %0";
5734 return "sra\t%1, 31, %3\n\twr\t%3, 0, %%y\n\tnop\n\tnop\n\tnop\n\tsdiv\t%1, %2, %0";
5737 return "sra\t%1, 31, %3\n\twr\t%3, 0, %%y\n\tld\t%2, %3\n\tsdiv\t%1, %3, %0";
5739 return "sra\t%1, 31, %3\n\twr\t%3, 0, %%y\n\tld\t%2, %3\n\tnop\n\tnop\n\tsdiv\t%1, %3, %0";
5741 [(set_attr "type" "multi")
5742 (set (attr "length")
5743 (if_then_else (eq_attr "isa" "v9")
5744 (const_int 4) (const_int 6)))])
5746 (define_insn "divsi3_sp64"
5747 [(set (match_operand:SI 0 "register_operand" "=r")
5748 (div:SI (match_operand:SI 1 "register_operand" "r")
5749 (match_operand:SI 2 "input_operand" "rI")))
5750 (use (match_operand:SI 3 "register_operand" "r"))]
5751 "TARGET_DEPRECATED_V8_INSNS && TARGET_ARCH64"
5752 "wr\t%%g0, %3, %%y\n\tsdiv\t%1, %2, %0"
5753 [(set_attr "type" "multi")
5754 (set_attr "length" "2")])
5756 (define_insn "divdi3"
5757 [(set (match_operand:DI 0 "register_operand" "=r")
5758 (div:DI (match_operand:DI 1 "register_operand" "r")
5759 (match_operand:DI 2 "arith_double_operand" "rHI")))]
5762 [(set_attr "type" "idiv")])
5764 (define_insn "*cmp_sdiv_cc_set"
5766 (compare:CC (div:SI (match_operand:SI 1 "register_operand" "r")
5767 (match_operand:SI 2 "arith_operand" "rI"))
5769 (set (match_operand:SI 0 "register_operand" "=r")
5770 (div:SI (match_dup 1) (match_dup 2)))
5771 (clobber (match_scratch:SI 3 "=&r"))]
5772 "TARGET_V8 || TARGET_DEPRECATED_V8_INSNS"
5775 return "sra\t%1, 31, %3\n\twr\t%3, 0, %%y\n\tsdivcc\t%1, %2, %0";
5777 return "sra\t%1, 31, %3\n\twr\t%3, 0, %%y\n\tnop\n\tnop\n\tnop\n\tsdivcc\t%1, %2, %0";
5779 [(set_attr "type" "multi")
5780 (set (attr "length")
5781 (if_then_else (eq_attr "isa" "v9")
5782 (const_int 3) (const_int 6)))])
5785 (define_expand "udivsi3"
5786 [(set (match_operand:SI 0 "register_operand" "")
5787 (udiv:SI (match_operand:SI 1 "reg_or_nonsymb_mem_operand" "")
5788 (match_operand:SI 2 "input_operand" "")))]
5789 "TARGET_V8 || TARGET_DEPRECATED_V8_INSNS"
5792 (define_insn "udivsi3_sp32"
5793 [(set (match_operand:SI 0 "register_operand" "=r,&r,&r")
5794 (udiv:SI (match_operand:SI 1 "reg_or_nonsymb_mem_operand" "r,r,m")
5795 (match_operand:SI 2 "input_operand" "rI,m,r")))]
5797 || TARGET_DEPRECATED_V8_INSNS)
5800 output_asm_insn ("wr\t%%g0, %%g0, %%y", operands);
5801 switch (which_alternative)
5804 return "nop\n\tnop\n\tnop\n\tudiv\t%1, %2, %0";
5806 return "ld\t%2, %0\n\tnop\n\tnop\n\tudiv\t%1, %0, %0";
5808 return "ld\t%1, %0\n\tnop\n\tnop\n\tudiv\t%0, %2, %0";
5811 [(set_attr "type" "multi")
5812 (set_attr "length" "5")])
5814 (define_insn "udivsi3_sp64"
5815 [(set (match_operand:SI 0 "register_operand" "=r")
5816 (udiv:SI (match_operand:SI 1 "reg_or_nonsymb_mem_operand" "r")
5817 (match_operand:SI 2 "input_operand" "rI")))]
5818 "TARGET_DEPRECATED_V8_INSNS && TARGET_ARCH64"
5819 "wr\t%%g0, 0, %%y\n\tudiv\t%1, %2, %0"
5820 [(set_attr "type" "multi")
5821 (set_attr "length" "2")])
5823 (define_insn "udivdi3"
5824 [(set (match_operand:DI 0 "register_operand" "=r")
5825 (udiv:DI (match_operand:DI 1 "register_operand" "r")
5826 (match_operand:DI 2 "arith_double_operand" "rHI")))]
5829 [(set_attr "type" "idiv")])
5831 (define_insn "*cmp_udiv_cc_set"
5833 (compare:CC (udiv:SI (match_operand:SI 1 "register_operand" "r")
5834 (match_operand:SI 2 "arith_operand" "rI"))
5836 (set (match_operand:SI 0 "register_operand" "=r")
5837 (udiv:SI (match_dup 1) (match_dup 2)))]
5839 || TARGET_DEPRECATED_V8_INSNS"
5842 return "wr\t%%g0, %%g0, %%y\n\tudivcc\t%1, %2, %0";
5844 return "wr\t%%g0, %%g0, %%y\n\tnop\n\tnop\n\tnop\n\tudivcc\t%1, %2, %0";
5846 [(set_attr "type" "multi")
5847 (set (attr "length")
5848 (if_then_else (eq_attr "isa" "v9")
5849 (const_int 2) (const_int 5)))])
5851 ; sparclet multiply/accumulate insns
5853 (define_insn "*smacsi"
5854 [(set (match_operand:SI 0 "register_operand" "=r")
5855 (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "%r")
5856 (match_operand:SI 2 "arith_operand" "rI"))
5857 (match_operand:SI 3 "register_operand" "0")))]
5860 [(set_attr "type" "imul")])
5862 (define_insn "*smacdi"
5863 [(set (match_operand:DI 0 "register_operand" "=r")
5864 (plus:DI (mult:DI (sign_extend:DI
5865 (match_operand:SI 1 "register_operand" "%r"))
5867 (match_operand:SI 2 "register_operand" "r")))
5868 (match_operand:DI 3 "register_operand" "0")))]
5870 "smacd\t%1, %2, %L0"
5871 [(set_attr "type" "imul")])
5873 (define_insn "*umacdi"
5874 [(set (match_operand:DI 0 "register_operand" "=r")
5875 (plus:DI (mult:DI (zero_extend:DI
5876 (match_operand:SI 1 "register_operand" "%r"))
5878 (match_operand:SI 2 "register_operand" "r")))
5879 (match_operand:DI 3 "register_operand" "0")))]
5881 "umacd\t%1, %2, %L0"
5882 [(set_attr "type" "imul")])
5884 ;;- Boolean instructions
5885 ;; We define DImode `and' so with DImode `not' we can get
5886 ;; DImode `andn'. Other combinations are possible.
5888 (define_expand "anddi3"
5889 [(set (match_operand:DI 0 "register_operand" "")
5890 (and:DI (match_operand:DI 1 "arith_double_operand" "")
5891 (match_operand:DI 2 "arith_double_operand" "")))]
5895 (define_insn "*anddi3_sp32"
5896 [(set (match_operand:DI 0 "register_operand" "=r,b")
5897 (and:DI (match_operand:DI 1 "arith_double_operand" "%r,b")
5898 (match_operand:DI 2 "arith_double_operand" "rHI,b")))]
5903 [(set_attr "type" "*,fga")
5904 (set_attr "length" "2,*")
5905 (set_attr "fptype" "double")])
5907 (define_insn "*anddi3_sp64"
5908 [(set (match_operand:DI 0 "register_operand" "=r,b")
5909 (and:DI (match_operand:DI 1 "arith_double_operand" "%r,b")
5910 (match_operand:DI 2 "arith_double_operand" "rHI,b")))]
5915 [(set_attr "type" "*,fga")
5916 (set_attr "fptype" "double")])
5918 (define_insn "andsi3"
5919 [(set (match_operand:SI 0 "register_operand" "=r,d")
5920 (and:SI (match_operand:SI 1 "arith_operand" "%r,d")
5921 (match_operand:SI 2 "arith_operand" "rI,d")))]
5926 [(set_attr "type" "*,fga")])
5929 [(set (match_operand:SI 0 "register_operand" "")
5930 (and:SI (match_operand:SI 1 "register_operand" "")
5931 (match_operand:SI 2 "" "")))
5932 (clobber (match_operand:SI 3 "register_operand" ""))]
5933 "GET_CODE (operands[2]) == CONST_INT
5934 && !SMALL_INT32 (operands[2])
5935 && (INTVAL (operands[2]) & 0x3ff) == 0x3ff"
5936 [(set (match_dup 3) (match_dup 4))
5937 (set (match_dup 0) (and:SI (not:SI (match_dup 3)) (match_dup 1)))]
5939 operands[4] = GEN_INT (~INTVAL (operands[2]));
5942 ;; Split DImode logical operations requiring two instructions.
5944 [(set (match_operand:DI 0 "register_operand" "")
5945 (match_operator:DI 1 "cc_arithop" ; AND, IOR, XOR
5946 [(match_operand:DI 2 "register_operand" "")
5947 (match_operand:DI 3 "arith_double_operand" "")]))]
5950 && ((GET_CODE (operands[0]) == REG
5951 && REGNO (operands[0]) < 32)
5952 || (GET_CODE (operands[0]) == SUBREG
5953 && GET_CODE (SUBREG_REG (operands[0])) == REG
5954 && REGNO (SUBREG_REG (operands[0])) < 32))"
5955 [(set (match_dup 4) (match_op_dup:SI 1 [(match_dup 6) (match_dup 8)]))
5956 (set (match_dup 5) (match_op_dup:SI 1 [(match_dup 7) (match_dup 9)]))]
5958 operands[4] = gen_highpart (SImode, operands[0]);
5959 operands[5] = gen_lowpart (SImode, operands[0]);
5960 operands[6] = gen_highpart (SImode, operands[2]);
5961 operands[7] = gen_lowpart (SImode, operands[2]);
5962 #if HOST_BITS_PER_WIDE_INT == 32
5963 if (GET_CODE (operands[3]) == CONST_INT)
5965 if (INTVAL (operands[3]) < 0)
5966 operands[8] = constm1_rtx;
5968 operands[8] = const0_rtx;
5972 operands[8] = gen_highpart_mode (SImode, DImode, operands[3]);
5973 operands[9] = gen_lowpart (SImode, operands[3]);
5976 (define_insn_and_split "*and_not_di_sp32"
5977 [(set (match_operand:DI 0 "register_operand" "=r,b")
5978 (and:DI (not:DI (match_operand:DI 1 "register_operand" "r,b"))
5979 (match_operand:DI 2 "register_operand" "r,b")))]
5983 fandnot1\t%1, %2, %0"
5984 "&& reload_completed
5985 && ((GET_CODE (operands[0]) == REG
5986 && REGNO (operands[0]) < 32)
5987 || (GET_CODE (operands[0]) == SUBREG
5988 && GET_CODE (SUBREG_REG (operands[0])) == REG
5989 && REGNO (SUBREG_REG (operands[0])) < 32))"
5990 [(set (match_dup 3) (and:SI (not:SI (match_dup 4)) (match_dup 5)))
5991 (set (match_dup 6) (and:SI (not:SI (match_dup 7)) (match_dup 8)))]
5992 "operands[3] = gen_highpart (SImode, operands[0]);
5993 operands[4] = gen_highpart (SImode, operands[1]);
5994 operands[5] = gen_highpart (SImode, operands[2]);
5995 operands[6] = gen_lowpart (SImode, operands[0]);
5996 operands[7] = gen_lowpart (SImode, operands[1]);
5997 operands[8] = gen_lowpart (SImode, operands[2]);"
5998 [(set_attr "type" "*,fga")
5999 (set_attr "length" "2,*")
6000 (set_attr "fptype" "double")])
6002 (define_insn "*and_not_di_sp64"
6003 [(set (match_operand:DI 0 "register_operand" "=r,b")
6004 (and:DI (not:DI (match_operand:DI 1 "register_operand" "r,b"))
6005 (match_operand:DI 2 "register_operand" "r,b")))]
6009 fandnot1\t%1, %2, %0"
6010 [(set_attr "type" "*,fga")
6011 (set_attr "fptype" "double")])
6013 (define_insn "*and_not_si"
6014 [(set (match_operand:SI 0 "register_operand" "=r,d")
6015 (and:SI (not:SI (match_operand:SI 1 "register_operand" "r,d"))
6016 (match_operand:SI 2 "register_operand" "r,d")))]
6020 fandnot1s\t%1, %2, %0"
6021 [(set_attr "type" "*,fga")])
6023 (define_expand "iordi3"
6024 [(set (match_operand:DI 0 "register_operand" "")
6025 (ior:DI (match_operand:DI 1 "arith_double_operand" "")
6026 (match_operand:DI 2 "arith_double_operand" "")))]
6030 (define_insn "*iordi3_sp32"
6031 [(set (match_operand:DI 0 "register_operand" "=r,b")
6032 (ior:DI (match_operand:DI 1 "arith_double_operand" "%r,b")
6033 (match_operand:DI 2 "arith_double_operand" "rHI,b")))]
6038 [(set_attr "type" "*,fga")
6039 (set_attr "length" "2,*")
6040 (set_attr "fptype" "double")])
6042 (define_insn "*iordi3_sp64"
6043 [(set (match_operand:DI 0 "register_operand" "=r,b")
6044 (ior:DI (match_operand:DI 1 "arith_double_operand" "%r,b")
6045 (match_operand:DI 2 "arith_double_operand" "rHI,b")))]
6050 [(set_attr "type" "*,fga")
6051 (set_attr "fptype" "double")])
6053 (define_insn "iorsi3"
6054 [(set (match_operand:SI 0 "register_operand" "=r,d")
6055 (ior:SI (match_operand:SI 1 "arith_operand" "%r,d")
6056 (match_operand:SI 2 "arith_operand" "rI,d")))]
6061 [(set_attr "type" "*,fga")])
6064 [(set (match_operand:SI 0 "register_operand" "")
6065 (ior:SI (match_operand:SI 1 "register_operand" "")
6066 (match_operand:SI 2 "" "")))
6067 (clobber (match_operand:SI 3 "register_operand" ""))]
6068 "GET_CODE (operands[2]) == CONST_INT
6069 && !SMALL_INT32 (operands[2])
6070 && (INTVAL (operands[2]) & 0x3ff) == 0x3ff"
6071 [(set (match_dup 3) (match_dup 4))
6072 (set (match_dup 0) (ior:SI (not:SI (match_dup 3)) (match_dup 1)))]
6074 operands[4] = GEN_INT (~INTVAL (operands[2]));
6077 (define_insn_and_split "*or_not_di_sp32"
6078 [(set (match_operand:DI 0 "register_operand" "=r,b")
6079 (ior:DI (not:DI (match_operand:DI 1 "register_operand" "r,b"))
6080 (match_operand:DI 2 "register_operand" "r,b")))]
6084 fornot1\t%1, %2, %0"
6085 "&& reload_completed
6086 && ((GET_CODE (operands[0]) == REG
6087 && REGNO (operands[0]) < 32)
6088 || (GET_CODE (operands[0]) == SUBREG
6089 && GET_CODE (SUBREG_REG (operands[0])) == REG
6090 && REGNO (SUBREG_REG (operands[0])) < 32))"
6091 [(set (match_dup 3) (ior:SI (not:SI (match_dup 4)) (match_dup 5)))
6092 (set (match_dup 6) (ior:SI (not:SI (match_dup 7)) (match_dup 8)))]
6093 "operands[3] = gen_highpart (SImode, operands[0]);
6094 operands[4] = gen_highpart (SImode, operands[1]);
6095 operands[5] = gen_highpart (SImode, operands[2]);
6096 operands[6] = gen_lowpart (SImode, operands[0]);
6097 operands[7] = gen_lowpart (SImode, operands[1]);
6098 operands[8] = gen_lowpart (SImode, operands[2]);"
6099 [(set_attr "type" "*,fga")
6100 (set_attr "length" "2,*")
6101 (set_attr "fptype" "double")])
6103 (define_insn "*or_not_di_sp64"
6104 [(set (match_operand:DI 0 "register_operand" "=r,b")
6105 (ior:DI (not:DI (match_operand:DI 1 "register_operand" "r,b"))
6106 (match_operand:DI 2 "register_operand" "r,b")))]
6110 fornot1\t%1, %2, %0"
6111 [(set_attr "type" "*,fga")
6112 (set_attr "fptype" "double")])
6114 (define_insn "*or_not_si"
6115 [(set (match_operand:SI 0 "register_operand" "=r,d")
6116 (ior:SI (not:SI (match_operand:SI 1 "register_operand" "r,d"))
6117 (match_operand:SI 2 "register_operand" "r,d")))]
6121 fornot1s\t%1, %2, %0"
6122 [(set_attr "type" "*,fga")])
6124 (define_expand "xordi3"
6125 [(set (match_operand:DI 0 "register_operand" "")
6126 (xor:DI (match_operand:DI 1 "arith_double_operand" "")
6127 (match_operand:DI 2 "arith_double_operand" "")))]
6131 (define_insn "*xordi3_sp32"
6132 [(set (match_operand:DI 0 "register_operand" "=r,b")
6133 (xor:DI (match_operand:DI 1 "arith_double_operand" "%r,b")
6134 (match_operand:DI 2 "arith_double_operand" "rHI,b")))]
6139 [(set_attr "type" "*,fga")
6140 (set_attr "length" "2,*")
6141 (set_attr "fptype" "double")])
6143 (define_insn "*xordi3_sp64"
6144 [(set (match_operand:DI 0 "register_operand" "=r,b")
6145 (xor:DI (match_operand:DI 1 "arith_double_operand" "%rJ,b")
6146 (match_operand:DI 2 "arith_double_operand" "rHI,b")))]
6151 [(set_attr "type" "*,fga")
6152 (set_attr "fptype" "double")])
6154 (define_insn "*xordi3_sp64_dbl"
6155 [(set (match_operand:DI 0 "register_operand" "=r")
6156 (xor:DI (match_operand:DI 1 "register_operand" "r")
6157 (match_operand:DI 2 "const64_operand" "")))]
6159 && HOST_BITS_PER_WIDE_INT != 64)"
6162 (define_insn "xorsi3"
6163 [(set (match_operand:SI 0 "register_operand" "=r,d")
6164 (xor:SI (match_operand:SI 1 "arith_operand" "%rJ,d")
6165 (match_operand:SI 2 "arith_operand" "rI,d")))]
6170 [(set_attr "type" "*,fga")])
6173 [(set (match_operand:SI 0 "register_operand" "")
6174 (xor:SI (match_operand:SI 1 "register_operand" "")
6175 (match_operand:SI 2 "" "")))
6176 (clobber (match_operand:SI 3 "register_operand" ""))]
6177 "GET_CODE (operands[2]) == CONST_INT
6178 && !SMALL_INT32 (operands[2])
6179 && (INTVAL (operands[2]) & 0x3ff) == 0x3ff"
6180 [(set (match_dup 3) (match_dup 4))
6181 (set (match_dup 0) (not:SI (xor:SI (match_dup 3) (match_dup 1))))]
6183 operands[4] = GEN_INT (~INTVAL (operands[2]));
6187 [(set (match_operand:SI 0 "register_operand" "")
6188 (not:SI (xor:SI (match_operand:SI 1 "register_operand" "")
6189 (match_operand:SI 2 "" ""))))
6190 (clobber (match_operand:SI 3 "register_operand" ""))]
6191 "GET_CODE (operands[2]) == CONST_INT
6192 && !SMALL_INT32 (operands[2])
6193 && (INTVAL (operands[2]) & 0x3ff) == 0x3ff"
6194 [(set (match_dup 3) (match_dup 4))
6195 (set (match_dup 0) (xor:SI (match_dup 3) (match_dup 1)))]
6197 operands[4] = GEN_INT (~INTVAL (operands[2]));
6200 ;; xnor patterns. Note that (a ^ ~b) == (~a ^ b) == ~(a ^ b).
6201 ;; Combine now canonicalizes to the rightmost expression.
6202 (define_insn_and_split "*xor_not_di_sp32"
6203 [(set (match_operand:DI 0 "register_operand" "=r,b")
6204 (not:DI (xor:DI (match_operand:DI 1 "register_operand" "r,b")
6205 (match_operand:DI 2 "register_operand" "r,b"))))]
6210 "&& reload_completed
6211 && ((GET_CODE (operands[0]) == REG
6212 && REGNO (operands[0]) < 32)
6213 || (GET_CODE (operands[0]) == SUBREG
6214 && GET_CODE (SUBREG_REG (operands[0])) == REG
6215 && REGNO (SUBREG_REG (operands[0])) < 32))"
6216 [(set (match_dup 3) (not:SI (xor:SI (match_dup 4) (match_dup 5))))
6217 (set (match_dup 6) (not:SI (xor:SI (match_dup 7) (match_dup 8))))]
6218 "operands[3] = gen_highpart (SImode, operands[0]);
6219 operands[4] = gen_highpart (SImode, operands[1]);
6220 operands[5] = gen_highpart (SImode, operands[2]);
6221 operands[6] = gen_lowpart (SImode, operands[0]);
6222 operands[7] = gen_lowpart (SImode, operands[1]);
6223 operands[8] = gen_lowpart (SImode, operands[2]);"
6224 [(set_attr "type" "*,fga")
6225 (set_attr "length" "2,*")
6226 (set_attr "fptype" "double")])
6228 (define_insn "*xor_not_di_sp64"
6229 [(set (match_operand:DI 0 "register_operand" "=r,b")
6230 (not:DI (xor:DI (match_operand:DI 1 "reg_or_0_operand" "rJ,b")
6231 (match_operand:DI 2 "arith_double_operand" "rHI,b"))))]
6236 [(set_attr "type" "*,fga")
6237 (set_attr "fptype" "double")])
6239 (define_insn "*xor_not_si"
6240 [(set (match_operand:SI 0 "register_operand" "=r,d")
6241 (not:SI (xor:SI (match_operand:SI 1 "reg_or_0_operand" "rJ,d")
6242 (match_operand:SI 2 "arith_operand" "rI,d"))))]
6247 [(set_attr "type" "*,fga")])
6249 ;; These correspond to the above in the case where we also (or only)
6250 ;; want to set the condition code.
6252 (define_insn "*cmp_cc_arith_op"
6255 (match_operator:SI 2 "cc_arithop"
6256 [(match_operand:SI 0 "arith_operand" "%r")
6257 (match_operand:SI 1 "arith_operand" "rI")])
6260 "%A2cc\t%0, %1, %%g0"
6261 [(set_attr "type" "compare")])
6263 (define_insn "*cmp_ccx_arith_op"
6266 (match_operator:DI 2 "cc_arithop"
6267 [(match_operand:DI 0 "arith_double_operand" "%r")
6268 (match_operand:DI 1 "arith_double_operand" "rHI")])
6271 "%A2cc\t%0, %1, %%g0"
6272 [(set_attr "type" "compare")])
6274 (define_insn "*cmp_cc_arith_op_set"
6277 (match_operator:SI 3 "cc_arithop"
6278 [(match_operand:SI 1 "arith_operand" "%r")
6279 (match_operand:SI 2 "arith_operand" "rI")])
6281 (set (match_operand:SI 0 "register_operand" "=r")
6282 (match_operator:SI 4 "cc_arithop" [(match_dup 1) (match_dup 2)]))]
6283 "GET_CODE (operands[3]) == GET_CODE (operands[4])"
6285 [(set_attr "type" "compare")])
6287 (define_insn "*cmp_ccx_arith_op_set"
6290 (match_operator:DI 3 "cc_arithop"
6291 [(match_operand:DI 1 "arith_double_operand" "%r")
6292 (match_operand:DI 2 "arith_double_operand" "rHI")])
6294 (set (match_operand:DI 0 "register_operand" "=r")
6295 (match_operator:DI 4 "cc_arithop" [(match_dup 1) (match_dup 2)]))]
6296 "TARGET_ARCH64 && GET_CODE (operands[3]) == GET_CODE (operands[4])"
6298 [(set_attr "type" "compare")])
6300 (define_insn "*cmp_cc_xor_not"
6303 (not:SI (xor:SI (match_operand:SI 0 "reg_or_0_operand" "%rJ")
6304 (match_operand:SI 1 "arith_operand" "rI")))
6307 "xnorcc\t%r0, %1, %%g0"
6308 [(set_attr "type" "compare")])
6310 (define_insn "*cmp_ccx_xor_not"
6313 (not:DI (xor:DI (match_operand:DI 0 "reg_or_0_operand" "%rJ")
6314 (match_operand:DI 1 "arith_double_operand" "rHI")))
6317 "xnorcc\t%r0, %1, %%g0"
6318 [(set_attr "type" "compare")])
6320 (define_insn "*cmp_cc_xor_not_set"
6323 (not:SI (xor:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ")
6324 (match_operand:SI 2 "arith_operand" "rI")))
6326 (set (match_operand:SI 0 "register_operand" "=r")
6327 (not:SI (xor:SI (match_dup 1) (match_dup 2))))]
6329 "xnorcc\t%r1, %2, %0"
6330 [(set_attr "type" "compare")])
6332 (define_insn "*cmp_ccx_xor_not_set"
6335 (not:DI (xor:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ")
6336 (match_operand:DI 2 "arith_double_operand" "rHI")))
6338 (set (match_operand:DI 0 "register_operand" "=r")
6339 (not:DI (xor:DI (match_dup 1) (match_dup 2))))]
6341 "xnorcc\t%r1, %2, %0"
6342 [(set_attr "type" "compare")])
6344 (define_insn "*cmp_cc_arith_op_not"
6347 (match_operator:SI 2 "cc_arithopn"
6348 [(not:SI (match_operand:SI 0 "arith_operand" "rI"))
6349 (match_operand:SI 1 "reg_or_0_operand" "rJ")])
6352 "%B2cc\t%r1, %0, %%g0"
6353 [(set_attr "type" "compare")])
6355 (define_insn "*cmp_ccx_arith_op_not"
6358 (match_operator:DI 2 "cc_arithopn"
6359 [(not:DI (match_operand:DI 0 "arith_double_operand" "rHI"))
6360 (match_operand:DI 1 "reg_or_0_operand" "rJ")])
6363 "%B2cc\t%r1, %0, %%g0"
6364 [(set_attr "type" "compare")])
6366 (define_insn "*cmp_cc_arith_op_not_set"
6369 (match_operator:SI 3 "cc_arithopn"
6370 [(not:SI (match_operand:SI 1 "arith_operand" "rI"))
6371 (match_operand:SI 2 "reg_or_0_operand" "rJ")])
6373 (set (match_operand:SI 0 "register_operand" "=r")
6374 (match_operator:SI 4 "cc_arithopn"
6375 [(not:SI (match_dup 1)) (match_dup 2)]))]
6376 "GET_CODE (operands[3]) == GET_CODE (operands[4])"
6377 "%B3cc\t%r2, %1, %0"
6378 [(set_attr "type" "compare")])
6380 (define_insn "*cmp_ccx_arith_op_not_set"
6383 (match_operator:DI 3 "cc_arithopn"
6384 [(not:DI (match_operand:DI 1 "arith_double_operand" "rHI"))
6385 (match_operand:DI 2 "reg_or_0_operand" "rJ")])
6387 (set (match_operand:DI 0 "register_operand" "=r")
6388 (match_operator:DI 4 "cc_arithopn"
6389 [(not:DI (match_dup 1)) (match_dup 2)]))]
6390 "TARGET_ARCH64 && GET_CODE (operands[3]) == GET_CODE (operands[4])"
6391 "%B3cc\t%r2, %1, %0"
6392 [(set_attr "type" "compare")])
6394 ;; We cannot use the "neg" pseudo insn because the Sun assembler
6395 ;; does not know how to make it work for constants.
6397 (define_expand "negdi2"
6398 [(set (match_operand:DI 0 "register_operand" "=r")
6399 (neg:DI (match_operand:DI 1 "register_operand" "r")))]
6402 if (! TARGET_ARCH64)
6404 emit_insn (gen_rtx_PARALLEL
6407 gen_rtx_SET (VOIDmode, operand0,
6408 gen_rtx_NEG (DImode, operand1)),
6409 gen_rtx_CLOBBER (VOIDmode,
6410 gen_rtx_REG (CCmode,
6416 (define_insn_and_split "*negdi2_sp32"
6417 [(set (match_operand:DI 0 "register_operand" "=r")
6418 (neg:DI (match_operand:DI 1 "register_operand" "r")))
6419 (clobber (reg:CC 100))]
6422 "&& reload_completed"
6423 [(parallel [(set (reg:CC_NOOV 100)
6424 (compare:CC_NOOV (minus:SI (const_int 0) (match_dup 5))
6426 (set (match_dup 4) (minus:SI (const_int 0) (match_dup 5)))])
6427 (set (match_dup 2) (minus:SI (minus:SI (const_int 0) (match_dup 3))
6428 (ltu:SI (reg:CC 100) (const_int 0))))]
6429 "operands[2] = gen_highpart (SImode, operands[0]);
6430 operands[3] = gen_highpart (SImode, operands[1]);
6431 operands[4] = gen_lowpart (SImode, operands[0]);
6432 operands[5] = gen_lowpart (SImode, operands[1]);"
6433 [(set_attr "length" "2")])
6435 (define_insn "*negdi2_sp64"
6436 [(set (match_operand:DI 0 "register_operand" "=r")
6437 (neg:DI (match_operand:DI 1 "register_operand" "r")))]
6439 "sub\t%%g0, %1, %0")
6441 (define_insn "negsi2"
6442 [(set (match_operand:SI 0 "register_operand" "=r")
6443 (neg:SI (match_operand:SI 1 "arith_operand" "rI")))]
6445 "sub\t%%g0, %1, %0")
6447 (define_insn "*cmp_cc_neg"
6448 [(set (reg:CC_NOOV 100)
6449 (compare:CC_NOOV (neg:SI (match_operand:SI 0 "arith_operand" "rI"))
6452 "subcc\t%%g0, %0, %%g0"
6453 [(set_attr "type" "compare")])
6455 (define_insn "*cmp_ccx_neg"
6456 [(set (reg:CCX_NOOV 100)
6457 (compare:CCX_NOOV (neg:DI (match_operand:DI 0 "arith_double_operand" "rHI"))
6460 "subcc\t%%g0, %0, %%g0"
6461 [(set_attr "type" "compare")])
6463 (define_insn "*cmp_cc_set_neg"
6464 [(set (reg:CC_NOOV 100)
6465 (compare:CC_NOOV (neg:SI (match_operand:SI 1 "arith_operand" "rI"))
6467 (set (match_operand:SI 0 "register_operand" "=r")
6468 (neg:SI (match_dup 1)))]
6470 "subcc\t%%g0, %1, %0"
6471 [(set_attr "type" "compare")])
6473 (define_insn "*cmp_ccx_set_neg"
6474 [(set (reg:CCX_NOOV 100)
6475 (compare:CCX_NOOV (neg:DI (match_operand:DI 1 "arith_double_operand" "rHI"))
6477 (set (match_operand:DI 0 "register_operand" "=r")
6478 (neg:DI (match_dup 1)))]
6480 "subcc\t%%g0, %1, %0"
6481 [(set_attr "type" "compare")])
6483 ;; We cannot use the "not" pseudo insn because the Sun assembler
6484 ;; does not know how to make it work for constants.
6485 (define_expand "one_cmpldi2"
6486 [(set (match_operand:DI 0 "register_operand" "")
6487 (not:DI (match_operand:DI 1 "register_operand" "")))]
6491 (define_insn_and_split "*one_cmpldi2_sp32"
6492 [(set (match_operand:DI 0 "register_operand" "=r,b")
6493 (not:DI (match_operand:DI 1 "register_operand" "r,b")))]
6498 "&& reload_completed
6499 && ((GET_CODE (operands[0]) == REG
6500 && REGNO (operands[0]) < 32)
6501 || (GET_CODE (operands[0]) == SUBREG
6502 && GET_CODE (SUBREG_REG (operands[0])) == REG
6503 && REGNO (SUBREG_REG (operands[0])) < 32))"
6504 [(set (match_dup 2) (not:SI (xor:SI (match_dup 3) (const_int 0))))
6505 (set (match_dup 4) (not:SI (xor:SI (match_dup 5) (const_int 0))))]
6506 "operands[2] = gen_highpart (SImode, operands[0]);
6507 operands[3] = gen_highpart (SImode, operands[1]);
6508 operands[4] = gen_lowpart (SImode, operands[0]);
6509 operands[5] = gen_lowpart (SImode, operands[1]);"
6510 [(set_attr "type" "*,fga")
6511 (set_attr "length" "2,*")
6512 (set_attr "fptype" "double")])
6514 (define_insn "*one_cmpldi2_sp64"
6515 [(set (match_operand:DI 0 "register_operand" "=r,b")
6516 (not:DI (match_operand:DI 1 "arith_double_operand" "rHI,b")))]
6521 [(set_attr "type" "*,fga")
6522 (set_attr "fptype" "double")])
6524 (define_insn "one_cmplsi2"
6525 [(set (match_operand:SI 0 "register_operand" "=r,d")
6526 (not:SI (match_operand:SI 1 "arith_operand" "rI,d")))]
6531 [(set_attr "type" "*,fga")])
6533 (define_insn "*cmp_cc_not"
6535 (compare:CC (not:SI (match_operand:SI 0 "arith_operand" "rI"))
6538 "xnorcc\t%%g0, %0, %%g0"
6539 [(set_attr "type" "compare")])
6541 (define_insn "*cmp_ccx_not"
6543 (compare:CCX (not:DI (match_operand:DI 0 "arith_double_operand" "rHI"))
6546 "xnorcc\t%%g0, %0, %%g0"
6547 [(set_attr "type" "compare")])
6549 (define_insn "*cmp_cc_set_not"
6551 (compare:CC (not:SI (match_operand:SI 1 "arith_operand" "rI"))
6553 (set (match_operand:SI 0 "register_operand" "=r")
6554 (not:SI (match_dup 1)))]
6556 "xnorcc\t%%g0, %1, %0"
6557 [(set_attr "type" "compare")])
6559 (define_insn "*cmp_ccx_set_not"
6561 (compare:CCX (not:DI (match_operand:DI 1 "arith_double_operand" "rHI"))
6563 (set (match_operand:DI 0 "register_operand" "=r")
6564 (not:DI (match_dup 1)))]
6566 "xnorcc\t%%g0, %1, %0"
6567 [(set_attr "type" "compare")])
6569 (define_insn "*cmp_cc_set"
6570 [(set (match_operand:SI 0 "register_operand" "=r")
6571 (match_operand:SI 1 "register_operand" "r"))
6573 (compare:CC (match_dup 1)
6577 [(set_attr "type" "compare")])
6579 (define_insn "*cmp_ccx_set64"
6580 [(set (match_operand:DI 0 "register_operand" "=r")
6581 (match_operand:DI 1 "register_operand" "r"))
6583 (compare:CCX (match_dup 1)
6587 [(set_attr "type" "compare")])
6589 ;; Floating point arithmetic instructions.
6591 (define_expand "addtf3"
6592 [(set (match_operand:TF 0 "nonimmediate_operand" "")
6593 (plus:TF (match_operand:TF 1 "general_operand" "")
6594 (match_operand:TF 2 "general_operand" "")))]
6595 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
6596 "emit_tfmode_binop (PLUS, operands); DONE;")
6598 (define_insn "*addtf3_hq"
6599 [(set (match_operand:TF 0 "register_operand" "=e")
6600 (plus:TF (match_operand:TF 1 "register_operand" "e")
6601 (match_operand:TF 2 "register_operand" "e")))]
6602 "TARGET_FPU && TARGET_HARD_QUAD"
6604 [(set_attr "type" "fp")])
6606 (define_insn "adddf3"
6607 [(set (match_operand:DF 0 "register_operand" "=e")
6608 (plus:DF (match_operand:DF 1 "register_operand" "e")
6609 (match_operand:DF 2 "register_operand" "e")))]
6612 [(set_attr "type" "fp")
6613 (set_attr "fptype" "double")])
6615 (define_insn "addsf3"
6616 [(set (match_operand:SF 0 "register_operand" "=f")
6617 (plus:SF (match_operand:SF 1 "register_operand" "f")
6618 (match_operand:SF 2 "register_operand" "f")))]
6621 [(set_attr "type" "fp")])
6623 (define_expand "subtf3"
6624 [(set (match_operand:TF 0 "nonimmediate_operand" "")
6625 (minus:TF (match_operand:TF 1 "general_operand" "")
6626 (match_operand:TF 2 "general_operand" "")))]
6627 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
6628 "emit_tfmode_binop (MINUS, operands); DONE;")
6630 (define_insn "*subtf3_hq"
6631 [(set (match_operand:TF 0 "register_operand" "=e")
6632 (minus:TF (match_operand:TF 1 "register_operand" "e")
6633 (match_operand:TF 2 "register_operand" "e")))]
6634 "TARGET_FPU && TARGET_HARD_QUAD"
6636 [(set_attr "type" "fp")])
6638 (define_insn "subdf3"
6639 [(set (match_operand:DF 0 "register_operand" "=e")
6640 (minus:DF (match_operand:DF 1 "register_operand" "e")
6641 (match_operand:DF 2 "register_operand" "e")))]
6644 [(set_attr "type" "fp")
6645 (set_attr "fptype" "double")])
6647 (define_insn "subsf3"
6648 [(set (match_operand:SF 0 "register_operand" "=f")
6649 (minus:SF (match_operand:SF 1 "register_operand" "f")
6650 (match_operand:SF 2 "register_operand" "f")))]
6653 [(set_attr "type" "fp")])
6655 (define_expand "multf3"
6656 [(set (match_operand:TF 0 "nonimmediate_operand" "")
6657 (mult:TF (match_operand:TF 1 "general_operand" "")
6658 (match_operand:TF 2 "general_operand" "")))]
6659 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
6660 "emit_tfmode_binop (MULT, operands); DONE;")
6662 (define_insn "*multf3_hq"
6663 [(set (match_operand:TF 0 "register_operand" "=e")
6664 (mult:TF (match_operand:TF 1 "register_operand" "e")
6665 (match_operand:TF 2 "register_operand" "e")))]
6666 "TARGET_FPU && TARGET_HARD_QUAD"
6668 [(set_attr "type" "fpmul")])
6670 (define_insn "muldf3"
6671 [(set (match_operand:DF 0 "register_operand" "=e")
6672 (mult:DF (match_operand:DF 1 "register_operand" "e")
6673 (match_operand:DF 2 "register_operand" "e")))]
6676 [(set_attr "type" "fpmul")
6677 (set_attr "fptype" "double")])
6679 (define_insn "mulsf3"
6680 [(set (match_operand:SF 0 "register_operand" "=f")
6681 (mult:SF (match_operand:SF 1 "register_operand" "f")
6682 (match_operand:SF 2 "register_operand" "f")))]
6685 [(set_attr "type" "fpmul")])
6687 (define_insn "*muldf3_extend"
6688 [(set (match_operand:DF 0 "register_operand" "=e")
6689 (mult:DF (float_extend:DF (match_operand:SF 1 "register_operand" "f"))
6690 (float_extend:DF (match_operand:SF 2 "register_operand" "f"))))]
6691 "(TARGET_V8 || TARGET_V9) && TARGET_FPU"
6692 "fsmuld\t%1, %2, %0"
6693 [(set_attr "type" "fpmul")
6694 (set_attr "fptype" "double")])
6696 (define_insn "*multf3_extend"
6697 [(set (match_operand:TF 0 "register_operand" "=e")
6698 (mult:TF (float_extend:TF (match_operand:DF 1 "register_operand" "e"))
6699 (float_extend:TF (match_operand:DF 2 "register_operand" "e"))))]
6700 "(TARGET_V8 || TARGET_V9) && TARGET_FPU && TARGET_HARD_QUAD"
6701 "fdmulq\t%1, %2, %0"
6702 [(set_attr "type" "fpmul")])
6704 (define_expand "divtf3"
6705 [(set (match_operand:TF 0 "nonimmediate_operand" "")
6706 (div:TF (match_operand:TF 1 "general_operand" "")
6707 (match_operand:TF 2 "general_operand" "")))]
6708 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
6709 "emit_tfmode_binop (DIV, operands); DONE;")
6711 ;; don't have timing for quad-prec. divide.
6712 (define_insn "*divtf3_hq"
6713 [(set (match_operand:TF 0 "register_operand" "=e")
6714 (div:TF (match_operand:TF 1 "register_operand" "e")
6715 (match_operand:TF 2 "register_operand" "e")))]
6716 "TARGET_FPU && TARGET_HARD_QUAD"
6718 [(set_attr "type" "fpdivd")])
6720 (define_insn "divdf3"
6721 [(set (match_operand:DF 0 "register_operand" "=e")
6722 (div:DF (match_operand:DF 1 "register_operand" "e")
6723 (match_operand:DF 2 "register_operand" "e")))]
6726 [(set_attr "type" "fpdivd")
6727 (set_attr "fptype" "double")])
6729 (define_insn "divsf3"
6730 [(set (match_operand:SF 0 "register_operand" "=f")
6731 (div:SF (match_operand:SF 1 "register_operand" "f")
6732 (match_operand:SF 2 "register_operand" "f")))]
6735 [(set_attr "type" "fpdivs")])
6737 (define_expand "negtf2"
6738 [(set (match_operand:TF 0 "register_operand" "=e,e")
6739 (neg:TF (match_operand:TF 1 "register_operand" "0,e")))]
6743 (define_insn_and_split "*negtf2_notv9"
6744 [(set (match_operand:TF 0 "register_operand" "=e,e")
6745 (neg:TF (match_operand:TF 1 "register_operand" "0,e")))]
6746 ; We don't use quad float insns here so we don't need TARGET_HARD_QUAD.
6752 "&& reload_completed
6753 && sparc_absnegfloat_split_legitimate (operands[0], operands[1])"
6754 [(set (match_dup 2) (neg:SF (match_dup 3)))
6755 (set (match_dup 4) (match_dup 5))
6756 (set (match_dup 6) (match_dup 7))]
6757 "operands[2] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]));
6758 operands[3] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]));
6759 operands[4] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]) + 1);
6760 operands[5] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]) + 1);
6761 operands[6] = gen_rtx_raw_REG (DFmode, REGNO (operands[0]) + 2);
6762 operands[7] = gen_rtx_raw_REG (DFmode, REGNO (operands[1]) + 2);"
6763 [(set_attr "type" "fpmove,*")
6764 (set_attr "length" "*,2")])
6766 (define_insn_and_split "*negtf2_v9"
6767 [(set (match_operand:TF 0 "register_operand" "=e,e")
6768 (neg:TF (match_operand:TF 1 "register_operand" "0,e")))]
6769 ; We don't use quad float insns here so we don't need TARGET_HARD_QUAD.
6770 "TARGET_FPU && TARGET_V9"
6774 "&& reload_completed
6775 && sparc_absnegfloat_split_legitimate (operands[0], operands[1])"
6776 [(set (match_dup 2) (neg:DF (match_dup 3)))
6777 (set (match_dup 4) (match_dup 5))]
6778 "operands[2] = gen_rtx_raw_REG (DFmode, REGNO (operands[0]));
6779 operands[3] = gen_rtx_raw_REG (DFmode, REGNO (operands[1]));
6780 operands[4] = gen_rtx_raw_REG (DFmode, REGNO (operands[0]) + 2);
6781 operands[5] = gen_rtx_raw_REG (DFmode, REGNO (operands[1]) + 2);"
6782 [(set_attr "type" "fpmove,*")
6783 (set_attr "length" "*,2")
6784 (set_attr "fptype" "double")])
6786 (define_expand "negdf2"
6787 [(set (match_operand:DF 0 "register_operand" "")
6788 (neg:DF (match_operand:DF 1 "register_operand" "")))]
6792 (define_insn_and_split "*negdf2_notv9"
6793 [(set (match_operand:DF 0 "register_operand" "=e,e")
6794 (neg:DF (match_operand:DF 1 "register_operand" "0,e")))]
6795 "TARGET_FPU && ! TARGET_V9"
6799 "&& reload_completed
6800 && sparc_absnegfloat_split_legitimate (operands[0], operands[1])"
6801 [(set (match_dup 2) (neg:SF (match_dup 3)))
6802 (set (match_dup 4) (match_dup 5))]
6803 "operands[2] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]));
6804 operands[3] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]));
6805 operands[4] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]) + 1);
6806 operands[5] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]) + 1);"
6807 [(set_attr "type" "fpmove,*")
6808 (set_attr "length" "*,2")])
6810 (define_insn "*negdf2_v9"
6811 [(set (match_operand:DF 0 "register_operand" "=e")
6812 (neg:DF (match_operand:DF 1 "register_operand" "e")))]
6813 "TARGET_FPU && TARGET_V9"
6815 [(set_attr "type" "fpmove")
6816 (set_attr "fptype" "double")])
6818 (define_insn "negsf2"
6819 [(set (match_operand:SF 0 "register_operand" "=f")
6820 (neg:SF (match_operand:SF 1 "register_operand" "f")))]
6823 [(set_attr "type" "fpmove")])
6825 (define_expand "abstf2"
6826 [(set (match_operand:TF 0 "register_operand" "")
6827 (abs:TF (match_operand:TF 1 "register_operand" "")))]
6831 (define_insn_and_split "*abstf2_notv9"
6832 [(set (match_operand:TF 0 "register_operand" "=e,e")
6833 (abs:TF (match_operand:TF 1 "register_operand" "0,e")))]
6834 ; We don't use quad float insns here so we don't need TARGET_HARD_QUAD.
6835 "TARGET_FPU && ! TARGET_V9"
6839 "&& reload_completed
6840 && sparc_absnegfloat_split_legitimate (operands[0], operands[1])"
6841 [(set (match_dup 2) (abs:SF (match_dup 3)))
6842 (set (match_dup 4) (match_dup 5))
6843 (set (match_dup 6) (match_dup 7))]
6844 "operands[2] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]));
6845 operands[3] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]));
6846 operands[4] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]) + 1);
6847 operands[5] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]) + 1);
6848 operands[6] = gen_rtx_raw_REG (DFmode, REGNO (operands[0]) + 2);
6849 operands[7] = gen_rtx_raw_REG (DFmode, REGNO (operands[1]) + 2);"
6850 [(set_attr "type" "fpmove,*")
6851 (set_attr "length" "*,2")])
6853 (define_insn "*abstf2_hq_v9"
6854 [(set (match_operand:TF 0 "register_operand" "=e,e")
6855 (abs:TF (match_operand:TF 1 "register_operand" "0,e")))]
6856 "TARGET_FPU && TARGET_V9 && TARGET_HARD_QUAD"
6860 [(set_attr "type" "fpmove")
6861 (set_attr "fptype" "double,*")])
6863 (define_insn_and_split "*abstf2_v9"
6864 [(set (match_operand:TF 0 "register_operand" "=e,e")
6865 (abs:TF (match_operand:TF 1 "register_operand" "0,e")))]
6866 "TARGET_FPU && TARGET_V9 && !TARGET_HARD_QUAD"
6870 "&& reload_completed
6871 && sparc_absnegfloat_split_legitimate (operands[0], operands[1])"
6872 [(set (match_dup 2) (abs:DF (match_dup 3)))
6873 (set (match_dup 4) (match_dup 5))]
6874 "operands[2] = gen_rtx_raw_REG (DFmode, REGNO (operands[0]));
6875 operands[3] = gen_rtx_raw_REG (DFmode, REGNO (operands[1]));
6876 operands[4] = gen_rtx_raw_REG (DFmode, REGNO (operands[0]) + 2);
6877 operands[5] = gen_rtx_raw_REG (DFmode, REGNO (operands[1]) + 2);"
6878 [(set_attr "type" "fpmove,*")
6879 (set_attr "length" "*,2")
6880 (set_attr "fptype" "double,*")])
6882 (define_expand "absdf2"
6883 [(set (match_operand:DF 0 "register_operand" "")
6884 (abs:DF (match_operand:DF 1 "register_operand" "")))]
6888 (define_insn_and_split "*absdf2_notv9"
6889 [(set (match_operand:DF 0 "register_operand" "=e,e")
6890 (abs:DF (match_operand:DF 1 "register_operand" "0,e")))]
6891 "TARGET_FPU && ! TARGET_V9"
6895 "&& reload_completed
6896 && sparc_absnegfloat_split_legitimate (operands[0], operands[1])"
6897 [(set (match_dup 2) (abs:SF (match_dup 3)))
6898 (set (match_dup 4) (match_dup 5))]
6899 "operands[2] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]));
6900 operands[3] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]));
6901 operands[4] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]) + 1);
6902 operands[5] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]) + 1);"
6903 [(set_attr "type" "fpmove,*")
6904 (set_attr "length" "*,2")])
6906 (define_insn "*absdf2_v9"
6907 [(set (match_operand:DF 0 "register_operand" "=e")
6908 (abs:DF (match_operand:DF 1 "register_operand" "e")))]
6909 "TARGET_FPU && TARGET_V9"
6911 [(set_attr "type" "fpmove")
6912 (set_attr "fptype" "double")])
6914 (define_insn "abssf2"
6915 [(set (match_operand:SF 0 "register_operand" "=f")
6916 (abs:SF (match_operand:SF 1 "register_operand" "f")))]
6919 [(set_attr "type" "fpmove")])
6921 (define_expand "sqrttf2"
6922 [(set (match_operand:TF 0 "nonimmediate_operand" "")
6923 (sqrt:TF (match_operand:TF 1 "general_operand" "")))]
6924 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
6925 "emit_tfmode_unop (SQRT, operands); DONE;")
6927 (define_insn "*sqrttf2_hq"
6928 [(set (match_operand:TF 0 "register_operand" "=e")
6929 (sqrt:TF (match_operand:TF 1 "register_operand" "e")))]
6930 "TARGET_FPU && TARGET_HARD_QUAD"
6932 [(set_attr "type" "fpsqrtd")])
6934 (define_insn "sqrtdf2"
6935 [(set (match_operand:DF 0 "register_operand" "=e")
6936 (sqrt:DF (match_operand:DF 1 "register_operand" "e")))]
6939 [(set_attr "type" "fpsqrtd")
6940 (set_attr "fptype" "double")])
6942 (define_insn "sqrtsf2"
6943 [(set (match_operand:SF 0 "register_operand" "=f")
6944 (sqrt:SF (match_operand:SF 1 "register_operand" "f")))]
6947 [(set_attr "type" "fpsqrts")])
6949 ;;- arithmetic shift instructions
6951 (define_insn "ashlsi3"
6952 [(set (match_operand:SI 0 "register_operand" "=r")
6953 (ashift:SI (match_operand:SI 1 "register_operand" "r")
6954 (match_operand:SI 2 "arith_operand" "rI")))]
6957 if (GET_CODE (operands[2]) == CONST_INT)
6958 operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
6959 return "sll\t%1, %2, %0";
6962 (if_then_else (match_operand 2 "const1_operand" "")
6963 (const_string "ialu") (const_string "shift")))])
6965 (define_expand "ashldi3"
6966 [(set (match_operand:DI 0 "register_operand" "=r")
6967 (ashift:DI (match_operand:DI 1 "register_operand" "r")
6968 (match_operand:SI 2 "arith_operand" "rI")))]
6969 "TARGET_ARCH64 || TARGET_V8PLUS"
6971 if (! TARGET_ARCH64)
6973 if (GET_CODE (operands[2]) == CONST_INT)
6975 emit_insn (gen_ashldi3_v8plus (operands[0], operands[1], operands[2]));
6980 (define_insn "*ashldi3_sp64"
6981 [(set (match_operand:DI 0 "register_operand" "=r")
6982 (ashift:DI (match_operand:DI 1 "register_operand" "r")
6983 (match_operand:SI 2 "arith_operand" "rI")))]
6986 if (GET_CODE (operands[2]) == CONST_INT)
6987 operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
6988 return "sllx\t%1, %2, %0";
6991 (if_then_else (match_operand 2 "const1_operand" "")
6992 (const_string "ialu") (const_string "shift")))])
6995 (define_insn "ashldi3_v8plus"
6996 [(set (match_operand:DI 0 "register_operand" "=&h,&h,r")
6997 (ashift:DI (match_operand:DI 1 "arith_operand" "rI,0,rI")
6998 (match_operand:SI 2 "arith_operand" "rI,rI,rI")))
6999 (clobber (match_scratch:SI 3 "=X,X,&h"))]
7001 "* return output_v8plus_shift (operands, insn, \"sllx\");"
7002 [(set_attr "type" "multi")
7003 (set_attr "length" "5,5,6")])
7005 ;; Optimize (1LL<<x)-1
7006 ;; XXX this also needs to be fixed to handle equal subregs
7007 ;; XXX first before we could re-enable it.
7009 ; [(set (match_operand:DI 0 "register_operand" "=h")
7010 ; (plus:DI (ashift:DI (const_int 1)
7011 ; (match_operand:SI 1 "arith_operand" "rI"))
7013 ; "0 && TARGET_V8PLUS"
7015 ; if (GET_CODE (operands[1]) == REG && REGNO (operands[1]) == REGNO (operands[0]))
7016 ; return "mov\t1, %L0\;sllx\t%L0, %1, %L0\;sub\t%L0, 1, %L0\;srlx\t%L0, 32, %H0";
7017 ; return "mov\t1, %H0\;sllx\t%H0, %1, %L0\;sub\t%L0, 1, %L0\;srlx\t%L0, 32, %H0";
7019 ; [(set_attr "type" "multi")
7020 ; (set_attr "length" "4")])
7022 (define_insn "*cmp_cc_ashift_1"
7023 [(set (reg:CC_NOOV 100)
7024 (compare:CC_NOOV (ashift:SI (match_operand:SI 0 "register_operand" "r")
7028 "addcc\t%0, %0, %%g0"
7029 [(set_attr "type" "compare")])
7031 (define_insn "*cmp_cc_set_ashift_1"
7032 [(set (reg:CC_NOOV 100)
7033 (compare:CC_NOOV (ashift:SI (match_operand:SI 1 "register_operand" "r")
7036 (set (match_operand:SI 0 "register_operand" "=r")
7037 (ashift:SI (match_dup 1) (const_int 1)))]
7040 [(set_attr "type" "compare")])
7042 (define_insn "ashrsi3"
7043 [(set (match_operand:SI 0 "register_operand" "=r")
7044 (ashiftrt:SI (match_operand:SI 1 "register_operand" "r")
7045 (match_operand:SI 2 "arith_operand" "rI")))]
7048 if (GET_CODE (operands[2]) == CONST_INT)
7049 operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
7050 return "sra\t%1, %2, %0";
7052 [(set_attr "type" "shift")])
7054 (define_insn "*ashrsi3_extend"
7055 [(set (match_operand:DI 0 "register_operand" "=r")
7056 (sign_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "r")
7057 (match_operand:SI 2 "arith_operand" "r"))))]
7060 [(set_attr "type" "shift")])
7062 ;; This handles the case as above, but with constant shift instead of
7063 ;; register. Combiner "simplifies" it for us a little bit though.
7064 (define_insn "*ashrsi3_extend2"
7065 [(set (match_operand:DI 0 "register_operand" "=r")
7066 (ashiftrt:DI (ashift:DI (subreg:DI (match_operand:SI 1 "register_operand" "r") 0)
7068 (match_operand:SI 2 "small_int_or_double" "n")))]
7070 && ((GET_CODE (operands[2]) == CONST_INT
7071 && INTVAL (operands[2]) >= 32 && INTVAL (operands[2]) < 64)
7072 || (GET_CODE (operands[2]) == CONST_DOUBLE
7073 && !CONST_DOUBLE_HIGH (operands[2])
7074 && CONST_DOUBLE_LOW (operands[2]) >= 32
7075 && CONST_DOUBLE_LOW (operands[2]) < 64))"
7077 operands[2] = GEN_INT (INTVAL (operands[2]) - 32);
7079 return "sra\t%1, %2, %0";
7081 [(set_attr "type" "shift")])
7083 (define_expand "ashrdi3"
7084 [(set (match_operand:DI 0 "register_operand" "=r")
7085 (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
7086 (match_operand:SI 2 "arith_operand" "rI")))]
7087 "TARGET_ARCH64 || TARGET_V8PLUS"
7089 if (! TARGET_ARCH64)
7091 if (GET_CODE (operands[2]) == CONST_INT)
7092 FAIL; /* prefer generic code in this case */
7093 emit_insn (gen_ashrdi3_v8plus (operands[0], operands[1], operands[2]));
7098 (define_insn "*ashrdi3_sp64"
7099 [(set (match_operand:DI 0 "register_operand" "=r")
7100 (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
7101 (match_operand:SI 2 "arith_operand" "rI")))]
7105 if (GET_CODE (operands[2]) == CONST_INT)
7106 operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
7107 return "srax\t%1, %2, %0";
7109 [(set_attr "type" "shift")])
7112 (define_insn "ashrdi3_v8plus"
7113 [(set (match_operand:DI 0 "register_operand" "=&h,&h,r")
7114 (ashiftrt:DI (match_operand:DI 1 "arith_operand" "rI,0,rI")
7115 (match_operand:SI 2 "arith_operand" "rI,rI,rI")))
7116 (clobber (match_scratch:SI 3 "=X,X,&h"))]
7118 "* return output_v8plus_shift (operands, insn, \"srax\");"
7119 [(set_attr "type" "multi")
7120 (set_attr "length" "5,5,6")])
7122 (define_insn "lshrsi3"
7123 [(set (match_operand:SI 0 "register_operand" "=r")
7124 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
7125 (match_operand:SI 2 "arith_operand" "rI")))]
7128 if (GET_CODE (operands[2]) == CONST_INT)
7129 operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
7130 return "srl\t%1, %2, %0";
7132 [(set_attr "type" "shift")])
7134 ;; This handles the case where
7135 ;; (zero_extend:DI (lshiftrt:SI (match_operand:SI) (match_operand:SI))),
7136 ;; but combiner "simplifies" it for us.
7137 (define_insn "*lshrsi3_extend"
7138 [(set (match_operand:DI 0 "register_operand" "=r")
7139 (and:DI (subreg:DI (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
7140 (match_operand:SI 2 "arith_operand" "r")) 0)
7141 (match_operand 3 "" "")))]
7143 && ((GET_CODE (operands[3]) == CONST_DOUBLE
7144 && CONST_DOUBLE_HIGH (operands[3]) == 0
7145 && CONST_DOUBLE_LOW (operands[3]) == 0xffffffff)
7146 || (HOST_BITS_PER_WIDE_INT >= 64
7147 && GET_CODE (operands[3]) == CONST_INT
7148 && (unsigned HOST_WIDE_INT) INTVAL (operands[3]) == 0xffffffff))"
7150 [(set_attr "type" "shift")])
7152 ;; This handles the case where
7153 ;; (lshiftrt:DI (zero_extend:DI (match_operand:SI)) (const_int >=0 < 32))
7154 ;; but combiner "simplifies" it for us.
7155 (define_insn "*lshrsi3_extend2"
7156 [(set (match_operand:DI 0 "register_operand" "=r")
7157 (zero_extract:DI (subreg:DI (match_operand:SI 1 "register_operand" "r") 0)
7158 (match_operand 2 "small_int_or_double" "n")
7161 && ((GET_CODE (operands[2]) == CONST_INT
7162 && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) < 32)
7163 || (GET_CODE (operands[2]) == CONST_DOUBLE
7164 && CONST_DOUBLE_HIGH (operands[2]) == 0
7165 && (unsigned HOST_WIDE_INT) CONST_DOUBLE_LOW (operands[2]) < 32))"
7167 operands[2] = GEN_INT (32 - INTVAL (operands[2]));
7169 return "srl\t%1, %2, %0";
7171 [(set_attr "type" "shift")])
7173 (define_expand "lshrdi3"
7174 [(set (match_operand:DI 0 "register_operand" "=r")
7175 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
7176 (match_operand:SI 2 "arith_operand" "rI")))]
7177 "TARGET_ARCH64 || TARGET_V8PLUS"
7179 if (! TARGET_ARCH64)
7181 if (GET_CODE (operands[2]) == CONST_INT)
7183 emit_insn (gen_lshrdi3_v8plus (operands[0], operands[1], operands[2]));
7188 (define_insn "*lshrdi3_sp64"
7189 [(set (match_operand:DI 0 "register_operand" "=r")
7190 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
7191 (match_operand:SI 2 "arith_operand" "rI")))]
7194 if (GET_CODE (operands[2]) == CONST_INT)
7195 operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
7196 return "srlx\t%1, %2, %0";
7198 [(set_attr "type" "shift")])
7201 (define_insn "lshrdi3_v8plus"
7202 [(set (match_operand:DI 0 "register_operand" "=&h,&h,r")
7203 (lshiftrt:DI (match_operand:DI 1 "arith_operand" "rI,0,rI")
7204 (match_operand:SI 2 "arith_operand" "rI,rI,rI")))
7205 (clobber (match_scratch:SI 3 "=X,X,&h"))]
7207 "* return output_v8plus_shift (operands, insn, \"srlx\");"
7208 [(set_attr "type" "multi")
7209 (set_attr "length" "5,5,6")])
7212 [(set (match_operand:SI 0 "register_operand" "=r")
7213 (ashiftrt:SI (subreg:SI (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
7215 (match_operand:SI 2 "small_int_or_double" "n")))]
7217 && ((GET_CODE (operands[2]) == CONST_INT
7218 && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) < 32)
7219 || (GET_CODE (operands[2]) == CONST_DOUBLE
7220 && !CONST_DOUBLE_HIGH (operands[2])
7221 && (unsigned HOST_WIDE_INT) CONST_DOUBLE_LOW (operands[2]) < 32))"
7223 operands[2] = GEN_INT (INTVAL (operands[2]) + 32);
7225 return "srax\t%1, %2, %0";
7227 [(set_attr "type" "shift")])
7230 [(set (match_operand:SI 0 "register_operand" "=r")
7231 (lshiftrt:SI (subreg:SI (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
7233 (match_operand:SI 2 "small_int_or_double" "n")))]
7235 && ((GET_CODE (operands[2]) == CONST_INT
7236 && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) < 32)
7237 || (GET_CODE (operands[2]) == CONST_DOUBLE
7238 && !CONST_DOUBLE_HIGH (operands[2])
7239 && (unsigned HOST_WIDE_INT) CONST_DOUBLE_LOW (operands[2]) < 32))"
7241 operands[2] = GEN_INT (INTVAL (operands[2]) + 32);
7243 return "srlx\t%1, %2, %0";
7245 [(set_attr "type" "shift")])
7248 [(set (match_operand:SI 0 "register_operand" "=r")
7249 (ashiftrt:SI (subreg:SI (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
7250 (match_operand:SI 2 "small_int_or_double" "n")) 4)
7251 (match_operand:SI 3 "small_int_or_double" "n")))]
7253 && GET_CODE (operands[2]) == CONST_INT && GET_CODE (operands[3]) == CONST_INT
7254 && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) >= 32
7255 && (unsigned HOST_WIDE_INT) INTVAL (operands[3]) < 32
7256 && (unsigned HOST_WIDE_INT) (INTVAL (operands[2]) + INTVAL (operands[3])) < 64"
7258 operands[2] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[3]));
7260 return "srax\t%1, %2, %0";
7262 [(set_attr "type" "shift")])
7265 [(set (match_operand:SI 0 "register_operand" "=r")
7266 (lshiftrt:SI (subreg:SI (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
7267 (match_operand:SI 2 "small_int_or_double" "n")) 4)
7268 (match_operand:SI 3 "small_int_or_double" "n")))]
7270 && GET_CODE (operands[2]) == CONST_INT && GET_CODE (operands[3]) == CONST_INT
7271 && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) >= 32
7272 && (unsigned HOST_WIDE_INT) INTVAL (operands[3]) < 32
7273 && (unsigned HOST_WIDE_INT) (INTVAL (operands[2]) + INTVAL (operands[3])) < 64"
7275 operands[2] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[3]));
7277 return "srlx\t%1, %2, %0";
7279 [(set_attr "type" "shift")])
7281 ;; Unconditional and other jump instructions
7283 [(set (pc) (label_ref (match_operand 0 "" "")))]
7285 "* return output_ubranch (operands[0], 0, insn);"
7286 [(set_attr "type" "uncond_branch")])
7288 (define_expand "tablejump"
7289 [(parallel [(set (pc) (match_operand 0 "register_operand" "r"))
7290 (use (label_ref (match_operand 1 "" "")))])]
7293 if (GET_MODE (operands[0]) != CASE_VECTOR_MODE)
7296 /* In pic mode, our address differences are against the base of the
7297 table. Add that base value back in; CSE ought to be able to combine
7298 the two address loads. */
7302 tmp = gen_rtx_LABEL_REF (Pmode, operands[1]);
7304 if (CASE_VECTOR_MODE != Pmode)
7305 tmp2 = gen_rtx_SIGN_EXTEND (Pmode, tmp2);
7306 tmp = gen_rtx_PLUS (Pmode, tmp2, tmp);
7307 operands[0] = memory_address (Pmode, tmp);
7311 (define_insn "*tablejump_sp32"
7312 [(set (pc) (match_operand:SI 0 "address_operand" "p"))
7313 (use (label_ref (match_operand 1 "" "")))]
7316 [(set_attr "type" "uncond_branch")])
7318 (define_insn "*tablejump_sp64"
7319 [(set (pc) (match_operand:DI 0 "address_operand" "p"))
7320 (use (label_ref (match_operand 1 "" "")))]
7323 [(set_attr "type" "uncond_branch")])
7325 ;;- jump to subroutine
7326 (define_expand "call"
7327 ;; Note that this expression is not used for generating RTL.
7328 ;; All the RTL is generated explicitly below.
7329 [(call (match_operand 0 "call_operand" "")
7330 (match_operand 3 "" "i"))]
7331 ;; operands[2] is next_arg_register
7332 ;; operands[3] is struct_value_size_rtx.
7337 if (GET_MODE (operands[0]) != FUNCTION_MODE)
7340 if (GET_CODE (operands[3]) != CONST_INT)
7343 if (GET_CODE (XEXP (operands[0], 0)) == LABEL_REF)
7345 /* This is really a PIC sequence. We want to represent
7346 it as a funny jump so its delay slots can be filled.
7348 ??? But if this really *is* a CALL, will not it clobber the
7349 call-clobbered registers? We lose this if it is a JUMP_INSN.
7350 Why cannot we have delay slots filled if it were a CALL? */
7352 /* We accept negative sizes for untyped calls. */
7353 if (! TARGET_ARCH64 && INTVAL (operands[3]) != 0)
7358 gen_rtx_SET (VOIDmode, pc_rtx, XEXP (operands[0], 0)),
7360 gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 15)))));
7366 gen_rtx_SET (VOIDmode, pc_rtx, XEXP (operands[0], 0)),
7367 gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 15)))));
7371 fn_rtx = operands[0];
7373 /* We accept negative sizes for untyped calls. */
7374 if (! TARGET_ARCH64 && INTVAL (operands[3]) != 0)
7378 gen_rtvec (3, gen_rtx_CALL (VOIDmode, fn_rtx, const0_rtx),
7380 gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 15)))));
7385 gen_rtvec (2, gen_rtx_CALL (VOIDmode, fn_rtx, const0_rtx),
7386 gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 15)))));
7393 ;; We can't use the same pattern for these two insns, because then registers
7394 ;; in the address may not be properly reloaded.
7396 (define_insn "*call_address_sp32"
7397 [(call (mem:SI (match_operand:SI 0 "address_operand" "p"))
7398 (match_operand 1 "" ""))
7399 (clobber (reg:SI 15))]
7400 ;;- Do not use operand 1 for most machines.
7403 [(set_attr "type" "call")])
7405 (define_insn "*call_symbolic_sp32"
7406 [(call (mem:SI (match_operand:SI 0 "symbolic_operand" "s"))
7407 (match_operand 1 "" ""))
7408 (clobber (reg:SI 15))]
7409 ;;- Do not use operand 1 for most machines.
7412 [(set_attr "type" "call")])
7414 (define_insn "*call_address_sp64"
7415 [(call (mem:DI (match_operand:DI 0 "address_operand" "p"))
7416 (match_operand 1 "" ""))
7417 (clobber (reg:DI 15))]
7418 ;;- Do not use operand 1 for most machines.
7421 [(set_attr "type" "call")])
7423 (define_insn "*call_symbolic_sp64"
7424 [(call (mem:DI (match_operand:DI 0 "symbolic_operand" "s"))
7425 (match_operand 1 "" ""))
7426 (clobber (reg:DI 15))]
7427 ;;- Do not use operand 1 for most machines.
7430 [(set_attr "type" "call")])
7432 ;; This is a call that wants a structure value.
7433 ;; There is no such critter for v9 (??? we may need one anyway).
7434 (define_insn "*call_address_struct_value_sp32"
7435 [(call (mem:SI (match_operand:SI 0 "address_operand" "p"))
7436 (match_operand 1 "" ""))
7437 (match_operand 2 "immediate_operand" "")
7438 (clobber (reg:SI 15))]
7439 ;;- Do not use operand 1 for most machines.
7440 "! TARGET_ARCH64 && GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) > 0"
7441 "call\t%a0, %1\n\t nop\n\tunimp\t%2"
7442 [(set_attr "type" "call_no_delay_slot")
7443 (set_attr "length" "3")])
7445 ;; This is a call that wants a structure value.
7446 ;; There is no such critter for v9 (??? we may need one anyway).
7447 (define_insn "*call_symbolic_struct_value_sp32"
7448 [(call (mem:SI (match_operand:SI 0 "symbolic_operand" "s"))
7449 (match_operand 1 "" ""))
7450 (match_operand 2 "immediate_operand" "")
7451 (clobber (reg:SI 15))]
7452 ;;- Do not use operand 1 for most machines.
7453 "! TARGET_ARCH64 && GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) > 0"
7454 "call\t%a0, %1\n\t nop\n\tunimp\t%2"
7455 [(set_attr "type" "call_no_delay_slot")
7456 (set_attr "length" "3")])
7458 ;; This is a call that may want a structure value. This is used for
7460 (define_insn "*call_address_untyped_struct_value_sp32"
7461 [(call (mem:SI (match_operand:SI 0 "address_operand" "p"))
7462 (match_operand 1 "" ""))
7463 (match_operand 2 "immediate_operand" "")
7464 (clobber (reg:SI 15))]
7465 ;;- Do not use operand 1 for most machines.
7466 "! TARGET_ARCH64 && GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0"
7467 "call\t%a0, %1\n\t nop\n\tnop"
7468 [(set_attr "type" "call_no_delay_slot")
7469 (set_attr "length" "3")])
7471 ;; This is a call that may want a structure value. This is used for
7473 (define_insn "*call_symbolic_untyped_struct_value_sp32"
7474 [(call (mem:SI (match_operand:SI 0 "symbolic_operand" "s"))
7475 (match_operand 1 "" ""))
7476 (match_operand 2 "immediate_operand" "")
7477 (clobber (reg:SI 15))]
7478 ;;- Do not use operand 1 for most machines.
7479 "! TARGET_ARCH64 && GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0"
7480 "call\t%a0, %1\n\t nop\n\tnop"
7481 [(set_attr "type" "call_no_delay_slot")
7482 (set_attr "length" "3")])
7484 (define_expand "call_value"
7485 ;; Note that this expression is not used for generating RTL.
7486 ;; All the RTL is generated explicitly below.
7487 [(set (match_operand 0 "register_operand" "=rf")
7488 (call (match_operand 1 "" "")
7489 (match_operand 4 "" "")))]
7490 ;; operand 2 is stack_size_rtx
7491 ;; operand 3 is next_arg_register
7497 if (GET_MODE (operands[1]) != FUNCTION_MODE)
7500 fn_rtx = operands[1];
7503 gen_rtx_SET (VOIDmode, operands[0],
7504 gen_rtx_CALL (VOIDmode, fn_rtx, const0_rtx)),
7505 gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 15)));
7507 emit_call_insn (gen_rtx_PARALLEL (VOIDmode, vec));
7512 (define_insn "*call_value_address_sp32"
7513 [(set (match_operand 0 "" "=rf")
7514 (call (mem:SI (match_operand:SI 1 "address_operand" "p"))
7515 (match_operand 2 "" "")))
7516 (clobber (reg:SI 15))]
7517 ;;- Do not use operand 2 for most machines.
7520 [(set_attr "type" "call")])
7522 (define_insn "*call_value_symbolic_sp32"
7523 [(set (match_operand 0 "" "=rf")
7524 (call (mem:SI (match_operand:SI 1 "symbolic_operand" "s"))
7525 (match_operand 2 "" "")))
7526 (clobber (reg:SI 15))]
7527 ;;- Do not use operand 2 for most machines.
7530 [(set_attr "type" "call")])
7532 (define_insn "*call_value_address_sp64"
7533 [(set (match_operand 0 "" "")
7534 (call (mem:DI (match_operand:DI 1 "address_operand" "p"))
7535 (match_operand 2 "" "")))
7536 (clobber (reg:DI 15))]
7537 ;;- Do not use operand 2 for most machines.
7540 [(set_attr "type" "call")])
7542 (define_insn "*call_value_symbolic_sp64"
7543 [(set (match_operand 0 "" "")
7544 (call (mem:DI (match_operand:DI 1 "symbolic_operand" "s"))
7545 (match_operand 2 "" "")))
7546 (clobber (reg:DI 15))]
7547 ;;- Do not use operand 2 for most machines.
7550 [(set_attr "type" "call")])
7552 (define_expand "untyped_call"
7553 [(parallel [(call (match_operand 0 "" "")
7555 (match_operand 1 "" "")
7556 (match_operand 2 "" "")])]
7561 /* Pass constm1 to indicate that it may expect a structure value, but
7562 we don't know what size it is. */
7563 emit_call_insn (GEN_CALL (operands[0], const0_rtx, NULL, constm1_rtx));
7565 for (i = 0; i < XVECLEN (operands[2], 0); i++)
7567 rtx set = XVECEXP (operands[2], 0, i);
7568 emit_move_insn (SET_DEST (set), SET_SRC (set));
7571 /* The optimizer does not know that the call sets the function value
7572 registers we stored in the result block. We avoid problems by
7573 claiming that all hard registers are used and clobbered at this
7575 emit_insn (gen_blockage ());
7581 (define_expand "sibcall"
7582 [(parallel [(call (match_operand 0 "call_operand" "") (const_int 0))
7587 (define_insn "*sibcall_symbolic_sp32"
7588 [(call (mem:SI (match_operand:SI 0 "symbolic_operand" "s"))
7589 (match_operand 1 "" ""))
7592 "* return output_sibcall(insn, operands[0]);"
7593 [(set_attr "type" "sibcall")])
7595 (define_insn "*sibcall_symbolic_sp64"
7596 [(call (mem:DI (match_operand:DI 0 "symbolic_operand" "s"))
7597 (match_operand 1 "" ""))
7600 "* return output_sibcall(insn, operands[0]);"
7601 [(set_attr "type" "sibcall")])
7603 (define_expand "sibcall_value"
7604 [(parallel [(set (match_operand 0 "register_operand" "=rf")
7605 (call (match_operand 1 "" "") (const_int 0)))
7610 (define_insn "*sibcall_value_symbolic_sp32"
7611 [(set (match_operand 0 "" "=rf")
7612 (call (mem:SI (match_operand:SI 1 "symbolic_operand" "s"))
7613 (match_operand 2 "" "")))
7616 "* return output_sibcall(insn, operands[1]);"
7617 [(set_attr "type" "sibcall")])
7619 (define_insn "*sibcall_value_symbolic_sp64"
7620 [(set (match_operand 0 "" "")
7621 (call (mem:DI (match_operand:DI 1 "symbolic_operand" "s"))
7622 (match_operand 2 "" "")))
7625 "* return output_sibcall(insn, operands[1]);"
7626 [(set_attr "type" "sibcall")])
7628 (define_expand "sibcall_epilogue"
7632 sparc_expand_epilogue ();
7636 (define_expand "prologue"
7640 sparc_expand_prologue ();
7644 (define_expand "save_register_window"
7645 [(use (match_operand 0 "arith_operand" ""))]
7651 gen_rtx_SET (VOIDmode,
7653 gen_rtx_PLUS (Pmode,
7654 hard_frame_pointer_rtx,
7656 gen_rtx_UNSPEC_VOLATILE (VOIDmode,
7657 gen_rtvec (1, const0_rtx),
7660 emit_insn (gen_rtx_PARALLEL (VOIDmode, vec));
7664 (define_insn "*save_register_windowsi"
7665 [(set (reg:SI 14) (plus:SI (reg:SI 30)
7666 (match_operand:SI 0 "arith_operand" "rI")))
7667 (unspec_volatile [(const_int 0)] UNSPECV_SAVEW)]
7669 "save\t%%sp, %0, %%sp"
7670 [(set_attr "type" "savew")])
7672 (define_insn "*save_register_windowdi"
7673 [(set (reg:DI 14) (plus:DI (reg:DI 30)
7674 (match_operand:DI 0 "arith_operand" "rI")))
7675 (unspec_volatile [(const_int 0)] UNSPECV_SAVEW)]
7677 "save\t%%sp, %0, %%sp"
7678 [(set_attr "type" "savew")])
7680 (define_expand "epilogue"
7684 sparc_expand_epilogue ();
7687 (define_insn "*return_internal"
7690 "* return output_return (insn);"
7691 [(set_attr "type" "return")
7692 (set (attr "length")
7693 (cond [(eq_attr "leaf_function" "true")
7694 (if_then_else (eq_attr "empty_delay_slot" "true")
7697 (eq_attr "calls_eh_return" "true")
7698 (if_then_else (eq_attr "delayed_branch" "true")
7699 (if_then_else (eq_attr "isa" "v9")
7702 (if_then_else (eq_attr "isa" "v9")
7705 (eq_attr "empty_delay_slot" "true")
7706 (if_then_else (eq_attr "delayed_branch" "true")
7711 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
7712 ;; all of memory. This blocks insns from being moved across this point.
7714 (define_insn "blockage"
7715 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
7718 [(set_attr "length" "0")])
7720 ;; Prepare to return any type including a structure value.
7722 (define_expand "untyped_return"
7723 [(match_operand:BLK 0 "memory_operand" "")
7724 (match_operand 1 "" "")]
7727 rtx valreg1 = gen_rtx_REG (DImode, 24);
7728 rtx valreg2 = gen_rtx_REG (TARGET_ARCH64 ? TFmode : DFmode, 32);
7729 rtx result = operands[0];
7731 if (! TARGET_ARCH64)
7733 rtx rtnreg = gen_rtx_REG (SImode, (current_function_uses_only_leaf_regs
7735 rtx value = gen_reg_rtx (SImode);
7737 /* Fetch the instruction where we will return to and see if it's an unimp
7738 instruction (the most significant 10 bits will be zero). If so,
7739 update the return address to skip the unimp instruction. */
7740 emit_move_insn (value,
7741 gen_rtx_MEM (SImode, plus_constant (rtnreg, 8)));
7742 emit_insn (gen_lshrsi3 (value, value, GEN_INT (22)));
7743 emit_insn (gen_update_return (rtnreg, value));
7746 /* Reload the function value registers. */
7747 emit_move_insn (valreg1, adjust_address (result, DImode, 0));
7748 emit_move_insn (valreg2,
7749 adjust_address (result, TARGET_ARCH64 ? TFmode : DFmode, 8));
7751 /* Put USE insns before the return. */
7752 emit_insn (gen_rtx_USE (VOIDmode, valreg1));
7753 emit_insn (gen_rtx_USE (VOIDmode, valreg2));
7755 /* Construct the return. */
7756 expand_naked_return ();
7761 ;; This is a bit of a hack. We're incrementing a fixed register (%i7),
7762 ;; and parts of the compiler don't want to believe that the add is needed.
7764 (define_insn "update_return"
7765 [(unspec:SI [(match_operand:SI 0 "register_operand" "r")
7766 (match_operand:SI 1 "register_operand" "r")] UNSPEC_UPDATE_RETURN)]
7769 if (flag_delayed_branch)
7770 return "cmp\t%1, 0\n\tbe,a\t.+8\n\t add\t%0, 4, %0";
7772 return "cmp\t%1, 0\n\tbne\t.+12\n\t nop\n\tadd\t%0, 4, %0";
7774 [(set (attr "type") (const_string "multi"))
7775 (set (attr "length")
7776 (if_then_else (eq_attr "delayed_branch" "true")
7785 (define_expand "indirect_jump"
7786 [(set (pc) (match_operand 0 "address_operand" "p"))]
7790 (define_insn "*branch_sp32"
7791 [(set (pc) (match_operand:SI 0 "address_operand" "p"))]
7794 [(set_attr "type" "uncond_branch")])
7796 (define_insn "*branch_sp64"
7797 [(set (pc) (match_operand:DI 0 "address_operand" "p"))]
7800 [(set_attr "type" "uncond_branch")])
7802 (define_expand "nonlocal_goto"
7803 [(match_operand:SI 0 "general_operand" "")
7804 (match_operand:SI 1 "general_operand" "")
7805 (match_operand:SI 2 "general_operand" "")
7806 (match_operand:SI 3 "" "")]
7809 rtx lab = operands[1];
7810 rtx stack = operands[2];
7811 rtx fp = operands[3];
7814 /* Trap instruction to flush all the register windows. */
7815 emit_insn (gen_flush_register_windows ());
7817 /* Load the fp value for the containing fn into %fp. This is needed
7818 because STACK refers to %fp. Note that virtual register instantiation
7819 fails if the virtual %fp isn't set from a register. */
7820 if (GET_CODE (fp) != REG)
7821 fp = force_reg (Pmode, fp);
7822 emit_move_insn (virtual_stack_vars_rtx, fp);
7824 /* Find the containing function's current nonlocal goto handler,
7825 which will do any cleanups and then jump to the label. */
7826 labreg = gen_rtx_REG (Pmode, 8);
7827 emit_move_insn (labreg, lab);
7829 /* Restore %fp from stack pointer value for containing function.
7830 The restore insn that follows will move this to %sp,
7831 and reload the appropriate value into %fp. */
7832 emit_move_insn (hard_frame_pointer_rtx, stack);
7834 emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
7835 emit_insn (gen_rtx_USE (VOIDmode, static_chain_rtx));
7837 /* ??? The V9-specific version was disabled in rev 1.65. */
7838 emit_jump_insn (gen_goto_handler_and_restore (labreg));
7843 ;; Special trap insn to flush register windows.
7844 (define_insn "flush_register_windows"
7845 [(unspec_volatile [(const_int 0)] UNSPECV_FLUSHW)]
7847 { return TARGET_V9 ? "flushw" : "ta\t3"; }
7848 [(set_attr "type" "flushw")])
7850 (define_insn "goto_handler_and_restore"
7851 [(unspec_volatile [(match_operand 0 "register_operand" "=r")] UNSPECV_GOTO)]
7852 "GET_MODE (operands[0]) == Pmode"
7854 if (flag_delayed_branch)
7855 return "jmp\t%0\n\t restore";
7857 return "mov\t%0,%%g1\n\trestore\n\tjmp\t%%g1\n\t nop";
7859 [(set (attr "type") (const_string "multi"))
7860 (set (attr "length")
7861 (if_then_else (eq_attr "delayed_branch" "true")
7865 ;; For __builtin_setjmp we need to flush register windows iff the function
7866 ;; calls alloca as well, because otherwise the register window might be
7867 ;; saved after %sp adjustment and thus setjmp would crash
7868 (define_expand "builtin_setjmp_setup"
7869 [(match_operand 0 "register_operand" "r")]
7872 emit_insn (gen_do_builtin_setjmp_setup ());
7876 (define_insn "do_builtin_setjmp_setup"
7877 [(unspec_volatile [(const_int 0)] UNSPECV_SETJMP)]
7880 if (! current_function_calls_alloca)
7884 fputs ("\tflushw\n", asm_out_file);
7886 fprintf (asm_out_file, "\tst%c\t%%l7, [%%sp+%d]\n",
7887 TARGET_ARCH64 ? 'x' : 'w',
7888 SPARC_STACK_BIAS + 7 * UNITS_PER_WORD);
7889 fprintf (asm_out_file, "\tst%c\t%%fp, [%%sp+%d]\n",
7890 TARGET_ARCH64 ? 'x' : 'w',
7891 SPARC_STACK_BIAS + 14 * UNITS_PER_WORD);
7892 fprintf (asm_out_file, "\tst%c\t%%i7, [%%sp+%d]\n",
7893 TARGET_ARCH64 ? 'x' : 'w',
7894 SPARC_STACK_BIAS + 15 * UNITS_PER_WORD);
7897 [(set_attr "type" "multi")
7898 (set (attr "length")
7899 (cond [(eq_attr "calls_alloca" "false")
7901 (eq_attr "isa" "!v9")
7903 (eq_attr "pic" "true")
7904 (const_int 4)] (const_int 3)))])
7906 ;; Pattern for use after a setjmp to store FP and the return register
7907 ;; into the stack area.
7909 (define_expand "setjmp"
7914 emit_insn (gen_setjmp_64 ());
7916 emit_insn (gen_setjmp_32 ());
7920 (define_expand "setjmp_32"
7921 [(set (mem:SI (plus:SI (reg:SI 14) (const_int 56))) (match_dup 0))
7922 (set (mem:SI (plus:SI (reg:SI 14) (const_int 60))) (reg:SI 31))]
7924 { operands[0] = frame_pointer_rtx; })
7926 (define_expand "setjmp_64"
7927 [(set (mem:DI (plus:DI (reg:DI 14) (const_int 112))) (match_dup 0))
7928 (set (mem:DI (plus:DI (reg:DI 14) (const_int 120))) (reg:DI 31))]
7930 { operands[0] = frame_pointer_rtx; })
7932 ;; Special pattern for the FLUSH instruction.
7934 ; We do SImode and DImode versions of this to quiet down genrecog's complaints
7935 ; of the define_insn otherwise missing a mode. We make "flush", aka
7936 ; gen_flush, the default one since sparc_initialize_trampoline uses
7937 ; it on SImode mem values.
7939 (define_insn "flush"
7940 [(unspec_volatile [(match_operand:SI 0 "memory_operand" "m")] UNSPECV_FLUSH)]
7942 { return TARGET_V9 ? "flush\t%f0" : "iflush\t%f0"; }
7943 [(set_attr "type" "iflush")])
7945 (define_insn "flushdi"
7946 [(unspec_volatile [(match_operand:DI 0 "memory_operand" "m")] UNSPECV_FLUSH)]
7948 { return TARGET_V9 ? "flush\t%f0" : "iflush\t%f0"; }
7949 [(set_attr "type" "iflush")])
7954 ;; The scan instruction searches from the most significant bit while ffs
7955 ;; searches from the least significant bit. The bit index and treatment of
7956 ;; zero also differ. It takes at least 7 instructions to get the proper
7957 ;; result. Here is an obvious 8 instruction sequence.
7960 (define_insn "ffssi2"
7961 [(set (match_operand:SI 0 "register_operand" "=&r")
7962 (ffs:SI (match_operand:SI 1 "register_operand" "r")))
7963 (clobber (match_scratch:SI 2 "=&r"))]
7964 "TARGET_SPARCLITE || TARGET_SPARCLET"
7966 return "sub\t%%g0, %1, %0\;and\t%0, %1, %0\;scan\t%0, 0, %0\;mov\t32, %2\;sub\t%2, %0, %0\;sra\t%0, 31, %2\;and\t%2, 31, %2\;add\t%2, %0, %0";
7968 [(set_attr "type" "multi")
7969 (set_attr "length" "8")])
7971 ;; ??? This should be a define expand, so that the extra instruction have
7972 ;; a chance of being optimized away.
7974 ;; Disabled because none of the UltraSPARCs implement popc. The HAL R1
7975 ;; does, but no one uses that and we don't have a switch for it.
7977 ;(define_insn "ffsdi2"
7978 ; [(set (match_operand:DI 0 "register_operand" "=&r")
7979 ; (ffs:DI (match_operand:DI 1 "register_operand" "r")))
7980 ; (clobber (match_scratch:DI 2 "=&r"))]
7982 ; "neg\t%1, %2\;xnor\t%1, %2, %2\;popc\t%2, %0\;movzr\t%1, 0, %0"
7983 ; [(set_attr "type" "multi")
7984 ; (set_attr "length" "4")])
7988 ;; Peepholes go at the end.
7990 ;; Optimize consecutive loads or stores into ldd and std when possible.
7991 ;; The conditions in which we do this are very restricted and are
7992 ;; explained in the code for {registers,memory}_ok_for_ldd functions.
7995 [(set (match_operand:SI 0 "memory_operand" "")
7997 (set (match_operand:SI 1 "memory_operand" "")
8000 && mems_ok_for_ldd_peep (operands[0], operands[1], NULL_RTX)"
8003 "operands[0] = widen_memory_access (operands[0], DImode, 0);")
8006 [(set (match_operand:SI 0 "memory_operand" "")
8008 (set (match_operand:SI 1 "memory_operand" "")
8011 && mems_ok_for_ldd_peep (operands[1], operands[0], NULL_RTX)"
8014 "operands[1] = widen_memory_access (operands[1], DImode, 0);")
8017 [(set (match_operand:SI 0 "register_operand" "")
8018 (match_operand:SI 1 "memory_operand" ""))
8019 (set (match_operand:SI 2 "register_operand" "")
8020 (match_operand:SI 3 "memory_operand" ""))]
8021 "registers_ok_for_ldd_peep (operands[0], operands[2])
8022 && mems_ok_for_ldd_peep (operands[1], operands[3], operands[0])"
8025 "operands[1] = widen_memory_access (operands[1], DImode, 0);
8026 operands[0] = gen_rtx_REG (DImode, REGNO (operands[0]));")
8029 [(set (match_operand:SI 0 "memory_operand" "")
8030 (match_operand:SI 1 "register_operand" ""))
8031 (set (match_operand:SI 2 "memory_operand" "")
8032 (match_operand:SI 3 "register_operand" ""))]
8033 "registers_ok_for_ldd_peep (operands[1], operands[3])
8034 && mems_ok_for_ldd_peep (operands[0], operands[2], NULL_RTX)"
8037 "operands[0] = widen_memory_access (operands[0], DImode, 0);
8038 operands[1] = gen_rtx_REG (DImode, REGNO (operands[1]));")
8041 [(set (match_operand:SF 0 "register_operand" "")
8042 (match_operand:SF 1 "memory_operand" ""))
8043 (set (match_operand:SF 2 "register_operand" "")
8044 (match_operand:SF 3 "memory_operand" ""))]
8045 "registers_ok_for_ldd_peep (operands[0], operands[2])
8046 && mems_ok_for_ldd_peep (operands[1], operands[3], operands[0])"
8049 "operands[1] = widen_memory_access (operands[1], DFmode, 0);
8050 operands[0] = gen_rtx_REG (DFmode, REGNO (operands[0]));")
8053 [(set (match_operand:SF 0 "memory_operand" "")
8054 (match_operand:SF 1 "register_operand" ""))
8055 (set (match_operand:SF 2 "memory_operand" "")
8056 (match_operand:SF 3 "register_operand" ""))]
8057 "registers_ok_for_ldd_peep (operands[1], operands[3])
8058 && mems_ok_for_ldd_peep (operands[0], operands[2], NULL_RTX)"
8061 "operands[0] = widen_memory_access (operands[0], DFmode, 0);
8062 operands[1] = gen_rtx_REG (DFmode, REGNO (operands[1]));")
8065 [(set (match_operand:SI 0 "register_operand" "")
8066 (match_operand:SI 1 "memory_operand" ""))
8067 (set (match_operand:SI 2 "register_operand" "")
8068 (match_operand:SI 3 "memory_operand" ""))]
8069 "registers_ok_for_ldd_peep (operands[2], operands[0])
8070 && mems_ok_for_ldd_peep (operands[3], operands[1], operands[0])"
8073 "operands[3] = widen_memory_access (operands[3], DImode, 0);
8074 operands[2] = gen_rtx_REG (DImode, REGNO (operands[2]));")
8077 [(set (match_operand:SI 0 "memory_operand" "")
8078 (match_operand:SI 1 "register_operand" ""))
8079 (set (match_operand:SI 2 "memory_operand" "")
8080 (match_operand:SI 3 "register_operand" ""))]
8081 "registers_ok_for_ldd_peep (operands[3], operands[1])
8082 && mems_ok_for_ldd_peep (operands[2], operands[0], NULL_RTX)"
8085 "operands[2] = widen_memory_access (operands[2], DImode, 0);
8086 operands[3] = gen_rtx_REG (DImode, REGNO (operands[3]));
8090 [(set (match_operand:SF 0 "register_operand" "")
8091 (match_operand:SF 1 "memory_operand" ""))
8092 (set (match_operand:SF 2 "register_operand" "")
8093 (match_operand:SF 3 "memory_operand" ""))]
8094 "registers_ok_for_ldd_peep (operands[2], operands[0])
8095 && mems_ok_for_ldd_peep (operands[3], operands[1], operands[0])"
8098 "operands[3] = widen_memory_access (operands[3], DFmode, 0);
8099 operands[2] = gen_rtx_REG (DFmode, REGNO (operands[2]));")
8102 [(set (match_operand:SF 0 "memory_operand" "")
8103 (match_operand:SF 1 "register_operand" ""))
8104 (set (match_operand:SF 2 "memory_operand" "")
8105 (match_operand:SF 3 "register_operand" ""))]
8106 "registers_ok_for_ldd_peep (operands[3], operands[1])
8107 && mems_ok_for_ldd_peep (operands[2], operands[0], NULL_RTX)"
8110 "operands[2] = widen_memory_access (operands[2], DFmode, 0);
8111 operands[3] = gen_rtx_REG (DFmode, REGNO (operands[3]));")
8113 ;; Optimize the case of following a reg-reg move with a test
8114 ;; of reg just moved. Don't allow floating point regs for operand 0 or 1.
8115 ;; This can result from a float to fix conversion.
8118 [(set (match_operand:SI 0 "register_operand" "")
8119 (match_operand:SI 1 "register_operand" ""))
8121 (compare:CC (match_operand:SI 2 "register_operand" "")
8123 "(rtx_equal_p (operands[2], operands[0])
8124 || rtx_equal_p (operands[2], operands[1]))
8125 && ! SPARC_FP_REG_P (REGNO (operands[0]))
8126 && ! SPARC_FP_REG_P (REGNO (operands[1]))"
8127 [(parallel [(set (match_dup 0) (match_dup 1))
8129 (compare:CC (match_dup 1) (const_int 0)))])]
8133 [(set (match_operand:DI 0 "register_operand" "")
8134 (match_operand:DI 1 "register_operand" ""))
8136 (compare:CCX (match_operand:DI 2 "register_operand" "")
8139 && (rtx_equal_p (operands[2], operands[0])
8140 || rtx_equal_p (operands[2], operands[1]))
8141 && ! SPARC_FP_REG_P (REGNO (operands[0]))
8142 && ! SPARC_FP_REG_P (REGNO (operands[1]))"
8143 [(parallel [(set (match_dup 0) (match_dup 1))
8145 (compare:CCX (match_dup 1) (const_int 0)))])]
8148 ;; ??? UltraSPARC-III note: A memory operation loading into the floating point register
8149 ;; ??? file, if it hits the prefetch cache, has a chance to dual-issue with other memory
8150 ;; ??? operations. With DFA we might be able to model this, but it requires a lot of
8152 (define_expand "prefetch"
8153 [(match_operand 0 "address_operand" "")
8154 (match_operand 1 "const_int_operand" "")
8155 (match_operand 2 "const_int_operand" "")]
8159 emit_insn (gen_prefetch_64 (operands[0], operands[1], operands[2]));
8161 emit_insn (gen_prefetch_32 (operands[0], operands[1], operands[2]));
8165 (define_insn "prefetch_64"
8166 [(prefetch (match_operand:DI 0 "address_operand" "p")
8167 (match_operand:DI 1 "const_int_operand" "n")
8168 (match_operand:DI 2 "const_int_operand" "n"))]
8171 static const char * const prefetch_instr[2][2] = {
8173 "prefetch\t[%a0], 1", /* no locality: prefetch for one read */
8174 "prefetch\t[%a0], 0", /* medium to high locality: prefetch for several reads */
8177 "prefetch\t[%a0], 3", /* no locality: prefetch for one write */
8178 "prefetch\t[%a0], 2", /* medium to high locality: prefetch for several writes */
8181 int read_or_write = INTVAL (operands[1]);
8182 int locality = INTVAL (operands[2]);
8184 if (read_or_write != 0 && read_or_write != 1)
8186 if (locality < 0 || locality > 3)
8188 return prefetch_instr [read_or_write][locality == 0 ? 0 : 1];
8190 [(set_attr "type" "load")])
8192 (define_insn "prefetch_32"
8193 [(prefetch (match_operand:SI 0 "address_operand" "p")
8194 (match_operand:SI 1 "const_int_operand" "n")
8195 (match_operand:SI 2 "const_int_operand" "n"))]
8198 static const char * const prefetch_instr[2][2] = {
8200 "prefetch\t[%a0], 1", /* no locality: prefetch for one read */
8201 "prefetch\t[%a0], 0", /* medium to high locality: prefetch for several reads */
8204 "prefetch\t[%a0], 3", /* no locality: prefetch for one write */
8205 "prefetch\t[%a0], 2", /* medium to high locality: prefetch for several writes */
8208 int read_or_write = INTVAL (operands[1]);
8209 int locality = INTVAL (operands[2]);
8211 if (read_or_write != 0 && read_or_write != 1)
8213 if (locality < 0 || locality > 3)
8215 return prefetch_instr [read_or_write][locality == 0 ? 0 : 1];
8217 [(set_attr "type" "load")])
8220 [(trap_if (const_int 1) (const_int 5))]
8223 [(set_attr "type" "trap")])
8225 (define_expand "conditional_trap"
8226 [(trap_if (match_operator 0 "noov_compare_op" [(match_dup 2) (match_dup 3)])
8227 (match_operand:SI 1 "arith_operand" ""))]
8229 "operands[2] = gen_compare_reg (GET_CODE (operands[0]),
8230 sparc_compare_op0, sparc_compare_op1);
8231 if (GET_MODE (operands[2]) != CCmode && GET_MODE (operands[2]) != CCXmode)
8233 operands[3] = const0_rtx;")
8236 [(trap_if (match_operator 0 "noov_compare_op" [(reg:CC 100) (const_int 0)])
8237 (match_operand:SI 1 "arith_operand" "rM"))]
8241 return "t%C0\t%%icc, %1";
8245 [(set_attr "type" "trap")])
8248 [(trap_if (match_operator 0 "noov_compare_op" [(reg:CCX 100) (const_int 0)])
8249 (match_operand:SI 1 "arith_operand" "rM"))]
8252 [(set_attr "type" "trap")])
8255 (define_insn "tgd_hi22"
8256 [(set (match_operand:SI 0 "register_operand" "=r")
8257 (high:SI (unspec:SI [(match_operand 1 "tgd_symbolic_operand" "")]
8260 "sethi\\t%%tgd_hi22(%a1), %0")
8262 (define_insn "tgd_lo10"
8263 [(set (match_operand:SI 0 "register_operand" "=r")
8264 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
8265 (unspec:SI [(match_operand 2 "tgd_symbolic_operand" "")]
8268 "add\\t%1, %%tgd_lo10(%a2), %0")
8270 (define_insn "tgd_add32"
8271 [(set (match_operand:SI 0 "register_operand" "=r")
8272 (plus:SI (match_operand:SI 1 "register_operand" "r")
8273 (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8274 (match_operand 3 "tgd_symbolic_operand" "")]
8276 "TARGET_TLS && TARGET_ARCH32"
8277 "add\\t%1, %2, %0, %%tgd_add(%a3)")
8279 (define_insn "tgd_add64"
8280 [(set (match_operand:DI 0 "register_operand" "=r")
8281 (plus:DI (match_operand:DI 1 "register_operand" "r")
8282 (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8283 (match_operand 3 "tgd_symbolic_operand" "")]
8285 "TARGET_TLS && TARGET_ARCH64"
8286 "add\\t%1, %2, %0, %%tgd_add(%a3)")
8288 (define_insn "tgd_call32"
8289 [(set (match_operand 0 "register_operand" "=r")
8290 (call (mem:SI (unspec:SI [(match_operand:SI 1 "symbolic_operand" "s")
8291 (match_operand 2 "tgd_symbolic_operand" "")]
8293 (match_operand 3 "" "")))
8294 (clobber (reg:SI 15))]
8295 "TARGET_TLS && TARGET_ARCH32"
8296 "call\t%a1, %%tgd_call(%a2)%#"
8297 [(set_attr "type" "call")])
8299 (define_insn "tgd_call64"
8300 [(set (match_operand 0 "register_operand" "=r")
8301 (call (mem:DI (unspec:DI [(match_operand:DI 1 "symbolic_operand" "s")
8302 (match_operand 2 "tgd_symbolic_operand" "")]
8304 (match_operand 3 "" "")))
8305 (clobber (reg:DI 15))]
8306 "TARGET_TLS && TARGET_ARCH64"
8307 "call\t%a1, %%tgd_call(%a2)%#"
8308 [(set_attr "type" "call")])
8310 (define_insn "tldm_hi22"
8311 [(set (match_operand:SI 0 "register_operand" "=r")
8312 (high:SI (unspec:SI [(const_int 0)] UNSPEC_TLSLDM)))]
8314 "sethi\\t%%tldm_hi22(%&), %0")
8316 (define_insn "tldm_lo10"
8317 [(set (match_operand:SI 0 "register_operand" "=r")
8318 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
8319 (unspec:SI [(const_int 0)] UNSPEC_TLSLDM)))]
8321 "add\\t%1, %%tldm_lo10(%&), %0")
8323 (define_insn "tldm_add32"
8324 [(set (match_operand:SI 0 "register_operand" "=r")
8325 (plus:SI (match_operand:SI 1 "register_operand" "r")
8326 (unspec:SI [(match_operand:SI 2 "register_operand" "r")]
8328 "TARGET_TLS && TARGET_ARCH32"
8329 "add\\t%1, %2, %0, %%tldm_add(%&)")
8331 (define_insn "tldm_add64"
8332 [(set (match_operand:DI 0 "register_operand" "=r")
8333 (plus:DI (match_operand:DI 1 "register_operand" "r")
8334 (unspec:DI [(match_operand:SI 2 "register_operand" "r")]
8336 "TARGET_TLS && TARGET_ARCH64"
8337 "add\\t%1, %2, %0, %%tldm_add(%&)")
8339 (define_insn "tldm_call32"
8340 [(set (match_operand 0 "register_operand" "=r")
8341 (call (mem:SI (unspec:SI [(match_operand:SI 1 "symbolic_operand" "s")]
8343 (match_operand 2 "" "")))
8344 (clobber (reg:SI 15))]
8345 "TARGET_TLS && TARGET_ARCH32"
8346 "call\t%a1, %%tldm_call(%&)%#"
8347 [(set_attr "type" "call")])
8349 (define_insn "tldm_call64"
8350 [(set (match_operand 0 "register_operand" "=r")
8351 (call (mem:DI (unspec:DI [(match_operand:DI 1 "symbolic_operand" "s")]
8353 (match_operand 2 "" "")))
8354 (clobber (reg:DI 15))]
8355 "TARGET_TLS && TARGET_ARCH64"
8356 "call\t%a1, %%tldm_call(%&)%#"
8357 [(set_attr "type" "call")])
8359 (define_insn "tldo_hix22"
8360 [(set (match_operand:SI 0 "register_operand" "=r")
8361 (high:SI (unspec:SI [(match_operand 1 "tld_symbolic_operand" "")]
8364 "sethi\\t%%tldo_hix22(%a1), %0")
8366 (define_insn "tldo_lox10"
8367 [(set (match_operand:SI 0 "register_operand" "=r")
8368 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
8369 (unspec:SI [(match_operand 2 "tld_symbolic_operand" "")]
8372 "xor\\t%1, %%tldo_lox10(%a2), %0")
8374 (define_insn "tldo_add32"
8375 [(set (match_operand:SI 0 "register_operand" "=r")
8376 (plus:SI (match_operand:SI 1 "register_operand" "r")
8377 (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8378 (match_operand 3 "tld_symbolic_operand" "")]
8380 "TARGET_TLS && TARGET_ARCH32"
8381 "add\\t%1, %2, %0, %%tldo_add(%a3)")
8383 (define_insn "tldo_add64"
8384 [(set (match_operand:DI 0 "register_operand" "=r")
8385 (plus:DI (match_operand:DI 1 "register_operand" "r")
8386 (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8387 (match_operand 3 "tld_symbolic_operand" "")]
8389 "TARGET_TLS && TARGET_ARCH64"
8390 "add\\t%1, %2, %0, %%tldo_add(%a3)")
8392 (define_insn "tie_hi22"
8393 [(set (match_operand:SI 0 "register_operand" "=r")
8394 (high:SI (unspec:SI [(match_operand 1 "tie_symbolic_operand" "")]
8397 "sethi\\t%%tie_hi22(%a1), %0")
8399 (define_insn "tie_lo10"
8400 [(set (match_operand:SI 0 "register_operand" "=r")
8401 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
8402 (unspec:SI [(match_operand 2 "tie_symbolic_operand" "")]
8405 "add\\t%1, %%tie_lo10(%a2), %0")
8407 (define_insn "tie_ld32"
8408 [(set (match_operand:SI 0 "register_operand" "=r")
8409 (unspec:SI [(match_operand:SI 1 "register_operand" "r")
8410 (match_operand:SI 2 "register_operand" "r")
8411 (match_operand 3 "tie_symbolic_operand" "")]
8413 "TARGET_TLS && TARGET_ARCH32"
8414 "ld\\t[%1 + %2], %0, %%tie_ld(%a3)"
8415 [(set_attr "type" "load")])
8417 (define_insn "tie_ld64"
8418 [(set (match_operand:DI 0 "register_operand" "=r")
8419 (unspec:DI [(match_operand:DI 1 "register_operand" "r")
8420 (match_operand:SI 2 "register_operand" "r")
8421 (match_operand 3 "tie_symbolic_operand" "")]
8423 "TARGET_TLS && TARGET_ARCH64"
8424 "ldx\\t[%1 + %2], %0, %%tie_ldx(%a3)"
8425 [(set_attr "type" "load")])
8427 (define_insn "tie_add32"
8428 [(set (match_operand:SI 0 "register_operand" "=r")
8429 (plus:SI (match_operand:SI 1 "register_operand" "r")
8430 (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8431 (match_operand 3 "tie_symbolic_operand" "")]
8433 "TARGET_SUN_TLS && TARGET_ARCH32"
8434 "add\\t%1, %2, %0, %%tie_add(%a3)")
8436 (define_insn "tie_add64"
8437 [(set (match_operand:DI 0 "register_operand" "=r")
8438 (plus:DI (match_operand:DI 1 "register_operand" "r")
8439 (unspec:DI [(match_operand:DI 2 "register_operand" "r")
8440 (match_operand 3 "tie_symbolic_operand" "")]
8442 "TARGET_SUN_TLS && TARGET_ARCH64"
8443 "add\\t%1, %2, %0, %%tie_add(%a3)")
8445 (define_insn "tle_hix22_sp32"
8446 [(set (match_operand:SI 0 "register_operand" "=r")
8447 (high:SI (unspec:SI [(match_operand 1 "tle_symbolic_operand" "")]
8449 "TARGET_TLS && TARGET_ARCH32"
8450 "sethi\\t%%tle_hix22(%a1), %0")
8452 (define_insn "tle_lox10_sp32"
8453 [(set (match_operand:SI 0 "register_operand" "=r")
8454 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
8455 (unspec:SI [(match_operand 2 "tle_symbolic_operand" "")]
8457 "TARGET_TLS && TARGET_ARCH32"
8458 "xor\\t%1, %%tle_lox10(%a2), %0")
8460 (define_insn "tle_hix22_sp64"
8461 [(set (match_operand:DI 0 "register_operand" "=r")
8462 (high:DI (unspec:DI [(match_operand 1 "tle_symbolic_operand" "")]
8464 "TARGET_TLS && TARGET_ARCH64"
8465 "sethi\\t%%tle_hix22(%a1), %0")
8467 (define_insn "tle_lox10_sp64"
8468 [(set (match_operand:DI 0 "register_operand" "=r")
8469 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
8470 (unspec:DI [(match_operand 2 "tle_symbolic_operand" "")]
8472 "TARGET_TLS && TARGET_ARCH64"
8473 "xor\\t%1, %%tle_lox10(%a2), %0")
8475 ;; Now patterns combining tldo_add{32,64} with some integer loads or stores
8476 (define_insn "*tldo_ldub_sp32"
8477 [(set (match_operand:QI 0 "register_operand" "=r")
8478 (mem:QI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8479 (match_operand 3 "tld_symbolic_operand" "")]
8481 (match_operand:SI 1 "register_operand" "r"))))]
8482 "TARGET_TLS && TARGET_ARCH32"
8483 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
8484 [(set_attr "type" "load")
8485 (set_attr "us3load_type" "3cycle")])
8487 (define_insn "*tldo_ldub1_sp32"
8488 [(set (match_operand:HI 0 "register_operand" "=r")
8489 (zero_extend:HI (mem:QI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8490 (match_operand 3 "tld_symbolic_operand" "")]
8492 (match_operand:SI 1 "register_operand" "r")))))]
8493 "TARGET_TLS && TARGET_ARCH32"
8494 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
8495 [(set_attr "type" "load")
8496 (set_attr "us3load_type" "3cycle")])
8498 (define_insn "*tldo_ldub2_sp32"
8499 [(set (match_operand:SI 0 "register_operand" "=r")
8500 (zero_extend:SI (mem:QI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8501 (match_operand 3 "tld_symbolic_operand" "")]
8503 (match_operand:SI 1 "register_operand" "r")))))]
8504 "TARGET_TLS && TARGET_ARCH32"
8505 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
8506 [(set_attr "type" "load")
8507 (set_attr "us3load_type" "3cycle")])
8509 (define_insn "*tldo_ldsb1_sp32"
8510 [(set (match_operand:HI 0 "register_operand" "=r")
8511 (sign_extend:HI (mem:QI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8512 (match_operand 3 "tld_symbolic_operand" "")]
8514 (match_operand:SI 1 "register_operand" "r")))))]
8515 "TARGET_TLS && TARGET_ARCH32"
8516 "ldsb\t[%1 + %2], %0, %%tldo_add(%3)"
8517 [(set_attr "type" "sload")
8518 (set_attr "us3load_type" "3cycle")])
8520 (define_insn "*tldo_ldsb2_sp32"
8521 [(set (match_operand:SI 0 "register_operand" "=r")
8522 (sign_extend:SI (mem:QI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8523 (match_operand 3 "tld_symbolic_operand" "")]
8525 (match_operand:SI 1 "register_operand" "r")))))]
8526 "TARGET_TLS && TARGET_ARCH32"
8527 "ldsb\t[%1 + %2], %0, %%tldo_add(%3)"
8528 [(set_attr "type" "sload")
8529 (set_attr "us3load_type" "3cycle")])
8531 (define_insn "*tldo_ldub_sp64"
8532 [(set (match_operand:QI 0 "register_operand" "=r")
8533 (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8534 (match_operand 3 "tld_symbolic_operand" "")]
8536 (match_operand:DI 1 "register_operand" "r"))))]
8537 "TARGET_TLS && TARGET_ARCH64"
8538 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
8539 [(set_attr "type" "load")
8540 (set_attr "us3load_type" "3cycle")])
8542 (define_insn "*tldo_ldub1_sp64"
8543 [(set (match_operand:HI 0 "register_operand" "=r")
8544 (zero_extend:HI (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8545 (match_operand 3 "tld_symbolic_operand" "")]
8547 (match_operand:DI 1 "register_operand" "r")))))]
8548 "TARGET_TLS && TARGET_ARCH64"
8549 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
8550 [(set_attr "type" "load")
8551 (set_attr "us3load_type" "3cycle")])
8553 (define_insn "*tldo_ldub2_sp64"
8554 [(set (match_operand:SI 0 "register_operand" "=r")
8555 (zero_extend:SI (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8556 (match_operand 3 "tld_symbolic_operand" "")]
8558 (match_operand:DI 1 "register_operand" "r")))))]
8559 "TARGET_TLS && TARGET_ARCH64"
8560 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
8561 [(set_attr "type" "load")
8562 (set_attr "us3load_type" "3cycle")])
8564 (define_insn "*tldo_ldub3_sp64"
8565 [(set (match_operand:DI 0 "register_operand" "=r")
8566 (zero_extend:DI (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8567 (match_operand 3 "tld_symbolic_operand" "")]
8569 (match_operand:DI 1 "register_operand" "r")))))]
8570 "TARGET_TLS && TARGET_ARCH64"
8571 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
8572 [(set_attr "type" "load")
8573 (set_attr "us3load_type" "3cycle")])
8575 (define_insn "*tldo_ldsb1_sp64"
8576 [(set (match_operand:HI 0 "register_operand" "=r")
8577 (sign_extend:HI (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8578 (match_operand 3 "tld_symbolic_operand" "")]
8580 (match_operand:DI 1 "register_operand" "r")))))]
8581 "TARGET_TLS && TARGET_ARCH64"
8582 "ldsb\t[%1 + %2], %0, %%tldo_add(%3)"
8583 [(set_attr "type" "sload")
8584 (set_attr "us3load_type" "3cycle")])
8586 (define_insn "*tldo_ldsb2_sp64"
8587 [(set (match_operand:SI 0 "register_operand" "=r")
8588 (sign_extend:SI (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8589 (match_operand 3 "tld_symbolic_operand" "")]
8591 (match_operand:DI 1 "register_operand" "r")))))]
8592 "TARGET_TLS && TARGET_ARCH64"
8593 "ldsb\t[%1 + %2], %0, %%tldo_add(%3)"
8594 [(set_attr "type" "sload")
8595 (set_attr "us3load_type" "3cycle")])
8597 (define_insn "*tldo_ldsb3_sp64"
8598 [(set (match_operand:DI 0 "register_operand" "=r")
8599 (sign_extend:DI (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8600 (match_operand 3 "tld_symbolic_operand" "")]
8602 (match_operand:DI 1 "register_operand" "r")))))]
8603 "TARGET_TLS && TARGET_ARCH64"
8604 "ldsb\t[%1 + %2], %0, %%tldo_add(%3)"
8605 [(set_attr "type" "sload")
8606 (set_attr "us3load_type" "3cycle")])
8608 (define_insn "*tldo_lduh_sp32"
8609 [(set (match_operand:HI 0 "register_operand" "=r")
8610 (mem:HI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8611 (match_operand 3 "tld_symbolic_operand" "")]
8613 (match_operand:SI 1 "register_operand" "r"))))]
8614 "TARGET_TLS && TARGET_ARCH32"
8615 "lduh\t[%1 + %2], %0, %%tldo_add(%3)"
8616 [(set_attr "type" "load")
8617 (set_attr "us3load_type" "3cycle")])
8619 (define_insn "*tldo_lduh1_sp32"
8620 [(set (match_operand:SI 0 "register_operand" "=r")
8621 (zero_extend:SI (mem:HI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8622 (match_operand 3 "tld_symbolic_operand" "")]
8624 (match_operand:SI 1 "register_operand" "r")))))]
8625 "TARGET_TLS && TARGET_ARCH32"
8626 "lduh\t[%1 + %2], %0, %%tldo_add(%3)"
8627 [(set_attr "type" "load")
8628 (set_attr "us3load_type" "3cycle")])
8630 (define_insn "*tldo_ldsh1_sp32"
8631 [(set (match_operand:SI 0 "register_operand" "=r")
8632 (sign_extend:SI (mem:HI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8633 (match_operand 3 "tld_symbolic_operand" "")]
8635 (match_operand:SI 1 "register_operand" "r")))))]
8636 "TARGET_TLS && TARGET_ARCH32"
8637 "ldsh\t[%1 + %2], %0, %%tldo_add(%3)"
8638 [(set_attr "type" "sload")
8639 (set_attr "us3load_type" "3cycle")])
8641 (define_insn "*tldo_lduh_sp64"
8642 [(set (match_operand:HI 0 "register_operand" "=r")
8643 (mem:HI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8644 (match_operand 3 "tld_symbolic_operand" "")]
8646 (match_operand:DI 1 "register_operand" "r"))))]
8647 "TARGET_TLS && TARGET_ARCH64"
8648 "lduh\t[%1 + %2], %0, %%tldo_add(%3)"
8649 [(set_attr "type" "load")
8650 (set_attr "us3load_type" "3cycle")])
8652 (define_insn "*tldo_lduh1_sp64"
8653 [(set (match_operand:SI 0 "register_operand" "=r")
8654 (zero_extend:SI (mem:HI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8655 (match_operand 3 "tld_symbolic_operand" "")]
8657 (match_operand:DI 1 "register_operand" "r")))))]
8658 "TARGET_TLS && TARGET_ARCH64"
8659 "lduh\t[%1 + %2], %0, %%tldo_add(%3)"
8660 [(set_attr "type" "load")
8661 (set_attr "us3load_type" "3cycle")])
8663 (define_insn "*tldo_lduh2_sp64"
8664 [(set (match_operand:DI 0 "register_operand" "=r")
8665 (zero_extend:DI (mem:HI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8666 (match_operand 3 "tld_symbolic_operand" "")]
8668 (match_operand:DI 1 "register_operand" "r")))))]
8669 "TARGET_TLS && TARGET_ARCH64"
8670 "lduh\t[%1 + %2], %0, %%tldo_add(%3)"
8671 [(set_attr "type" "load")
8672 (set_attr "us3load_type" "3cycle")])
8674 (define_insn "*tldo_ldsh1_sp64"
8675 [(set (match_operand:SI 0 "register_operand" "=r")
8676 (sign_extend:SI (mem:HI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8677 (match_operand 3 "tld_symbolic_operand" "")]
8679 (match_operand:DI 1 "register_operand" "r")))))]
8680 "TARGET_TLS && TARGET_ARCH64"
8681 "ldsh\t[%1 + %2], %0, %%tldo_add(%3)"
8682 [(set_attr "type" "sload")
8683 (set_attr "us3load_type" "3cycle")])
8685 (define_insn "*tldo_ldsh2_sp64"
8686 [(set (match_operand:DI 0 "register_operand" "=r")
8687 (sign_extend:DI (mem:HI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8688 (match_operand 3 "tld_symbolic_operand" "")]
8690 (match_operand:DI 1 "register_operand" "r")))))]
8691 "TARGET_TLS && TARGET_ARCH64"
8692 "ldsh\t[%1 + %2], %0, %%tldo_add(%3)"
8693 [(set_attr "type" "sload")
8694 (set_attr "us3load_type" "3cycle")])
8696 (define_insn "*tldo_lduw_sp32"
8697 [(set (match_operand:SI 0 "register_operand" "=r")
8698 (mem:SI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8699 (match_operand 3 "tld_symbolic_operand" "")]
8701 (match_operand:SI 1 "register_operand" "r"))))]
8702 "TARGET_TLS && TARGET_ARCH32"
8703 "ld\t[%1 + %2], %0, %%tldo_add(%3)"
8704 [(set_attr "type" "load")])
8706 (define_insn "*tldo_lduw_sp64"
8707 [(set (match_operand:SI 0 "register_operand" "=r")
8708 (mem:SI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8709 (match_operand 3 "tld_symbolic_operand" "")]
8711 (match_operand:DI 1 "register_operand" "r"))))]
8712 "TARGET_TLS && TARGET_ARCH64"
8713 "lduw\t[%1 + %2], %0, %%tldo_add(%3)"
8714 [(set_attr "type" "load")])
8716 (define_insn "*tldo_lduw1_sp64"
8717 [(set (match_operand:DI 0 "register_operand" "=r")
8718 (zero_extend:DI (mem:SI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8719 (match_operand 3 "tld_symbolic_operand" "")]
8721 (match_operand:DI 1 "register_operand" "r")))))]
8722 "TARGET_TLS && TARGET_ARCH64"
8723 "lduw\t[%1 + %2], %0, %%tldo_add(%3)"
8724 [(set_attr "type" "load")])
8726 (define_insn "*tldo_ldsw1_sp64"
8727 [(set (match_operand:DI 0 "register_operand" "=r")
8728 (sign_extend:DI (mem:SI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8729 (match_operand 3 "tld_symbolic_operand" "")]
8731 (match_operand:DI 1 "register_operand" "r")))))]
8732 "TARGET_TLS && TARGET_ARCH64"
8733 "ldsw\t[%1 + %2], %0, %%tldo_add(%3)"
8734 [(set_attr "type" "sload")
8735 (set_attr "us3load_type" "3cycle")])
8737 (define_insn "*tldo_ldx_sp64"
8738 [(set (match_operand:DI 0 "register_operand" "=r")
8739 (mem:DI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8740 (match_operand 3 "tld_symbolic_operand" "")]
8742 (match_operand:DI 1 "register_operand" "r"))))]
8743 "TARGET_TLS && TARGET_ARCH64"
8744 "ldx\t[%1 + %2], %0, %%tldo_add(%3)"
8745 [(set_attr "type" "load")])
8747 (define_insn "*tldo_stb_sp32"
8748 [(set (mem:QI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8749 (match_operand 3 "tld_symbolic_operand" "")]
8751 (match_operand:SI 1 "register_operand" "r")))
8752 (match_operand:QI 0 "register_operand" "=r"))]
8753 "TARGET_TLS && TARGET_ARCH32"
8754 "stb\t%0, [%1 + %2], %%tldo_add(%3)"
8755 [(set_attr "type" "store")])
8757 (define_insn "*tldo_stb_sp64"
8758 [(set (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8759 (match_operand 3 "tld_symbolic_operand" "")]
8761 (match_operand:DI 1 "register_operand" "r")))
8762 (match_operand:QI 0 "register_operand" "=r"))]
8763 "TARGET_TLS && TARGET_ARCH64"
8764 "stb\t%0, [%1 + %2], %%tldo_add(%3)"
8765 [(set_attr "type" "store")])
8767 (define_insn "*tldo_sth_sp32"
8768 [(set (mem:HI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8769 (match_operand 3 "tld_symbolic_operand" "")]
8771 (match_operand:SI 1 "register_operand" "r")))
8772 (match_operand:HI 0 "register_operand" "=r"))]
8773 "TARGET_TLS && TARGET_ARCH32"
8774 "sth\t%0, [%1 + %2], %%tldo_add(%3)"
8775 [(set_attr "type" "store")])
8777 (define_insn "*tldo_sth_sp64"
8778 [(set (mem:HI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8779 (match_operand 3 "tld_symbolic_operand" "")]
8781 (match_operand:DI 1 "register_operand" "r")))
8782 (match_operand:HI 0 "register_operand" "=r"))]
8783 "TARGET_TLS && TARGET_ARCH64"
8784 "sth\t%0, [%1 + %2], %%tldo_add(%3)"
8785 [(set_attr "type" "store")])
8787 (define_insn "*tldo_stw_sp32"
8788 [(set (mem:SI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
8789 (match_operand 3 "tld_symbolic_operand" "")]
8791 (match_operand:SI 1 "register_operand" "r")))
8792 (match_operand:SI 0 "register_operand" "=r"))]
8793 "TARGET_TLS && TARGET_ARCH32"
8794 "st\t%0, [%1 + %2], %%tldo_add(%3)"
8795 [(set_attr "type" "store")])
8797 (define_insn "*tldo_stw_sp64"
8798 [(set (mem:SI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8799 (match_operand 3 "tld_symbolic_operand" "")]
8801 (match_operand:DI 1 "register_operand" "r")))
8802 (match_operand:SI 0 "register_operand" "=r"))]
8803 "TARGET_TLS && TARGET_ARCH64"
8804 "stw\t%0, [%1 + %2], %%tldo_add(%3)"
8805 [(set_attr "type" "store")])
8807 (define_insn "*tldo_stx_sp64"
8808 [(set (mem:DI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
8809 (match_operand 3 "tld_symbolic_operand" "")]
8811 (match_operand:DI 1 "register_operand" "r")))
8812 (match_operand:DI 0 "register_operand" "=r"))]
8813 "TARGET_TLS && TARGET_ARCH64"
8814 "stx\t%0, [%1 + %2], %%tldo_add(%3)"
8815 [(set_attr "type" "store")])