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, 2005,2006, 2007 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 3, 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 COPYING3. If not see
22 ;; <http://www.gnu.org/licenses/>.
24 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
28 (UNSPEC_UPDATE_RETURN 1)
29 (UNSPEC_LOAD_PCREL_SYM 2)
30 (UNSPEC_MOVE_PIC_LABEL 5)
36 (UNSPEC_EMB_TEXTUHI 13)
37 (UNSPEC_EMB_TEXTHI 14)
38 (UNSPEC_EMB_TEXTULO 15)
46 (UNSPEC_TLSLD_BASE 35)
77 ;; The upper 32 fp regs on the v9 can't hold SFmode values. To deal with this
78 ;; a second register class, EXTRA_FP_REGS, exists for the v9 chip. The name
79 ;; is a bit of a misnomer as it covers all 64 fp regs. The corresponding
80 ;; constraint letter is 'e'. To avoid any confusion, 'e' is used instead of
81 ;; 'f' for all DF/TFmode values, including those that are specific to the v8.
84 ;; Attribute for cpu type.
85 ;; These must match the values for enum processor_type in sparc.h.
92 hypersparc,sparclite86x,
99 (const (symbol_ref "sparc_cpu_attr")))
101 ;; Attribute for the instruction set.
102 ;; At present we only need to distinguish v9/!v9, but for clarity we
103 ;; test TARGET_V8 too.
104 (define_attr "isa" "v7,v8,v9,sparclet"
106 (cond [(symbol_ref "TARGET_V9") (const_string "v9")
107 (symbol_ref "TARGET_V8") (const_string "v8")
108 (symbol_ref "TARGET_SPARCLET") (const_string "sparclet")]
109 (const_string "v7"))))
115 uncond_branch,branch,call,sibcall,call_no_delay_slot,return,
123 fga,fgm_pack,fgm_mul,fgm_pdist,fgm_cmp,
126 multi,savew,flushw,iflush,trap"
127 (const_string "ialu"))
129 ;; True if branch/call has empty delay slot and will emit a nop in it
130 (define_attr "empty_delay_slot" "false,true"
131 (symbol_ref "empty_delay_slot (insn)"))
133 (define_attr "branch_type" "none,icc,fcc,reg"
134 (const_string "none"))
136 (define_attr "pic" "false,true"
137 (symbol_ref "flag_pic != 0"))
139 (define_attr "calls_alloca" "false,true"
140 (symbol_ref "cfun->calls_alloca != 0"))
142 (define_attr "calls_eh_return" "false,true"
143 (symbol_ref "crtl->calls_eh_return !=0 "))
145 (define_attr "leaf_function" "false,true"
146 (symbol_ref "current_function_uses_only_leaf_regs != 0"))
148 (define_attr "delayed_branch" "false,true"
149 (symbol_ref "flag_delayed_branch != 0"))
151 ;; Length (in # of insns).
152 ;; Beware that setting a length greater or equal to 3 for conditional branches
153 ;; has a side-effect (see output_cbranch and output_v9branch).
154 (define_attr "length" ""
155 (cond [(eq_attr "type" "uncond_branch,call")
156 (if_then_else (eq_attr "empty_delay_slot" "true")
159 (eq_attr "type" "sibcall")
160 (if_then_else (eq_attr "leaf_function" "true")
161 (if_then_else (eq_attr "empty_delay_slot" "true")
164 (if_then_else (eq_attr "empty_delay_slot" "true")
167 (eq_attr "branch_type" "icc")
168 (if_then_else (match_operand 0 "noov_compare64_operator" "")
169 (if_then_else (lt (pc) (match_dup 1))
170 (if_then_else (lt (minus (match_dup 1) (pc)) (const_int 260000))
171 (if_then_else (eq_attr "empty_delay_slot" "true")
174 (if_then_else (eq_attr "empty_delay_slot" "true")
177 (if_then_else (lt (minus (pc) (match_dup 1)) (const_int 260000))
178 (if_then_else (eq_attr "empty_delay_slot" "true")
181 (if_then_else (eq_attr "empty_delay_slot" "true")
184 (if_then_else (eq_attr "empty_delay_slot" "true")
187 (eq_attr "branch_type" "fcc")
188 (if_then_else (match_operand 0 "fcc0_register_operand" "")
189 (if_then_else (eq_attr "empty_delay_slot" "true")
190 (if_then_else (eq (symbol_ref "TARGET_V9") (const_int 0))
193 (if_then_else (eq (symbol_ref "TARGET_V9") (const_int 0))
196 (if_then_else (lt (pc) (match_dup 2))
197 (if_then_else (lt (minus (match_dup 2) (pc)) (const_int 260000))
198 (if_then_else (eq_attr "empty_delay_slot" "true")
201 (if_then_else (eq_attr "empty_delay_slot" "true")
204 (if_then_else (lt (minus (pc) (match_dup 2)) (const_int 260000))
205 (if_then_else (eq_attr "empty_delay_slot" "true")
208 (if_then_else (eq_attr "empty_delay_slot" "true")
211 (eq_attr "branch_type" "reg")
212 (if_then_else (lt (pc) (match_dup 2))
213 (if_then_else (lt (minus (match_dup 2) (pc)) (const_int 32000))
214 (if_then_else (eq_attr "empty_delay_slot" "true")
217 (if_then_else (eq_attr "empty_delay_slot" "true")
220 (if_then_else (lt (minus (pc) (match_dup 2)) (const_int 32000))
221 (if_then_else (eq_attr "empty_delay_slot" "true")
224 (if_then_else (eq_attr "empty_delay_slot" "true")
230 (define_attr "fptype" "single,double"
231 (const_string "single"))
233 ;; UltraSPARC-III integer load type.
234 (define_attr "us3load_type" "2cycle,3cycle"
235 (const_string "2cycle"))
237 (define_asm_attributes
238 [(set_attr "length" "2")
239 (set_attr "type" "multi")])
241 ;; Attributes for instruction and branch scheduling
242 (define_attr "tls_call_delay" "false,true"
243 (symbol_ref "tls_call_delay (insn)"))
245 (define_attr "in_call_delay" "false,true"
246 (cond [(eq_attr "type" "uncond_branch,branch,call,sibcall,call_no_delay_slot,multi")
247 (const_string "false")
248 (eq_attr "type" "load,fpload,store,fpstore")
249 (if_then_else (eq_attr "length" "1")
250 (const_string "true")
251 (const_string "false"))]
252 (if_then_else (and (eq_attr "length" "1")
253 (eq_attr "tls_call_delay" "true"))
254 (const_string "true")
255 (const_string "false"))))
257 (define_attr "eligible_for_sibcall_delay" "false,true"
258 (symbol_ref "eligible_for_sibcall_delay (insn)"))
260 (define_attr "eligible_for_return_delay" "false,true"
261 (symbol_ref "eligible_for_return_delay (insn)"))
263 ;; ??? !v9: Should implement the notion of predelay slots for floating-point
264 ;; branches. This would allow us to remove the nop always inserted before
265 ;; a floating point branch.
267 ;; ??? It is OK for fill_simple_delay_slots to put load/store instructions
268 ;; in a delay slot, but it is not OK for fill_eager_delay_slots to do so.
269 ;; This is because doing so will add several pipeline stalls to the path
270 ;; that the load/store did not come from. Unfortunately, there is no way
271 ;; to prevent fill_eager_delay_slots from using load/store without completely
272 ;; disabling them. For the SPEC benchmark set, this is a serious lose,
273 ;; because it prevents us from moving back the final store of inner loops.
275 (define_attr "in_branch_delay" "false,true"
276 (if_then_else (and (eq_attr "type" "!uncond_branch,branch,call,sibcall,call_no_delay_slot,multi")
277 (eq_attr "length" "1"))
278 (const_string "true")
279 (const_string "false")))
281 (define_attr "in_uncond_branch_delay" "false,true"
282 (if_then_else (and (eq_attr "type" "!uncond_branch,branch,call,sibcall,call_no_delay_slot,multi")
283 (eq_attr "length" "1"))
284 (const_string "true")
285 (const_string "false")))
287 (define_attr "in_annul_branch_delay" "false,true"
288 (if_then_else (and (eq_attr "type" "!uncond_branch,branch,call,sibcall,call_no_delay_slot,multi")
289 (eq_attr "length" "1"))
290 (const_string "true")
291 (const_string "false")))
293 (define_delay (eq_attr "type" "call")
294 [(eq_attr "in_call_delay" "true") (nil) (nil)])
296 (define_delay (eq_attr "type" "sibcall")
297 [(eq_attr "eligible_for_sibcall_delay" "true") (nil) (nil)])
299 (define_delay (eq_attr "type" "branch")
300 [(eq_attr "in_branch_delay" "true")
301 (nil) (eq_attr "in_annul_branch_delay" "true")])
303 (define_delay (eq_attr "type" "uncond_branch")
304 [(eq_attr "in_uncond_branch_delay" "true")
307 (define_delay (eq_attr "type" "return")
308 [(eq_attr "eligible_for_return_delay" "true") (nil) (nil)])
311 ;; Include SPARC DFA schedulers
313 (include "cypress.md")
314 (include "supersparc.md")
315 (include "hypersparc.md")
316 (include "sparclet.md")
317 (include "ultra1_2.md")
318 (include "ultra3.md")
319 (include "niagara.md")
320 (include "niagara2.md")
323 ;; Operand and operator predicates.
325 (include "predicates.md")
328 ;; Compare instructions.
330 ;; We generate RTL for comparisons and branches by having the cmpxx
331 ;; patterns store away the operands. Then, the scc and bcc patterns
332 ;; emit RTL for both the compare and the branch.
334 ;; We do this because we want to generate different code for an sne and
335 ;; seq insn. In those cases, if the second operand of the compare is not
336 ;; const0_rtx, we want to compute the xor of the two operands and test
339 ;; We start with the DEFINE_EXPANDs, then the DEFINE_INSNs to match
340 ;; the patterns. Finally, we have the DEFINE_SPLITs for some of the scc
341 ;; insns that actually require more than one machine instruction.
343 (define_expand "cmpsi"
345 (compare:CC (match_operand:SI 0 "compare_operand" "")
346 (match_operand:SI 1 "arith_operand" "")))]
349 if (GET_CODE (operands[0]) == ZERO_EXTRACT && operands[1] != const0_rtx)
350 operands[0] = force_reg (SImode, operands[0]);
352 sparc_compare_op0 = operands[0];
353 sparc_compare_op1 = operands[1];
357 (define_expand "cmpdi"
359 (compare:CCX (match_operand:DI 0 "compare_operand" "")
360 (match_operand:DI 1 "arith_operand" "")))]
363 if (GET_CODE (operands[0]) == ZERO_EXTRACT && operands[1] != const0_rtx)
364 operands[0] = force_reg (DImode, operands[0]);
366 sparc_compare_op0 = operands[0];
367 sparc_compare_op1 = operands[1];
371 (define_expand "cmpsf"
372 ;; The 96 here isn't ever used by anyone.
374 (compare:CCFP (match_operand:SF 0 "register_operand" "")
375 (match_operand:SF 1 "register_operand" "")))]
378 sparc_compare_op0 = operands[0];
379 sparc_compare_op1 = operands[1];
383 (define_expand "cmpdf"
384 ;; The 96 here isn't ever used by anyone.
386 (compare:CCFP (match_operand:DF 0 "register_operand" "")
387 (match_operand:DF 1 "register_operand" "")))]
390 sparc_compare_op0 = operands[0];
391 sparc_compare_op1 = operands[1];
395 (define_expand "cmptf"
396 ;; The 96 here isn't ever used by anyone.
398 (compare:CCFP (match_operand:TF 0 "register_operand" "")
399 (match_operand:TF 1 "register_operand" "")))]
402 sparc_compare_op0 = operands[0];
403 sparc_compare_op1 = operands[1];
407 ;; Now the compare DEFINE_INSNs.
409 (define_insn "*cmpsi_insn"
411 (compare:CC (match_operand:SI 0 "register_operand" "r")
412 (match_operand:SI 1 "arith_operand" "rI")))]
415 [(set_attr "type" "compare")])
417 (define_insn "*cmpdi_sp64"
419 (compare:CCX (match_operand:DI 0 "register_operand" "r")
420 (match_operand:DI 1 "arith_operand" "rI")))]
423 [(set_attr "type" "compare")])
425 (define_insn "*cmpsf_fpe"
426 [(set (match_operand:CCFPE 0 "fcc_register_operand" "=c")
427 (compare:CCFPE (match_operand:SF 1 "register_operand" "f")
428 (match_operand:SF 2 "register_operand" "f")))]
432 return "fcmpes\t%0, %1, %2";
433 return "fcmpes\t%1, %2";
435 [(set_attr "type" "fpcmp")])
437 (define_insn "*cmpdf_fpe"
438 [(set (match_operand:CCFPE 0 "fcc_register_operand" "=c")
439 (compare:CCFPE (match_operand:DF 1 "register_operand" "e")
440 (match_operand:DF 2 "register_operand" "e")))]
444 return "fcmped\t%0, %1, %2";
445 return "fcmped\t%1, %2";
447 [(set_attr "type" "fpcmp")
448 (set_attr "fptype" "double")])
450 (define_insn "*cmptf_fpe"
451 [(set (match_operand:CCFPE 0 "fcc_register_operand" "=c")
452 (compare:CCFPE (match_operand:TF 1 "register_operand" "e")
453 (match_operand:TF 2 "register_operand" "e")))]
454 "TARGET_FPU && TARGET_HARD_QUAD"
457 return "fcmpeq\t%0, %1, %2";
458 return "fcmpeq\t%1, %2";
460 [(set_attr "type" "fpcmp")])
462 (define_insn "*cmpsf_fp"
463 [(set (match_operand:CCFP 0 "fcc_register_operand" "=c")
464 (compare:CCFP (match_operand:SF 1 "register_operand" "f")
465 (match_operand:SF 2 "register_operand" "f")))]
469 return "fcmps\t%0, %1, %2";
470 return "fcmps\t%1, %2";
472 [(set_attr "type" "fpcmp")])
474 (define_insn "*cmpdf_fp"
475 [(set (match_operand:CCFP 0 "fcc_register_operand" "=c")
476 (compare:CCFP (match_operand:DF 1 "register_operand" "e")
477 (match_operand:DF 2 "register_operand" "e")))]
481 return "fcmpd\t%0, %1, %2";
482 return "fcmpd\t%1, %2";
484 [(set_attr "type" "fpcmp")
485 (set_attr "fptype" "double")])
487 (define_insn "*cmptf_fp"
488 [(set (match_operand:CCFP 0 "fcc_register_operand" "=c")
489 (compare:CCFP (match_operand:TF 1 "register_operand" "e")
490 (match_operand:TF 2 "register_operand" "e")))]
491 "TARGET_FPU && TARGET_HARD_QUAD"
494 return "fcmpq\t%0, %1, %2";
495 return "fcmpq\t%1, %2";
497 [(set_attr "type" "fpcmp")])
499 ;; Next come the scc insns. For seq, sne, sgeu, and sltu, we can do this
500 ;; without jumps using the addx/subx instructions. For seq/sne on v9 we use
501 ;; the same code as v8 (the addx/subx method has more applications). The
502 ;; exception to this is "reg != 0" which can be done in one instruction on v9
503 ;; (so we do it). For the rest, on v9 we use conditional moves; on v8, we do
506 ;; Seq_special[_xxx] and sne_special[_xxx] clobber the CC reg, because they
507 ;; generate addcc/subcc instructions.
509 (define_expand "seqsi_special"
511 (xor:SI (match_operand:SI 1 "register_operand" "")
512 (match_operand:SI 2 "register_operand" "")))
513 (parallel [(set (match_operand:SI 0 "register_operand" "")
514 (eq:SI (match_dup 3) (const_int 0)))
515 (clobber (reg:CC 100))])]
517 { operands[3] = gen_reg_rtx (SImode); })
519 (define_expand "seqdi_special"
521 (xor:DI (match_operand:DI 1 "register_operand" "")
522 (match_operand:DI 2 "register_operand" "")))
523 (set (match_operand:DI 0 "register_operand" "")
524 (eq:DI (match_dup 3) (const_int 0)))]
526 { operands[3] = gen_reg_rtx (DImode); })
528 (define_expand "snesi_special"
530 (xor:SI (match_operand:SI 1 "register_operand" "")
531 (match_operand:SI 2 "register_operand" "")))
532 (parallel [(set (match_operand:SI 0 "register_operand" "")
533 (ne:SI (match_dup 3) (const_int 0)))
534 (clobber (reg:CC 100))])]
536 { operands[3] = gen_reg_rtx (SImode); })
538 (define_expand "snedi_special"
540 (xor:DI (match_operand:DI 1 "register_operand" "")
541 (match_operand:DI 2 "register_operand" "")))
542 (set (match_operand:DI 0 "register_operand" "")
543 (ne:DI (match_dup 3) (const_int 0)))]
545 { operands[3] = gen_reg_rtx (DImode); })
547 (define_expand "seqdi_special_trunc"
549 (xor:DI (match_operand:DI 1 "register_operand" "")
550 (match_operand:DI 2 "register_operand" "")))
551 (set (match_operand:SI 0 "register_operand" "")
552 (eq:SI (match_dup 3) (const_int 0)))]
554 { operands[3] = gen_reg_rtx (DImode); })
556 (define_expand "snedi_special_trunc"
558 (xor:DI (match_operand:DI 1 "register_operand" "")
559 (match_operand:DI 2 "register_operand" "")))
560 (set (match_operand:SI 0 "register_operand" "")
561 (ne:SI (match_dup 3) (const_int 0)))]
563 { operands[3] = gen_reg_rtx (DImode); })
565 (define_expand "seqsi_special_extend"
567 (xor:SI (match_operand:SI 1 "register_operand" "")
568 (match_operand:SI 2 "register_operand" "")))
569 (parallel [(set (match_operand:DI 0 "register_operand" "")
570 (eq:DI (match_dup 3) (const_int 0)))
571 (clobber (reg:CC 100))])]
573 { operands[3] = gen_reg_rtx (SImode); })
575 (define_expand "snesi_special_extend"
577 (xor:SI (match_operand:SI 1 "register_operand" "")
578 (match_operand:SI 2 "register_operand" "")))
579 (parallel [(set (match_operand:DI 0 "register_operand" "")
580 (ne:DI (match_dup 3) (const_int 0)))
581 (clobber (reg:CC 100))])]
583 { operands[3] = gen_reg_rtx (SImode); })
585 ;; ??? v9: Operand 0 needs a mode, so SImode was chosen.
586 ;; However, the code handles both SImode and DImode.
588 [(set (match_operand:SI 0 "int_register_operand" "")
589 (eq:SI (match_dup 1) (const_int 0)))]
592 if (GET_MODE (sparc_compare_op0) == SImode)
596 if (GET_MODE (operands[0]) == SImode)
597 pat = gen_seqsi_special (operands[0], sparc_compare_op0,
599 else if (! TARGET_ARCH64)
602 pat = gen_seqsi_special_extend (operands[0], sparc_compare_op0,
607 else if (GET_MODE (sparc_compare_op0) == DImode)
613 else if (GET_MODE (operands[0]) == SImode)
614 pat = gen_seqdi_special_trunc (operands[0], sparc_compare_op0,
617 pat = gen_seqdi_special (operands[0], sparc_compare_op0,
622 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
625 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, EQ);
626 gcc_assert (code == NE);
627 emit_insn (gen_sne (operands[0]));
632 if (gen_v9_scc (EQ, operands))
639 ;; ??? v9: Operand 0 needs a mode, so SImode was chosen.
640 ;; However, the code handles both SImode and DImode.
642 [(set (match_operand:SI 0 "int_register_operand" "")
643 (ne:SI (match_dup 1) (const_int 0)))]
646 if (GET_MODE (sparc_compare_op0) == SImode)
650 if (GET_MODE (operands[0]) == SImode)
651 pat = gen_snesi_special (operands[0], sparc_compare_op0,
653 else if (! TARGET_ARCH64)
656 pat = gen_snesi_special_extend (operands[0], sparc_compare_op0,
661 else if (GET_MODE (sparc_compare_op0) == DImode)
667 else if (GET_MODE (operands[0]) == SImode)
668 pat = gen_snedi_special_trunc (operands[0], sparc_compare_op0,
671 pat = gen_snedi_special (operands[0], sparc_compare_op0,
676 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
679 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, NE);
680 gcc_assert (code == NE);
681 emit_insn (gen_sne (operands[0]));
686 if (gen_v9_scc (NE, operands))
694 [(set (match_operand:SI 0 "int_register_operand" "")
695 (gt:SI (match_dup 1) (const_int 0)))]
698 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
701 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, GT);
702 gcc_assert (code == NE);
703 emit_insn (gen_sne (operands[0]));
708 if (gen_v9_scc (GT, operands))
716 [(set (match_operand:SI 0 "int_register_operand" "")
717 (lt:SI (match_dup 1) (const_int 0)))]
720 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
723 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, LT);
724 gcc_assert (code == NE);
725 emit_insn (gen_sne (operands[0]));
730 if (gen_v9_scc (LT, operands))
738 [(set (match_operand:SI 0 "int_register_operand" "")
739 (ge:SI (match_dup 1) (const_int 0)))]
742 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
745 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, GE);
746 gcc_assert (code == NE);
747 emit_insn (gen_sne (operands[0]));
752 if (gen_v9_scc (GE, operands))
760 [(set (match_operand:SI 0 "int_register_operand" "")
761 (le:SI (match_dup 1) (const_int 0)))]
764 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
767 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, LE);
768 gcc_assert (code == NE);
769 emit_insn (gen_sne (operands[0]));
774 if (gen_v9_scc (LE, operands))
781 (define_expand "sgtu"
782 [(set (match_operand:SI 0 "int_register_operand" "")
783 (gtu:SI (match_dup 1) (const_int 0)))]
790 /* We can do ltu easily, so if both operands are registers, swap them and
792 if ((GET_CODE (sparc_compare_op0) == REG
793 || GET_CODE (sparc_compare_op0) == SUBREG)
794 && (GET_CODE (sparc_compare_op1) == REG
795 || GET_CODE (sparc_compare_op1) == SUBREG))
797 tem = sparc_compare_op0;
798 sparc_compare_op0 = sparc_compare_op1;
799 sparc_compare_op1 = tem;
800 pat = gen_sltu (operands[0]);
809 if (gen_v9_scc (GTU, operands))
815 (define_expand "sltu"
816 [(set (match_operand:SI 0 "int_register_operand" "")
817 (ltu:SI (match_dup 1) (const_int 0)))]
822 if (gen_v9_scc (LTU, operands))
825 operands[1] = gen_compare_reg (LTU);
828 (define_expand "sgeu"
829 [(set (match_operand:SI 0 "int_register_operand" "")
830 (geu:SI (match_dup 1) (const_int 0)))]
835 if (gen_v9_scc (GEU, operands))
838 operands[1] = gen_compare_reg (GEU);
841 (define_expand "sleu"
842 [(set (match_operand:SI 0 "int_register_operand" "")
843 (leu:SI (match_dup 1) (const_int 0)))]
850 /* We can do geu easily, so if both operands are registers, swap them and
852 if ((GET_CODE (sparc_compare_op0) == REG
853 || GET_CODE (sparc_compare_op0) == SUBREG)
854 && (GET_CODE (sparc_compare_op1) == REG
855 || GET_CODE (sparc_compare_op1) == SUBREG))
857 tem = sparc_compare_op0;
858 sparc_compare_op0 = sparc_compare_op1;
859 sparc_compare_op1 = tem;
860 pat = gen_sgeu (operands[0]);
869 if (gen_v9_scc (LEU, operands))
875 ;; Now the DEFINE_INSNs for the scc cases.
877 ;; The SEQ and SNE patterns are special because they can be done
878 ;; without any branching and do not involve a COMPARE. We want
879 ;; them to always use the splits below so the results can be
882 (define_insn_and_split "*snesi_zero"
883 [(set (match_operand:SI 0 "register_operand" "=r")
884 (ne:SI (match_operand:SI 1 "register_operand" "r")
886 (clobber (reg:CC 100))]
890 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
892 (set (match_dup 0) (ltu:SI (reg:CC 100) (const_int 0)))]
894 [(set_attr "length" "2")])
896 (define_insn_and_split "*neg_snesi_zero"
897 [(set (match_operand:SI 0 "register_operand" "=r")
898 (neg:SI (ne:SI (match_operand:SI 1 "register_operand" "r")
900 (clobber (reg:CC 100))]
904 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
906 (set (match_dup 0) (neg:SI (ltu:SI (reg:CC 100) (const_int 0))))]
908 [(set_attr "length" "2")])
910 (define_insn_and_split "*snesi_zero_extend"
911 [(set (match_operand:DI 0 "register_operand" "=r")
912 (ne:DI (match_operand:SI 1 "register_operand" "r")
914 (clobber (reg:CC 100))]
918 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (minus:SI (const_int 0)
921 (set (match_dup 0) (zero_extend:DI (plus:SI (plus:SI (const_int 0)
923 (ltu:SI (reg:CC_NOOV 100)
926 [(set_attr "length" "2")])
928 (define_insn_and_split "*snedi_zero"
929 [(set (match_operand:DI 0 "register_operand" "=&r")
930 (ne:DI (match_operand:DI 1 "register_operand" "r")
934 "&& ! reg_overlap_mentioned_p (operands[1], operands[0])"
935 [(set (match_dup 0) (const_int 0))
936 (set (match_dup 0) (if_then_else:DI (ne:DI (match_dup 1)
941 [(set_attr "length" "2")])
943 (define_insn_and_split "*neg_snedi_zero"
944 [(set (match_operand:DI 0 "register_operand" "=&r")
945 (neg:DI (ne:DI (match_operand:DI 1 "register_operand" "r")
949 "&& ! reg_overlap_mentioned_p (operands[1], operands[0])"
950 [(set (match_dup 0) (const_int 0))
951 (set (match_dup 0) (if_then_else:DI (ne:DI (match_dup 1)
956 [(set_attr "length" "2")])
958 (define_insn_and_split "*snedi_zero_trunc"
959 [(set (match_operand:SI 0 "register_operand" "=&r")
960 (ne:SI (match_operand:DI 1 "register_operand" "r")
964 "&& ! reg_overlap_mentioned_p (operands[1], operands[0])"
965 [(set (match_dup 0) (const_int 0))
966 (set (match_dup 0) (if_then_else:SI (ne:DI (match_dup 1)
971 [(set_attr "length" "2")])
973 (define_insn_and_split "*seqsi_zero"
974 [(set (match_operand:SI 0 "register_operand" "=r")
975 (eq:SI (match_operand:SI 1 "register_operand" "r")
977 (clobber (reg:CC 100))]
981 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
983 (set (match_dup 0) (geu:SI (reg:CC 100) (const_int 0)))]
985 [(set_attr "length" "2")])
987 (define_insn_and_split "*neg_seqsi_zero"
988 [(set (match_operand:SI 0 "register_operand" "=r")
989 (neg:SI (eq:SI (match_operand:SI 1 "register_operand" "r")
991 (clobber (reg:CC 100))]
995 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
997 (set (match_dup 0) (neg:SI (geu:SI (reg:CC 100) (const_int 0))))]
999 [(set_attr "length" "2")])
1001 (define_insn_and_split "*seqsi_zero_extend"
1002 [(set (match_operand:DI 0 "register_operand" "=r")
1003 (eq:DI (match_operand:SI 1 "register_operand" "r")
1005 (clobber (reg:CC 100))]
1009 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (minus:SI (const_int 0)
1012 (set (match_dup 0) (zero_extend:DI (minus:SI (minus:SI (const_int 0)
1014 (ltu:SI (reg:CC_NOOV 100)
1017 [(set_attr "length" "2")])
1019 (define_insn_and_split "*seqdi_zero"
1020 [(set (match_operand:DI 0 "register_operand" "=&r")
1021 (eq:DI (match_operand:DI 1 "register_operand" "r")
1025 "&& ! reg_overlap_mentioned_p (operands[1], operands[0])"
1026 [(set (match_dup 0) (const_int 0))
1027 (set (match_dup 0) (if_then_else:DI (eq:DI (match_dup 1)
1032 [(set_attr "length" "2")])
1034 (define_insn_and_split "*neg_seqdi_zero"
1035 [(set (match_operand:DI 0 "register_operand" "=&r")
1036 (neg:DI (eq:DI (match_operand:DI 1 "register_operand" "r")
1040 "&& ! reg_overlap_mentioned_p (operands[1], operands[0])"
1041 [(set (match_dup 0) (const_int 0))
1042 (set (match_dup 0) (if_then_else:DI (eq:DI (match_dup 1)
1047 [(set_attr "length" "2")])
1049 (define_insn_and_split "*seqdi_zero_trunc"
1050 [(set (match_operand:SI 0 "register_operand" "=&r")
1051 (eq:SI (match_operand:DI 1 "register_operand" "r")
1055 "&& ! reg_overlap_mentioned_p (operands[1], operands[0])"
1056 [(set (match_dup 0) (const_int 0))
1057 (set (match_dup 0) (if_then_else:SI (eq:DI (match_dup 1)
1062 [(set_attr "length" "2")])
1064 ;; We can also do (x + (i == 0)) and related, so put them in.
1065 ;; ??? The addx/subx insns use the 32 bit carry flag so there are no DImode
1068 (define_insn_and_split "*x_plus_i_ne_0"
1069 [(set (match_operand:SI 0 "register_operand" "=r")
1070 (plus:SI (ne:SI (match_operand:SI 1 "register_operand" "r")
1072 (match_operand:SI 2 "register_operand" "r")))
1073 (clobber (reg:CC 100))]
1077 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
1079 (set (match_dup 0) (plus:SI (ltu:SI (reg:CC 100) (const_int 0))
1082 [(set_attr "length" "2")])
1084 (define_insn_and_split "*x_minus_i_ne_0"
1085 [(set (match_operand:SI 0 "register_operand" "=r")
1086 (minus:SI (match_operand:SI 2 "register_operand" "r")
1087 (ne:SI (match_operand:SI 1 "register_operand" "r")
1089 (clobber (reg:CC 100))]
1093 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
1095 (set (match_dup 0) (minus:SI (match_dup 2)
1096 (ltu:SI (reg:CC 100) (const_int 0))))]
1098 [(set_attr "length" "2")])
1100 (define_insn_and_split "*x_plus_i_eq_0"
1101 [(set (match_operand:SI 0 "register_operand" "=r")
1102 (plus:SI (eq:SI (match_operand:SI 1 "register_operand" "r")
1104 (match_operand:SI 2 "register_operand" "r")))
1105 (clobber (reg:CC 100))]
1109 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
1111 (set (match_dup 0) (plus:SI (geu:SI (reg:CC 100) (const_int 0))
1114 [(set_attr "length" "2")])
1116 (define_insn_and_split "*x_minus_i_eq_0"
1117 [(set (match_operand:SI 0 "register_operand" "=r")
1118 (minus:SI (match_operand:SI 2 "register_operand" "r")
1119 (eq:SI (match_operand:SI 1 "register_operand" "r")
1121 (clobber (reg:CC 100))]
1125 [(set (reg:CC_NOOV 100) (compare:CC_NOOV (neg:SI (match_dup 1))
1127 (set (match_dup 0) (minus:SI (match_dup 2)
1128 (geu:SI (reg:CC 100) (const_int 0))))]
1130 [(set_attr "length" "2")])
1132 ;; We can also do GEU and LTU directly, but these operate after a compare.
1133 ;; ??? The addx/subx insns use the 32 bit carry flag so there are no DImode
1136 (define_insn "*sltu_insn"
1137 [(set (match_operand:SI 0 "register_operand" "=r")
1138 (ltu:SI (reg:CC 100) (const_int 0)))]
1141 [(set_attr "type" "ialuX")])
1143 (define_insn "*neg_sltu_insn"
1144 [(set (match_operand:SI 0 "register_operand" "=r")
1145 (neg:SI (ltu:SI (reg:CC 100) (const_int 0))))]
1148 [(set_attr "type" "ialuX")])
1150 ;; ??? Combine should canonicalize these next two to the same pattern.
1151 (define_insn "*neg_sltu_minus_x"
1152 [(set (match_operand:SI 0 "register_operand" "=r")
1153 (minus:SI (neg:SI (ltu:SI (reg:CC 100) (const_int 0)))
1154 (match_operand:SI 1 "arith_operand" "rI")))]
1156 "subx\t%%g0, %1, %0"
1157 [(set_attr "type" "ialuX")])
1159 (define_insn "*neg_sltu_plus_x"
1160 [(set (match_operand:SI 0 "register_operand" "=r")
1161 (neg:SI (plus:SI (ltu:SI (reg:CC 100) (const_int 0))
1162 (match_operand:SI 1 "arith_operand" "rI"))))]
1164 "subx\t%%g0, %1, %0"
1165 [(set_attr "type" "ialuX")])
1167 (define_insn "*sgeu_insn"
1168 [(set (match_operand:SI 0 "register_operand" "=r")
1169 (geu:SI (reg:CC 100) (const_int 0)))]
1171 "subx\t%%g0, -1, %0"
1172 [(set_attr "type" "ialuX")])
1174 (define_insn "*neg_sgeu_insn"
1175 [(set (match_operand:SI 0 "register_operand" "=r")
1176 (neg:SI (geu:SI (reg:CC 100) (const_int 0))))]
1178 "addx\t%%g0, -1, %0"
1179 [(set_attr "type" "ialuX")])
1181 ;; We can also do (x + ((unsigned) i >= 0)) and related, so put them in.
1182 ;; ??? The addx/subx insns use the 32 bit carry flag so there are no DImode
1185 (define_insn "*sltu_plus_x"
1186 [(set (match_operand:SI 0 "register_operand" "=r")
1187 (plus:SI (ltu:SI (reg:CC 100) (const_int 0))
1188 (match_operand:SI 1 "arith_operand" "rI")))]
1190 "addx\t%%g0, %1, %0"
1191 [(set_attr "type" "ialuX")])
1193 (define_insn "*sltu_plus_x_plus_y"
1194 [(set (match_operand:SI 0 "register_operand" "=r")
1195 (plus:SI (ltu:SI (reg:CC 100) (const_int 0))
1196 (plus:SI (match_operand:SI 1 "arith_operand" "%r")
1197 (match_operand:SI 2 "arith_operand" "rI"))))]
1200 [(set_attr "type" "ialuX")])
1202 (define_insn "*x_minus_sltu"
1203 [(set (match_operand:SI 0 "register_operand" "=r")
1204 (minus:SI (match_operand:SI 1 "register_operand" "r")
1205 (ltu:SI (reg:CC 100) (const_int 0))))]
1208 [(set_attr "type" "ialuX")])
1210 ;; ??? Combine should canonicalize these next two to the same pattern.
1211 (define_insn "*x_minus_y_minus_sltu"
1212 [(set (match_operand:SI 0 "register_operand" "=r")
1213 (minus:SI (minus:SI (match_operand:SI 1 "register_or_zero_operand" "rJ")
1214 (match_operand:SI 2 "arith_operand" "rI"))
1215 (ltu:SI (reg:CC 100) (const_int 0))))]
1218 [(set_attr "type" "ialuX")])
1220 (define_insn "*x_minus_sltu_plus_y"
1221 [(set (match_operand:SI 0 "register_operand" "=r")
1222 (minus:SI (match_operand:SI 1 "register_or_zero_operand" "rJ")
1223 (plus:SI (ltu:SI (reg:CC 100) (const_int 0))
1224 (match_operand:SI 2 "arith_operand" "rI"))))]
1227 [(set_attr "type" "ialuX")])
1229 (define_insn "*sgeu_plus_x"
1230 [(set (match_operand:SI 0 "register_operand" "=r")
1231 (plus:SI (geu:SI (reg:CC 100) (const_int 0))
1232 (match_operand:SI 1 "register_operand" "r")))]
1235 [(set_attr "type" "ialuX")])
1237 (define_insn "*x_minus_sgeu"
1238 [(set (match_operand:SI 0 "register_operand" "=r")
1239 (minus:SI (match_operand:SI 1 "register_operand" "r")
1240 (geu:SI (reg:CC 100) (const_int 0))))]
1243 [(set_attr "type" "ialuX")])
1246 [(set (match_operand:SI 0 "register_operand" "")
1247 (match_operator:SI 2 "noov_compare_operator"
1248 [(match_operand 1 "icc_or_fcc_register_operand" "")
1251 && REGNO (operands[1]) == SPARC_ICC_REG
1252 && (GET_MODE (operands[1]) == CCXmode
1253 /* 32-bit LTU/GEU are better implemented using addx/subx. */
1254 || (GET_CODE (operands[2]) != LTU && GET_CODE (operands[2]) != GEU))"
1255 [(set (match_dup 0) (const_int 0))
1257 (if_then_else:SI (match_op_dup:SI 2 [(match_dup 1) (const_int 0)])
1263 ;; These control RTL generation for conditional jump insns
1265 ;; The quad-word fp compare library routines all return nonzero to indicate
1266 ;; true, which is different from the equivalent libgcc routines, so we must
1267 ;; handle them specially here.
1269 (define_expand "beq"
1271 (if_then_else (eq (match_dup 1) (const_int 0))
1272 (label_ref (match_operand 0 "" ""))
1276 if (TARGET_ARCH64 && sparc_compare_op1 == const0_rtx
1277 && GET_CODE (sparc_compare_op0) == REG
1278 && GET_MODE (sparc_compare_op0) == DImode)
1280 emit_v9_brxx_insn (EQ, sparc_compare_op0, operands[0]);
1283 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1286 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, EQ);
1287 gcc_assert (code == NE);
1288 emit_jump_insn (gen_bne (operands[0]));
1291 operands[1] = gen_compare_reg (EQ);
1294 (define_expand "bne"
1296 (if_then_else (ne (match_dup 1) (const_int 0))
1297 (label_ref (match_operand 0 "" ""))
1301 if (TARGET_ARCH64 && sparc_compare_op1 == const0_rtx
1302 && GET_CODE (sparc_compare_op0) == REG
1303 && GET_MODE (sparc_compare_op0) == DImode)
1305 emit_v9_brxx_insn (NE, sparc_compare_op0, operands[0]);
1308 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1311 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, NE);
1312 gcc_assert (code == NE);
1313 emit_jump_insn (gen_bne (operands[0]));
1316 operands[1] = gen_compare_reg (NE);
1319 (define_expand "bgt"
1321 (if_then_else (gt (match_dup 1) (const_int 0))
1322 (label_ref (match_operand 0 "" ""))
1326 if (TARGET_ARCH64 && sparc_compare_op1 == const0_rtx
1327 && GET_CODE (sparc_compare_op0) == REG
1328 && GET_MODE (sparc_compare_op0) == DImode)
1330 emit_v9_brxx_insn (GT, sparc_compare_op0, operands[0]);
1333 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1336 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, GT);
1337 gcc_assert (code == NE);
1338 emit_jump_insn (gen_bne (operands[0]));
1341 operands[1] = gen_compare_reg (GT);
1344 (define_expand "bgtu"
1346 (if_then_else (gtu (match_dup 1) (const_int 0))
1347 (label_ref (match_operand 0 "" ""))
1351 operands[1] = gen_compare_reg (GTU);
1354 (define_expand "blt"
1356 (if_then_else (lt (match_dup 1) (const_int 0))
1357 (label_ref (match_operand 0 "" ""))
1361 if (TARGET_ARCH64 && sparc_compare_op1 == const0_rtx
1362 && GET_CODE (sparc_compare_op0) == REG
1363 && GET_MODE (sparc_compare_op0) == DImode)
1365 emit_v9_brxx_insn (LT, sparc_compare_op0, operands[0]);
1368 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1371 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, LT);
1372 gcc_assert (code == NE);
1373 emit_jump_insn (gen_bne (operands[0]));
1376 operands[1] = gen_compare_reg (LT);
1379 (define_expand "bltu"
1381 (if_then_else (ltu (match_dup 1) (const_int 0))
1382 (label_ref (match_operand 0 "" ""))
1386 operands[1] = gen_compare_reg (LTU);
1389 (define_expand "bge"
1391 (if_then_else (ge (match_dup 1) (const_int 0))
1392 (label_ref (match_operand 0 "" ""))
1396 if (TARGET_ARCH64 && sparc_compare_op1 == const0_rtx
1397 && GET_CODE (sparc_compare_op0) == REG
1398 && GET_MODE (sparc_compare_op0) == DImode)
1400 emit_v9_brxx_insn (GE, sparc_compare_op0, operands[0]);
1403 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1406 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, GE);
1407 gcc_assert (code == NE);
1408 emit_jump_insn (gen_bne (operands[0]));
1411 operands[1] = gen_compare_reg (GE);
1414 (define_expand "bgeu"
1416 (if_then_else (geu (match_dup 1) (const_int 0))
1417 (label_ref (match_operand 0 "" ""))
1421 operands[1] = gen_compare_reg (GEU);
1424 (define_expand "ble"
1426 (if_then_else (le (match_dup 1) (const_int 0))
1427 (label_ref (match_operand 0 "" ""))
1431 if (TARGET_ARCH64 && sparc_compare_op1 == const0_rtx
1432 && GET_CODE (sparc_compare_op0) == REG
1433 && GET_MODE (sparc_compare_op0) == DImode)
1435 emit_v9_brxx_insn (LE, sparc_compare_op0, operands[0]);
1438 else if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1441 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, LE);
1442 gcc_assert (code == NE);
1443 emit_jump_insn (gen_bne (operands[0]));
1446 operands[1] = gen_compare_reg (LE);
1449 (define_expand "bleu"
1451 (if_then_else (leu (match_dup 1) (const_int 0))
1452 (label_ref (match_operand 0 "" ""))
1456 operands[1] = gen_compare_reg (LEU);
1459 (define_expand "bunordered"
1461 (if_then_else (unordered (match_dup 1) (const_int 0))
1462 (label_ref (match_operand 0 "" ""))
1466 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1469 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, UNORDERED);
1470 gcc_assert (code == EQ);
1471 emit_jump_insn (gen_beq (operands[0]));
1474 operands[1] = gen_compare_reg (UNORDERED);
1477 (define_expand "bordered"
1479 (if_then_else (ordered (match_dup 1) (const_int 0))
1480 (label_ref (match_operand 0 "" ""))
1484 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1487 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, ORDERED);
1488 gcc_assert (code == NE);
1489 emit_jump_insn (gen_bne (operands[0]));
1492 operands[1] = gen_compare_reg (ORDERED);
1495 (define_expand "bungt"
1497 (if_then_else (ungt (match_dup 1) (const_int 0))
1498 (label_ref (match_operand 0 "" ""))
1502 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1505 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, UNGT);
1506 gcc_assert (code == GT);
1507 emit_jump_insn (gen_bgt (operands[0]));
1510 operands[1] = gen_compare_reg (UNGT);
1513 (define_expand "bunlt"
1515 (if_then_else (unlt (match_dup 1) (const_int 0))
1516 (label_ref (match_operand 0 "" ""))
1520 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1523 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, UNLT);
1524 gcc_assert (code == NE);
1525 emit_jump_insn (gen_bne (operands[0]));
1528 operands[1] = gen_compare_reg (UNLT);
1531 (define_expand "buneq"
1533 (if_then_else (uneq (match_dup 1) (const_int 0))
1534 (label_ref (match_operand 0 "" ""))
1538 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1541 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, UNEQ);
1542 gcc_assert (code == EQ);
1543 emit_jump_insn (gen_beq (operands[0]));
1546 operands[1] = gen_compare_reg (UNEQ);
1549 (define_expand "bunge"
1551 (if_then_else (unge (match_dup 1) (const_int 0))
1552 (label_ref (match_operand 0 "" ""))
1556 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1559 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, UNGE);
1560 gcc_assert (code == NE);
1561 emit_jump_insn (gen_bne (operands[0]));
1564 operands[1] = gen_compare_reg (UNGE);
1567 (define_expand "bunle"
1569 (if_then_else (unle (match_dup 1) (const_int 0))
1570 (label_ref (match_operand 0 "" ""))
1574 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1577 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, UNLE);
1578 gcc_assert (code == NE);
1579 emit_jump_insn (gen_bne (operands[0]));
1582 operands[1] = gen_compare_reg (UNLE);
1585 (define_expand "bltgt"
1587 (if_then_else (ltgt (match_dup 1) (const_int 0))
1588 (label_ref (match_operand 0 "" ""))
1592 if (GET_MODE (sparc_compare_op0) == TFmode && ! TARGET_HARD_QUAD)
1595 = sparc_emit_float_lib_cmp (sparc_compare_op0, sparc_compare_op1, LTGT);
1596 gcc_assert (code == NE);
1597 emit_jump_insn (gen_bne (operands[0]));
1600 operands[1] = gen_compare_reg (LTGT);
1603 ;; Now match both normal and inverted jump.
1605 ;; XXX fpcmp nop braindamage
1606 (define_insn "*normal_branch"
1608 (if_then_else (match_operator 0 "noov_compare_operator"
1609 [(reg 100) (const_int 0)])
1610 (label_ref (match_operand 1 "" ""))
1614 return output_cbranch (operands[0], operands[1], 1, 0,
1615 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1618 [(set_attr "type" "branch")
1619 (set_attr "branch_type" "icc")])
1621 ;; XXX fpcmp nop braindamage
1622 (define_insn "*inverted_branch"
1624 (if_then_else (match_operator 0 "noov_compare_operator"
1625 [(reg 100) (const_int 0)])
1627 (label_ref (match_operand 1 "" ""))))]
1630 return output_cbranch (operands[0], operands[1], 1, 1,
1631 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1634 [(set_attr "type" "branch")
1635 (set_attr "branch_type" "icc")])
1637 ;; XXX fpcmp nop braindamage
1638 (define_insn "*normal_fp_branch"
1640 (if_then_else (match_operator 1 "comparison_operator"
1641 [(match_operand:CCFP 0 "fcc_register_operand" "c")
1643 (label_ref (match_operand 2 "" ""))
1647 return output_cbranch (operands[1], operands[2], 2, 0,
1648 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1651 [(set_attr "type" "branch")
1652 (set_attr "branch_type" "fcc")])
1654 ;; XXX fpcmp nop braindamage
1655 (define_insn "*inverted_fp_branch"
1657 (if_then_else (match_operator 1 "comparison_operator"
1658 [(match_operand:CCFP 0 "fcc_register_operand" "c")
1661 (label_ref (match_operand 2 "" ""))))]
1664 return output_cbranch (operands[1], operands[2], 2, 1,
1665 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1668 [(set_attr "type" "branch")
1669 (set_attr "branch_type" "fcc")])
1671 ;; XXX fpcmp nop braindamage
1672 (define_insn "*normal_fpe_branch"
1674 (if_then_else (match_operator 1 "comparison_operator"
1675 [(match_operand:CCFPE 0 "fcc_register_operand" "c")
1677 (label_ref (match_operand 2 "" ""))
1681 return output_cbranch (operands[1], operands[2], 2, 0,
1682 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1685 [(set_attr "type" "branch")
1686 (set_attr "branch_type" "fcc")])
1688 ;; XXX fpcmp nop braindamage
1689 (define_insn "*inverted_fpe_branch"
1691 (if_then_else (match_operator 1 "comparison_operator"
1692 [(match_operand:CCFPE 0 "fcc_register_operand" "c")
1695 (label_ref (match_operand 2 "" ""))))]
1698 return output_cbranch (operands[1], operands[2], 2, 1,
1699 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1702 [(set_attr "type" "branch")
1703 (set_attr "branch_type" "fcc")])
1705 ;; SPARC V9-specific jump insns. None of these are guaranteed to be
1706 ;; in the architecture.
1708 ;; There are no 32 bit brreg insns.
1711 (define_insn "*normal_int_branch_sp64"
1713 (if_then_else (match_operator 0 "v9_register_compare_operator"
1714 [(match_operand:DI 1 "register_operand" "r")
1716 (label_ref (match_operand 2 "" ""))
1720 return output_v9branch (operands[0], operands[2], 1, 2, 0,
1721 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1724 [(set_attr "type" "branch")
1725 (set_attr "branch_type" "reg")])
1728 (define_insn "*inverted_int_branch_sp64"
1730 (if_then_else (match_operator 0 "v9_register_compare_operator"
1731 [(match_operand:DI 1 "register_operand" "r")
1734 (label_ref (match_operand 2 "" ""))))]
1737 return output_v9branch (operands[0], operands[2], 1, 2, 1,
1738 final_sequence && INSN_ANNULLED_BRANCH_P (insn),
1741 [(set_attr "type" "branch")
1742 (set_attr "branch_type" "reg")])
1745 (define_mode_iterator P [(SI "Pmode == SImode") (DI "Pmode == DImode")])
1747 ;; Load in operand 0 the (absolute) address of operand 1, which is a symbolic
1748 ;; value subject to a PC-relative relocation. Operand 2 is a helper function
1749 ;; that adds the PC value at the call point to operand 0.
1751 (define_insn "load_pcrel_sym<P:mode>"
1752 [(set (match_operand:P 0 "register_operand" "=r")
1753 (unspec:P [(match_operand:P 1 "symbolic_operand" "")
1754 (match_operand:P 2 "call_address_operand" "")] UNSPEC_LOAD_PCREL_SYM))
1755 (clobber (reg:P 15))]
1758 if (flag_delayed_branch)
1759 return "sethi\t%%hi(%a1-4), %0\n\tcall\t%a2\n\t add\t%0, %%lo(%a1+4), %0";
1761 return "sethi\t%%hi(%a1-8), %0\n\tadd\t%0, %%lo(%a1-4), %0\n\tcall\t%a2\n\t nop";
1763 [(set (attr "type") (const_string "multi"))
1764 (set (attr "length")
1765 (if_then_else (eq_attr "delayed_branch" "true")
1770 ;; Integer move instructions
1772 (define_expand "movqi"
1773 [(set (match_operand:QI 0 "nonimmediate_operand" "")
1774 (match_operand:QI 1 "general_operand" ""))]
1777 if (sparc_expand_move (QImode, operands))
1781 (define_insn "*movqi_insn"
1782 [(set (match_operand:QI 0 "nonimmediate_operand" "=r,r,m")
1783 (match_operand:QI 1 "input_operand" "rI,m,rJ"))]
1784 "(register_operand (operands[0], QImode)
1785 || register_or_zero_operand (operands[1], QImode))"
1790 [(set_attr "type" "*,load,store")
1791 (set_attr "us3load_type" "*,3cycle,*")])
1793 (define_expand "movhi"
1794 [(set (match_operand:HI 0 "nonimmediate_operand" "")
1795 (match_operand:HI 1 "general_operand" ""))]
1798 if (sparc_expand_move (HImode, operands))
1802 (define_insn "*movhi_insn"
1803 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
1804 (match_operand:HI 1 "input_operand" "rI,K,m,rJ"))]
1805 "(register_operand (operands[0], HImode)
1806 || register_or_zero_operand (operands[1], HImode))"
1809 sethi\t%%hi(%a1), %0
1812 [(set_attr "type" "*,*,load,store")
1813 (set_attr "us3load_type" "*,*,3cycle,*")])
1815 ;; We always work with constants here.
1816 (define_insn "*movhi_lo_sum"
1817 [(set (match_operand:HI 0 "register_operand" "=r")
1818 (ior:HI (match_operand:HI 1 "register_operand" "%r")
1819 (match_operand:HI 2 "small_int_operand" "I")))]
1823 (define_expand "movsi"
1824 [(set (match_operand:SI 0 "nonimmediate_operand" "")
1825 (match_operand:SI 1 "general_operand" ""))]
1828 if (sparc_expand_move (SImode, operands))
1832 (define_insn "*movsi_insn"
1833 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,r,r,m,!f,!f,!m,d")
1834 (match_operand:SI 1 "input_operand" "rI,K,m,rJ,f,m,f,J"))]
1835 "(register_operand (operands[0], SImode)
1836 || register_or_zero_operand (operands[1], SImode))"
1839 sethi\t%%hi(%a1), %0
1846 [(set_attr "type" "*,*,load,store,fpmove,fpload,fpstore,fga")])
1848 (define_insn "*movsi_lo_sum"
1849 [(set (match_operand:SI 0 "register_operand" "=r")
1850 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
1851 (match_operand:SI 2 "immediate_operand" "in")))]
1853 "or\t%1, %%lo(%a2), %0")
1855 (define_insn "*movsi_high"
1856 [(set (match_operand:SI 0 "register_operand" "=r")
1857 (high:SI (match_operand:SI 1 "immediate_operand" "in")))]
1859 "sethi\t%%hi(%a1), %0")
1861 ;; The next two patterns must wrap the SYMBOL_REF in an UNSPEC
1862 ;; so that CSE won't optimize the address computation away.
1863 (define_insn "movsi_lo_sum_pic"
1864 [(set (match_operand:SI 0 "register_operand" "=r")
1865 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
1866 (unspec:SI [(match_operand:SI 2 "immediate_operand" "in")] UNSPEC_MOVE_PIC)))]
1868 "or\t%1, %%lo(%a2), %0")
1870 (define_insn "movsi_high_pic"
1871 [(set (match_operand:SI 0 "register_operand" "=r")
1872 (high:SI (unspec:SI [(match_operand 1 "" "")] UNSPEC_MOVE_PIC)))]
1873 "flag_pic && check_pic (1)"
1874 "sethi\t%%hi(%a1), %0")
1876 (define_expand "movsi_pic_label_ref"
1877 [(set (match_dup 3) (high:SI
1878 (unspec:SI [(match_operand:SI 1 "label_ref_operand" "")
1879 (match_dup 2)] UNSPEC_MOVE_PIC_LABEL)))
1880 (set (match_dup 4) (lo_sum:SI (match_dup 3)
1881 (unspec:SI [(match_dup 1) (match_dup 2)] UNSPEC_MOVE_PIC_LABEL)))
1882 (set (match_operand:SI 0 "register_operand" "=r")
1883 (minus:SI (match_dup 5) (match_dup 4)))]
1886 crtl->uses_pic_offset_table = 1;
1887 operands[2] = gen_rtx_SYMBOL_REF (Pmode, "_GLOBAL_OFFSET_TABLE_");
1888 if (!can_create_pseudo_p ())
1890 operands[3] = operands[0];
1891 operands[4] = operands[0];
1895 operands[3] = gen_reg_rtx (SImode);
1896 operands[4] = gen_reg_rtx (SImode);
1898 operands[5] = pic_offset_table_rtx;
1901 (define_insn "*movsi_high_pic_label_ref"
1902 [(set (match_operand:SI 0 "register_operand" "=r")
1904 (unspec:SI [(match_operand:SI 1 "label_ref_operand" "")
1905 (match_operand:SI 2 "" "")] UNSPEC_MOVE_PIC_LABEL)))]
1907 "sethi\t%%hi(%a2-(%a1-.)), %0")
1909 (define_insn "*movsi_lo_sum_pic_label_ref"
1910 [(set (match_operand:SI 0 "register_operand" "=r")
1911 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
1912 (unspec:SI [(match_operand:SI 2 "label_ref_operand" "")
1913 (match_operand:SI 3 "" "")] UNSPEC_MOVE_PIC_LABEL)))]
1915 "or\t%1, %%lo(%a3-(%a2-.)), %0")
1917 ;; Set up the PIC register for VxWorks.
1919 (define_expand "vxworks_load_got"
1921 (high:SI (match_dup 1)))
1923 (mem:SI (lo_sum:SI (match_dup 0) (match_dup 1))))
1925 (mem:SI (lo_sum:SI (match_dup 0) (match_dup 2))))]
1926 "TARGET_VXWORKS_RTP"
1928 operands[0] = pic_offset_table_rtx;
1929 operands[1] = gen_rtx_SYMBOL_REF (SImode, VXWORKS_GOTT_BASE);
1930 operands[2] = gen_rtx_SYMBOL_REF (SImode, VXWORKS_GOTT_INDEX);
1933 (define_expand "movdi"
1934 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1935 (match_operand:DI 1 "general_operand" ""))]
1938 if (sparc_expand_move (DImode, operands))
1942 ;; Be careful, fmovd does not exist when !v9.
1943 ;; We match MEM moves directly when we have correct even
1944 ;; numbered registers, but fall into splits otherwise.
1945 ;; The constraint ordering here is really important to
1946 ;; avoid insane problems in reload, especially for patterns
1949 ;; (set (mem:DI (plus:SI (reg:SI 30 %fp)
1950 ;; (const_int -5016)))
1954 (define_insn "*movdi_insn_sp32"
1955 [(set (match_operand:DI 0 "nonimmediate_operand"
1956 "=o,T,U,o,r,r,r,?T,?f,?f,?o,?f")
1957 (match_operand:DI 1 "input_operand"
1958 " J,U,T,r,o,i,r, f, T, o, f, f"))]
1960 && (register_operand (operands[0], DImode)
1961 || register_or_zero_operand (operands[1], DImode))"
1975 [(set_attr "type" "store,store,load,*,*,*,*,fpstore,fpload,*,*,*")
1976 (set_attr "length" "2,*,*,2,2,2,2,*,*,2,2,2")])
1978 (define_insn "*movdi_insn_sp32_v9"
1979 [(set (match_operand:DI 0 "nonimmediate_operand"
1980 "=T,o,T,U,o,r,r,r,?T,?f,?f,?o,?e,?e,?W")
1981 (match_operand:DI 1 "input_operand"
1982 " J,J,U,T,r,o,i,r, f, T, o, f, e, W, e"))]
1985 && (register_operand (operands[0], DImode)
1986 || register_or_zero_operand (operands[1], DImode))"
2003 [(set_attr "type" "store,store,store,load,*,*,*,*,fpstore,fpload,*,*,fpmove,fpload,fpstore")
2004 (set_attr "length" "*,2,*,*,2,2,2,2,*,*,2,2,*,*,*")
2005 (set_attr "fptype" "*,*,*,*,*,*,*,*,*,*,*,*,double,*,*")])
2007 (define_insn "*movdi_insn_sp64"
2008 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,r,m,?e,?e,?W,b")
2009 (match_operand:DI 1 "input_operand" "rI,N,m,rJ,e,W,e,J"))]
2011 && (register_operand (operands[0], DImode)
2012 || register_or_zero_operand (operands[1], DImode))"
2015 sethi\t%%hi(%a1), %0
2022 [(set_attr "type" "*,*,load,store,fpmove,fpload,fpstore,fga")
2023 (set_attr "fptype" "*,*,*,*,double,*,*,double")])
2025 (define_expand "movdi_pic_label_ref"
2026 [(set (match_dup 3) (high:DI
2027 (unspec:DI [(match_operand:DI 1 "label_ref_operand" "")
2028 (match_dup 2)] UNSPEC_MOVE_PIC_LABEL)))
2029 (set (match_dup 4) (lo_sum:DI (match_dup 3)
2030 (unspec:DI [(match_dup 1) (match_dup 2)] UNSPEC_MOVE_PIC_LABEL)))
2031 (set (match_operand:DI 0 "register_operand" "=r")
2032 (minus:DI (match_dup 5) (match_dup 4)))]
2033 "TARGET_ARCH64 && flag_pic"
2035 crtl->uses_pic_offset_table = 1;
2036 operands[2] = gen_rtx_SYMBOL_REF (Pmode, "_GLOBAL_OFFSET_TABLE_");
2037 if (!can_create_pseudo_p ())
2039 operands[3] = operands[0];
2040 operands[4] = operands[0];
2044 operands[3] = gen_reg_rtx (DImode);
2045 operands[4] = gen_reg_rtx (DImode);
2047 operands[5] = pic_offset_table_rtx;
2050 (define_insn "*movdi_high_pic_label_ref"
2051 [(set (match_operand:DI 0 "register_operand" "=r")
2053 (unspec:DI [(match_operand:DI 1 "label_ref_operand" "")
2054 (match_operand:DI 2 "" "")] UNSPEC_MOVE_PIC_LABEL)))]
2055 "TARGET_ARCH64 && flag_pic"
2056 "sethi\t%%hi(%a2-(%a1-.)), %0")
2058 (define_insn "*movdi_lo_sum_pic_label_ref"
2059 [(set (match_operand:DI 0 "register_operand" "=r")
2060 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2061 (unspec:DI [(match_operand:DI 2 "label_ref_operand" "")
2062 (match_operand:DI 3 "" "")] UNSPEC_MOVE_PIC_LABEL)))]
2063 "TARGET_ARCH64 && flag_pic"
2064 "or\t%1, %%lo(%a3-(%a2-.)), %0")
2066 ;; SPARC-v9 code model support insns. See sparc_emit_set_symbolic_const64
2067 ;; in sparc.c to see what is going on here... PIC stuff comes first.
2069 (define_insn "movdi_lo_sum_pic"
2070 [(set (match_operand:DI 0 "register_operand" "=r")
2071 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2072 (unspec:DI [(match_operand:DI 2 "immediate_operand" "in")] UNSPEC_MOVE_PIC)))]
2073 "TARGET_ARCH64 && flag_pic"
2074 "or\t%1, %%lo(%a2), %0")
2076 (define_insn "movdi_high_pic"
2077 [(set (match_operand:DI 0 "register_operand" "=r")
2078 (high:DI (unspec:DI [(match_operand 1 "" "")] UNSPEC_MOVE_PIC)))]
2079 "TARGET_ARCH64 && flag_pic && check_pic (1)"
2080 "sethi\t%%hi(%a1), %0")
2082 (define_insn "*sethi_di_medlow_embmedany_pic"
2083 [(set (match_operand:DI 0 "register_operand" "=r")
2084 (high:DI (match_operand:DI 1 "medium_pic_operand" "")))]
2085 "(TARGET_CM_MEDLOW || TARGET_CM_EMBMEDANY) && check_pic (1)"
2086 "sethi\t%%hi(%a1), %0")
2088 (define_insn "*sethi_di_medlow"
2089 [(set (match_operand:DI 0 "register_operand" "=r")
2090 (high:DI (match_operand:DI 1 "symbolic_operand" "")))]
2091 "TARGET_CM_MEDLOW && check_pic (1)"
2092 "sethi\t%%hi(%a1), %0")
2094 (define_insn "*losum_di_medlow"
2095 [(set (match_operand:DI 0 "register_operand" "=r")
2096 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2097 (match_operand:DI 2 "symbolic_operand" "")))]
2099 "or\t%1, %%lo(%a2), %0")
2101 (define_insn "seth44"
2102 [(set (match_operand:DI 0 "register_operand" "=r")
2103 (high:DI (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")] UNSPEC_SETH44)))]
2105 "sethi\t%%h44(%a1), %0")
2107 (define_insn "setm44"
2108 [(set (match_operand:DI 0 "register_operand" "=r")
2109 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2110 (unspec:DI [(match_operand:DI 2 "symbolic_operand" "")] UNSPEC_SETM44)))]
2112 "or\t%1, %%m44(%a2), %0")
2114 (define_insn "setl44"
2115 [(set (match_operand:DI 0 "register_operand" "=r")
2116 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2117 (match_operand:DI 2 "symbolic_operand" "")))]
2119 "or\t%1, %%l44(%a2), %0")
2121 (define_insn "sethh"
2122 [(set (match_operand:DI 0 "register_operand" "=r")
2123 (high:DI (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")] UNSPEC_SETHH)))]
2125 "sethi\t%%hh(%a1), %0")
2127 (define_insn "setlm"
2128 [(set (match_operand:DI 0 "register_operand" "=r")
2129 (high:DI (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")] UNSPEC_SETLM)))]
2131 "sethi\t%%lm(%a1), %0")
2133 (define_insn "sethm"
2134 [(set (match_operand:DI 0 "register_operand" "=r")
2135 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2136 (unspec:DI [(match_operand:DI 2 "symbolic_operand" "")] UNSPEC_EMB_SETHM)))]
2138 "or\t%1, %%hm(%a2), %0")
2140 (define_insn "setlo"
2141 [(set (match_operand:DI 0 "register_operand" "=r")
2142 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2143 (match_operand:DI 2 "symbolic_operand" "")))]
2145 "or\t%1, %%lo(%a2), %0")
2147 (define_insn "embmedany_sethi"
2148 [(set (match_operand:DI 0 "register_operand" "=r")
2149 (high:DI (unspec:DI [(match_operand:DI 1 "data_segment_operand" "")] UNSPEC_EMB_HISUM)))]
2150 "TARGET_CM_EMBMEDANY && check_pic (1)"
2151 "sethi\t%%hi(%a1), %0")
2153 (define_insn "embmedany_losum"
2154 [(set (match_operand:DI 0 "register_operand" "=r")
2155 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2156 (match_operand:DI 2 "data_segment_operand" "")))]
2157 "TARGET_CM_EMBMEDANY"
2158 "add\t%1, %%lo(%a2), %0")
2160 (define_insn "embmedany_brsum"
2161 [(set (match_operand:DI 0 "register_operand" "=r")
2162 (unspec:DI [(match_operand:DI 1 "register_operand" "r")] UNSPEC_EMB_HISUM))]
2163 "TARGET_CM_EMBMEDANY"
2166 (define_insn "embmedany_textuhi"
2167 [(set (match_operand:DI 0 "register_operand" "=r")
2168 (high:DI (unspec:DI [(match_operand:DI 1 "text_segment_operand" "")] UNSPEC_EMB_TEXTUHI)))]
2169 "TARGET_CM_EMBMEDANY && check_pic (1)"
2170 "sethi\t%%uhi(%a1), %0")
2172 (define_insn "embmedany_texthi"
2173 [(set (match_operand:DI 0 "register_operand" "=r")
2174 (high:DI (unspec:DI [(match_operand:DI 1 "text_segment_operand" "")] UNSPEC_EMB_TEXTHI)))]
2175 "TARGET_CM_EMBMEDANY && check_pic (1)"
2176 "sethi\t%%hi(%a1), %0")
2178 (define_insn "embmedany_textulo"
2179 [(set (match_operand:DI 0 "register_operand" "=r")
2180 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2181 (unspec:DI [(match_operand:DI 2 "text_segment_operand" "")] UNSPEC_EMB_TEXTULO)))]
2182 "TARGET_CM_EMBMEDANY"
2183 "or\t%1, %%ulo(%a2), %0")
2185 (define_insn "embmedany_textlo"
2186 [(set (match_operand:DI 0 "register_operand" "=r")
2187 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
2188 (match_operand:DI 2 "text_segment_operand" "")))]
2189 "TARGET_CM_EMBMEDANY"
2190 "or\t%1, %%lo(%a2), %0")
2192 ;; Now some patterns to help reload out a bit.
2193 (define_expand "reload_indi"
2194 [(parallel [(match_operand:DI 0 "register_operand" "=r")
2195 (match_operand:DI 1 "immediate_operand" "")
2196 (match_operand:TI 2 "register_operand" "=&r")])]
2198 || TARGET_CM_EMBMEDANY)
2201 sparc_emit_set_symbolic_const64 (operands[0], operands[1], operands[2]);
2205 (define_expand "reload_outdi"
2206 [(parallel [(match_operand:DI 0 "register_operand" "=r")
2207 (match_operand:DI 1 "immediate_operand" "")
2208 (match_operand:TI 2 "register_operand" "=&r")])]
2210 || TARGET_CM_EMBMEDANY)
2213 sparc_emit_set_symbolic_const64 (operands[0], operands[1], operands[2]);
2217 ;; Split up putting CONSTs and REGs into DI regs when !arch64
2219 [(set (match_operand:DI 0 "register_operand" "")
2220 (match_operand:DI 1 "const_int_operand" ""))]
2221 "! TARGET_ARCH64 && reload_completed"
2222 [(clobber (const_int 0))]
2224 #if HOST_BITS_PER_WIDE_INT == 32
2225 emit_insn (gen_movsi (gen_highpart (SImode, operands[0]),
2226 (INTVAL (operands[1]) < 0) ?
2229 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]),
2232 unsigned int low, high;
2234 low = trunc_int_for_mode (INTVAL (operands[1]), SImode);
2235 high = trunc_int_for_mode (INTVAL (operands[1]) >> 32, SImode);
2236 emit_insn (gen_movsi (gen_highpart (SImode, operands[0]), GEN_INT (high)));
2238 /* Slick... but this trick loses if this subreg constant part
2239 can be done in one insn. */
2241 && ! SPARC_SETHI32_P (high)
2242 && ! SPARC_SIMM13_P (high))
2243 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]),
2244 gen_highpart (SImode, operands[0])));
2246 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]), GEN_INT (low)));
2252 [(set (match_operand:DI 0 "register_operand" "")
2253 (match_operand:DI 1 "const_double_operand" ""))]
2257 && ((GET_CODE (operands[0]) == REG
2258 && REGNO (operands[0]) < 32)
2259 || (GET_CODE (operands[0]) == SUBREG
2260 && GET_CODE (SUBREG_REG (operands[0])) == REG
2261 && REGNO (SUBREG_REG (operands[0])) < 32))))"
2262 [(clobber (const_int 0))]
2264 emit_insn (gen_movsi (gen_highpart (SImode, operands[0]),
2265 GEN_INT (CONST_DOUBLE_HIGH (operands[1]))));
2267 /* Slick... but this trick loses if this subreg constant part
2268 can be done in one insn. */
2269 if (CONST_DOUBLE_LOW (operands[1]) == CONST_DOUBLE_HIGH (operands[1])
2270 && ! SPARC_SETHI32_P (CONST_DOUBLE_HIGH (operands[1]))
2271 && ! SPARC_SIMM13_P (CONST_DOUBLE_HIGH (operands[1])))
2273 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]),
2274 gen_highpart (SImode, operands[0])));
2278 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]),
2279 GEN_INT (CONST_DOUBLE_LOW (operands[1]))));
2285 [(set (match_operand:DI 0 "register_operand" "")
2286 (match_operand:DI 1 "register_operand" ""))]
2290 && ((GET_CODE (operands[0]) == REG
2291 && REGNO (operands[0]) < 32)
2292 || (GET_CODE (operands[0]) == SUBREG
2293 && GET_CODE (SUBREG_REG (operands[0])) == REG
2294 && REGNO (SUBREG_REG (operands[0])) < 32))))"
2295 [(clobber (const_int 0))]
2297 rtx set_dest = operands[0];
2298 rtx set_src = operands[1];
2302 dest1 = gen_highpart (SImode, set_dest);
2303 dest2 = gen_lowpart (SImode, set_dest);
2304 src1 = gen_highpart (SImode, set_src);
2305 src2 = gen_lowpart (SImode, set_src);
2307 /* Now emit using the real source and destination we found, swapping
2308 the order if we detect overlap. */
2309 if (reg_overlap_mentioned_p (dest1, src2))
2311 emit_insn (gen_movsi (dest2, src2));
2312 emit_insn (gen_movsi (dest1, src1));
2316 emit_insn (gen_movsi (dest1, src1));
2317 emit_insn (gen_movsi (dest2, src2));
2322 ;; Now handle the cases of memory moves from/to non-even
2323 ;; DI mode register pairs.
2325 [(set (match_operand:DI 0 "register_operand" "")
2326 (match_operand:DI 1 "memory_operand" ""))]
2329 && sparc_splitdi_legitimate (operands[0], operands[1]))"
2330 [(clobber (const_int 0))]
2332 rtx word0 = adjust_address (operands[1], SImode, 0);
2333 rtx word1 = adjust_address (operands[1], SImode, 4);
2334 rtx high_part = gen_highpart (SImode, operands[0]);
2335 rtx low_part = gen_lowpart (SImode, operands[0]);
2337 if (reg_overlap_mentioned_p (high_part, word1))
2339 emit_insn (gen_movsi (low_part, word1));
2340 emit_insn (gen_movsi (high_part, word0));
2344 emit_insn (gen_movsi (high_part, word0));
2345 emit_insn (gen_movsi (low_part, word1));
2351 [(set (match_operand:DI 0 "memory_operand" "")
2352 (match_operand:DI 1 "register_operand" ""))]
2355 && sparc_splitdi_legitimate (operands[1], operands[0]))"
2356 [(clobber (const_int 0))]
2358 emit_insn (gen_movsi (adjust_address (operands[0], SImode, 0),
2359 gen_highpart (SImode, operands[1])));
2360 emit_insn (gen_movsi (adjust_address (operands[0], SImode, 4),
2361 gen_lowpart (SImode, operands[1])));
2366 [(set (match_operand:DI 0 "memory_operand" "")
2367 (match_operand:DI 1 "const_zero_operand" ""))]
2371 && ! mem_min_alignment (operands[0], 8)))
2372 && offsettable_memref_p (operands[0])"
2373 [(clobber (const_int 0))]
2375 emit_insn (gen_movsi (adjust_address (operands[0], SImode, 0), const0_rtx));
2376 emit_insn (gen_movsi (adjust_address (operands[0], SImode, 4), const0_rtx));
2381 ;; Floating point and vector move instructions
2383 ;; We don't define V1SI because SI should work just fine.
2384 (define_mode_iterator V32 [SF V2HI V4QI])
2386 ;; Yes, you guessed it right, the former movsf expander.
2387 (define_expand "mov<V32:mode>"
2388 [(set (match_operand:V32 0 "nonimmediate_operand" "")
2389 (match_operand:V32 1 "general_operand" ""))]
2390 "<V32:MODE>mode == SFmode || TARGET_VIS"
2392 if (sparc_expand_move (<V32:MODE>mode, operands))
2396 (define_insn "*movsf_insn"
2397 [(set (match_operand:V32 0 "nonimmediate_operand" "=d,f,*r,*r,*r,f,*r,m,m")
2398 (match_operand:V32 1 "input_operand" "GY,f,*rRY,Q,S,m,m,f,*rGY"))]
2400 && (register_operand (operands[0], <V32:MODE>mode)
2401 || register_or_zero_operand (operands[1], <V32:MODE>mode))"
2403 if (GET_CODE (operands[1]) == CONST_DOUBLE
2404 && (which_alternative == 2
2405 || which_alternative == 3
2406 || which_alternative == 4))
2411 REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
2412 REAL_VALUE_TO_TARGET_SINGLE (r, i);
2413 operands[1] = GEN_INT (i);
2416 switch (which_alternative)
2419 return "fzeros\t%0";
2421 return "fmovs\t%1, %0";
2423 return "mov\t%1, %0";
2425 return "sethi\t%%hi(%a1), %0";
2430 return "ld\t%1, %0";
2433 return "st\t%r1, %0";
2438 [(set_attr "type" "fga,fpmove,*,*,*,fpload,load,fpstore,store")])
2440 ;; Exactly the same as above, except that all `f' cases are deleted.
2441 ;; This is necessary to prevent reload from ever trying to use a `f' reg
2444 (define_insn "*movsf_insn_no_fpu"
2445 [(set (match_operand:SF 0 "nonimmediate_operand" "=r,r,r,r,m")
2446 (match_operand:SF 1 "input_operand" "rR,Q,S,m,rG"))]
2448 && (register_operand (operands[0], SFmode)
2449 || register_or_zero_operand (operands[1], SFmode))"
2451 if (GET_CODE (operands[1]) == CONST_DOUBLE
2452 && (which_alternative == 0
2453 || which_alternative == 1
2454 || which_alternative == 2))
2459 REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
2460 REAL_VALUE_TO_TARGET_SINGLE (r, i);
2461 operands[1] = GEN_INT (i);
2464 switch (which_alternative)
2467 return "mov\t%1, %0";
2469 return "sethi\t%%hi(%a1), %0";
2473 return "ld\t%1, %0";
2475 return "st\t%r1, %0";
2480 [(set_attr "type" "*,*,*,load,store")])
2482 ;; The following 3 patterns build SFmode constants in integer registers.
2484 (define_insn "*movsf_lo_sum"
2485 [(set (match_operand:SF 0 "register_operand" "=r")
2486 (lo_sum:SF (match_operand:SF 1 "register_operand" "r")
2487 (match_operand:SF 2 "fp_const_high_losum_operand" "S")))]
2493 REAL_VALUE_FROM_CONST_DOUBLE (r, operands[2]);
2494 REAL_VALUE_TO_TARGET_SINGLE (r, i);
2495 operands[2] = GEN_INT (i);
2496 return "or\t%1, %%lo(%a2), %0";
2499 (define_insn "*movsf_high"
2500 [(set (match_operand:SF 0 "register_operand" "=r")
2501 (high:SF (match_operand:SF 1 "fp_const_high_losum_operand" "S")))]
2507 REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
2508 REAL_VALUE_TO_TARGET_SINGLE (r, i);
2509 operands[1] = GEN_INT (i);
2510 return "sethi\t%%hi(%1), %0";
2514 [(set (match_operand:SF 0 "register_operand" "")
2515 (match_operand:SF 1 "fp_const_high_losum_operand" ""))]
2516 "REG_P (operands[0]) && REGNO (operands[0]) < 32"
2517 [(set (match_dup 0) (high:SF (match_dup 1)))
2518 (set (match_dup 0) (lo_sum:SF (match_dup 0) (match_dup 1)))])
2520 (define_mode_iterator V64 [DF V2SI V4HI V8QI])
2522 ;; Yes, you again guessed it right, the former movdf expander.
2523 (define_expand "mov<V64:mode>"
2524 [(set (match_operand:V64 0 "nonimmediate_operand" "")
2525 (match_operand:V64 1 "general_operand" ""))]
2526 "<V64:MODE>mode == DFmode || TARGET_VIS"
2528 if (sparc_expand_move (<V64:MODE>mode, operands))
2532 ;; Be careful, fmovd does not exist when !v9.
2533 (define_insn "*movdf_insn_sp32"
2534 [(set (match_operand:DF 0 "nonimmediate_operand" "=e,W,U,T,o,e,*r,o,e,o")
2535 (match_operand:DF 1 "input_operand" "W#F,e,T,U,G,e,*rFo,*r,o#F,e"))]
2538 && (register_operand (operands[0], DFmode)
2539 || register_or_zero_operand (operands[1], DFmode))"
2551 [(set_attr "type" "fpload,fpstore,load,store,*,*,*,*,*,*")
2552 (set_attr "length" "*,*,*,*,2,2,2,2,2,2")])
2554 (define_insn "*movdf_insn_sp32_no_fpu"
2555 [(set (match_operand:DF 0 "nonimmediate_operand" "=U,T,o,r,o")
2556 (match_operand:DF 1 "input_operand" "T,U,G,ro,r"))]
2559 && (register_operand (operands[0], DFmode)
2560 || register_or_zero_operand (operands[1], DFmode))"
2567 [(set_attr "type" "load,store,*,*,*")
2568 (set_attr "length" "*,*,2,2,2")])
2570 ;; We have available v9 double floats but not 64-bit integer registers.
2571 (define_insn "*movdf_insn_sp32_v9"
2572 [(set (match_operand:V64 0 "nonimmediate_operand" "=b,e,e,T,W,U,T,f,*r,o")
2573 (match_operand:V64 1 "input_operand" "GY,e,W#F,GY,e,T,U,o#F,*roGYF,*rGYf"))]
2577 && (register_operand (operands[0], <V64:MODE>mode)
2578 || register_or_zero_operand (operands[1], <V64:MODE>mode))"
2590 [(set_attr "type" "fga,fpmove,load,store,store,load,store,*,*,*")
2591 (set_attr "length" "*,*,*,*,*,*,*,2,2,2")
2592 (set_attr "fptype" "double,double,*,*,*,*,*,*,*,*")])
2594 (define_insn "*movdf_insn_sp32_v9_no_fpu"
2595 [(set (match_operand:DF 0 "nonimmediate_operand" "=U,T,T,r,o")
2596 (match_operand:DF 1 "input_operand" "T,U,G,ro,rG"))]
2600 && (register_operand (operands[0], DFmode)
2601 || register_or_zero_operand (operands[1], DFmode))"
2608 [(set_attr "type" "load,store,store,*,*")
2609 (set_attr "length" "*,*,*,2,2")])
2611 ;; We have available both v9 double floats and 64-bit integer registers.
2612 (define_insn "*movdf_insn_sp64"
2613 [(set (match_operand:V64 0 "nonimmediate_operand" "=b,e,e,W,*r,*r,m,*r")
2614 (match_operand:V64 1 "input_operand" "GY,e,W#F,e,*rGY,m,*rGY,F"))]
2617 && (register_operand (operands[0], <V64:MODE>mode)
2618 || register_or_zero_operand (operands[1], <V64:MODE>mode))"
2628 [(set_attr "type" "fga,fpmove,load,store,*,load,store,*")
2629 (set_attr "length" "*,*,*,*,*,*,*,2")
2630 (set_attr "fptype" "double,double,*,*,*,*,*,*")])
2632 (define_insn "*movdf_insn_sp64_no_fpu"
2633 [(set (match_operand:DF 0 "nonimmediate_operand" "=r,r,m")
2634 (match_operand:DF 1 "input_operand" "r,m,rG"))]
2637 && (register_operand (operands[0], DFmode)
2638 || register_or_zero_operand (operands[1], DFmode))"
2643 [(set_attr "type" "*,load,store")])
2645 ;; This pattern build DFmode constants in integer registers.
2647 [(set (match_operand:DF 0 "register_operand" "")
2648 (match_operand:DF 1 "const_double_operand" ""))]
2650 && (GET_CODE (operands[0]) == REG
2651 && REGNO (operands[0]) < 32)
2652 && ! const_zero_operand(operands[1], DFmode)
2653 && reload_completed"
2654 [(clobber (const_int 0))]
2659 REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
2660 REAL_VALUE_TO_TARGET_DOUBLE (r, l);
2661 operands[0] = gen_rtx_raw_REG (DImode, REGNO (operands[0]));
2665 #if HOST_BITS_PER_WIDE_INT == 32
2670 val = ((HOST_WIDE_INT)(unsigned long)l[1] |
2671 ((HOST_WIDE_INT)(unsigned long)l[0] << 32));
2672 emit_insn (gen_movdi (operands[0], gen_int_mode (val, DImode)));
2677 emit_insn (gen_movsi (gen_highpart (SImode, operands[0]),
2678 gen_int_mode (l[0], SImode)));
2680 /* Slick... but this trick loses if this subreg constant part
2681 can be done in one insn. */
2683 && ! SPARC_SETHI32_P (l[0])
2684 && ! SPARC_SIMM13_P (l[0]))
2686 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]),
2687 gen_highpart (SImode, operands[0])));
2691 emit_insn (gen_movsi (gen_lowpart (SImode, operands[0]),
2692 gen_int_mode (l[1], SImode)));
2698 ;; Ok, now the splits to handle all the multi insn and
2699 ;; mis-aligned memory address cases.
2700 ;; In these splits please take note that we must be
2701 ;; careful when V9 but not ARCH64 because the integer
2702 ;; register DFmode cases must be handled.
2704 [(set (match_operand:V64 0 "register_operand" "")
2705 (match_operand:V64 1 "register_operand" ""))]
2708 && ((GET_CODE (operands[0]) == REG
2709 && REGNO (operands[0]) < 32)
2710 || (GET_CODE (operands[0]) == SUBREG
2711 && GET_CODE (SUBREG_REG (operands[0])) == REG
2712 && REGNO (SUBREG_REG (operands[0])) < 32))))
2713 && reload_completed"
2714 [(clobber (const_int 0))]
2716 rtx set_dest = operands[0];
2717 rtx set_src = operands[1];
2720 enum machine_mode half_mode;
2722 /* We can be expanded for DFmode or integral vector modes. */
2723 if (<V64:MODE>mode == DFmode)
2728 dest1 = gen_highpart (half_mode, set_dest);
2729 dest2 = gen_lowpart (half_mode, set_dest);
2730 src1 = gen_highpart (half_mode, set_src);
2731 src2 = gen_lowpart (half_mode, set_src);
2733 /* Now emit using the real source and destination we found, swapping
2734 the order if we detect overlap. */
2735 if (reg_overlap_mentioned_p (dest1, src2))
2737 emit_move_insn_1 (dest2, src2);
2738 emit_move_insn_1 (dest1, src1);
2742 emit_move_insn_1 (dest1, src1);
2743 emit_move_insn_1 (dest2, src2);
2749 [(set (match_operand:V64 0 "register_operand" "")
2750 (match_operand:V64 1 "memory_operand" ""))]
2753 && (((REGNO (operands[0]) % 2) != 0)
2754 || ! mem_min_alignment (operands[1], 8))
2755 && offsettable_memref_p (operands[1])"
2756 [(clobber (const_int 0))]
2758 enum machine_mode half_mode;
2761 /* We can be expanded for DFmode or integral vector modes. */
2762 if (<V64:MODE>mode == DFmode)
2767 word0 = adjust_address (operands[1], half_mode, 0);
2768 word1 = adjust_address (operands[1], half_mode, 4);
2770 if (reg_overlap_mentioned_p (gen_highpart (half_mode, operands[0]), word1))
2772 emit_move_insn_1 (gen_lowpart (half_mode, operands[0]), word1);
2773 emit_move_insn_1 (gen_highpart (half_mode, operands[0]), word0);
2777 emit_move_insn_1 (gen_highpart (half_mode, operands[0]), word0);
2778 emit_move_insn_1 (gen_lowpart (half_mode, operands[0]), word1);
2784 [(set (match_operand:V64 0 "memory_operand" "")
2785 (match_operand:V64 1 "register_operand" ""))]
2788 && (((REGNO (operands[1]) % 2) != 0)
2789 || ! mem_min_alignment (operands[0], 8))
2790 && offsettable_memref_p (operands[0])"
2791 [(clobber (const_int 0))]
2793 enum machine_mode half_mode;
2796 /* We can be expanded for DFmode or integral vector modes. */
2797 if (<V64:MODE>mode == DFmode)
2802 word0 = adjust_address (operands[0], half_mode, 0);
2803 word1 = adjust_address (operands[0], half_mode, 4);
2805 emit_move_insn_1 (word0, gen_highpart (half_mode, operands[1]));
2806 emit_move_insn_1 (word1, gen_lowpart (half_mode, operands[1]));
2811 [(set (match_operand:V64 0 "memory_operand" "")
2812 (match_operand:V64 1 "const_zero_operand" ""))]
2816 && ! mem_min_alignment (operands[0], 8)))
2817 && offsettable_memref_p (operands[0])"
2818 [(clobber (const_int 0))]
2820 enum machine_mode half_mode;
2823 /* We can be expanded for DFmode or integral vector modes. */
2824 if (<V64:MODE>mode == DFmode)
2829 dest1 = adjust_address (operands[0], half_mode, 0);
2830 dest2 = adjust_address (operands[0], half_mode, 4);
2832 emit_move_insn_1 (dest1, CONST0_RTX (half_mode));
2833 emit_move_insn_1 (dest2, CONST0_RTX (half_mode));
2838 [(set (match_operand:V64 0 "register_operand" "")
2839 (match_operand:V64 1 "const_zero_operand" ""))]
2842 && ((GET_CODE (operands[0]) == REG
2843 && REGNO (operands[0]) < 32)
2844 || (GET_CODE (operands[0]) == SUBREG
2845 && GET_CODE (SUBREG_REG (operands[0])) == REG
2846 && REGNO (SUBREG_REG (operands[0])) < 32))"
2847 [(clobber (const_int 0))]
2849 enum machine_mode half_mode;
2850 rtx set_dest = operands[0];
2853 /* We can be expanded for DFmode or integral vector modes. */
2854 if (<V64:MODE>mode == DFmode)
2859 dest1 = gen_highpart (half_mode, set_dest);
2860 dest2 = gen_lowpart (half_mode, set_dest);
2861 emit_move_insn_1 (dest1, CONST0_RTX (half_mode));
2862 emit_move_insn_1 (dest2, CONST0_RTX (half_mode));
2866 (define_expand "movtf"
2867 [(set (match_operand:TF 0 "nonimmediate_operand" "")
2868 (match_operand:TF 1 "general_operand" ""))]
2871 if (sparc_expand_move (TFmode, operands))
2875 (define_insn "*movtf_insn_sp32"
2876 [(set (match_operand:TF 0 "nonimmediate_operand" "=b,e,o,U,r")
2877 (match_operand:TF 1 "input_operand" "G,oe,GeUr,o,roG"))]
2880 && (register_operand (operands[0], TFmode)
2881 || register_or_zero_operand (operands[1], TFmode))"
2883 [(set_attr "length" "4")])
2885 ;; Exactly the same as above, except that all `e' cases are deleted.
2886 ;; This is necessary to prevent reload from ever trying to use a `e' reg
2889 (define_insn "*movtf_insn_sp32_no_fpu"
2890 [(set (match_operand:TF 0 "nonimmediate_operand" "=o,U,o,r,o")
2891 (match_operand:TF 1 "input_operand" "G,o,U,roG,r"))]
2894 && (register_operand (operands[0], TFmode)
2895 || register_or_zero_operand (operands[1], TFmode))"
2897 [(set_attr "length" "4")])
2899 (define_insn "*movtf_insn_sp64"
2900 [(set (match_operand:TF 0 "nonimmediate_operand" "=b,e,o,r")
2901 (match_operand:TF 1 "input_operand" "G,oe,Ger,roG"))]
2904 && ! TARGET_HARD_QUAD
2905 && (register_operand (operands[0], TFmode)
2906 || register_or_zero_operand (operands[1], TFmode))"
2908 [(set_attr "length" "2")])
2910 (define_insn "*movtf_insn_sp64_hq"
2911 [(set (match_operand:TF 0 "nonimmediate_operand" "=b,e,e,m,o,r")
2912 (match_operand:TF 1 "input_operand" "G,e,m,e,rG,roG"))]
2916 && (register_operand (operands[0], TFmode)
2917 || register_or_zero_operand (operands[1], TFmode))"
2925 [(set_attr "type" "*,fpmove,fpload,fpstore,*,*")
2926 (set_attr "length" "2,*,*,*,2,2")])
2928 (define_insn "*movtf_insn_sp64_no_fpu"
2929 [(set (match_operand:TF 0 "nonimmediate_operand" "=r,o")
2930 (match_operand:TF 1 "input_operand" "orG,rG"))]
2933 && (register_operand (operands[0], TFmode)
2934 || register_or_zero_operand (operands[1], TFmode))"
2936 [(set_attr "length" "2")])
2938 ;; Now all the splits to handle multi-insn TF mode moves.
2940 [(set (match_operand:TF 0 "register_operand" "")
2941 (match_operand:TF 1 "register_operand" ""))]
2945 && ! TARGET_HARD_QUAD)
2946 || ! fp_register_operand (operands[0], TFmode))"
2947 [(clobber (const_int 0))]
2949 rtx set_dest = operands[0];
2950 rtx set_src = operands[1];
2954 dest1 = gen_df_reg (set_dest, 0);
2955 dest2 = gen_df_reg (set_dest, 1);
2956 src1 = gen_df_reg (set_src, 0);
2957 src2 = gen_df_reg (set_src, 1);
2959 /* Now emit using the real source and destination we found, swapping
2960 the order if we detect overlap. */
2961 if (reg_overlap_mentioned_p (dest1, src2))
2963 emit_insn (gen_movdf (dest2, src2));
2964 emit_insn (gen_movdf (dest1, src1));
2968 emit_insn (gen_movdf (dest1, src1));
2969 emit_insn (gen_movdf (dest2, src2));
2975 [(set (match_operand:TF 0 "nonimmediate_operand" "")
2976 (match_operand:TF 1 "const_zero_operand" ""))]
2978 [(clobber (const_int 0))]
2980 rtx set_dest = operands[0];
2983 switch (GET_CODE (set_dest))
2986 dest1 = gen_df_reg (set_dest, 0);
2987 dest2 = gen_df_reg (set_dest, 1);
2990 dest1 = adjust_address (set_dest, DFmode, 0);
2991 dest2 = adjust_address (set_dest, DFmode, 8);
2997 emit_insn (gen_movdf (dest1, CONST0_RTX (DFmode)));
2998 emit_insn (gen_movdf (dest2, CONST0_RTX (DFmode)));
3003 [(set (match_operand:TF 0 "register_operand" "")
3004 (match_operand:TF 1 "memory_operand" ""))]
3006 && offsettable_memref_p (operands[1])
3008 || ! TARGET_HARD_QUAD
3009 || ! fp_register_operand (operands[0], TFmode)))"
3010 [(clobber (const_int 0))]
3012 rtx word0 = adjust_address (operands[1], DFmode, 0);
3013 rtx word1 = adjust_address (operands[1], DFmode, 8);
3014 rtx set_dest, dest1, dest2;
3016 set_dest = operands[0];
3018 dest1 = gen_df_reg (set_dest, 0);
3019 dest2 = gen_df_reg (set_dest, 1);
3021 /* Now output, ordering such that we don't clobber any registers
3022 mentioned in the address. */
3023 if (reg_overlap_mentioned_p (dest1, word1))
3026 emit_insn (gen_movdf (dest2, word1));
3027 emit_insn (gen_movdf (dest1, word0));
3031 emit_insn (gen_movdf (dest1, word0));
3032 emit_insn (gen_movdf (dest2, word1));
3038 [(set (match_operand:TF 0 "memory_operand" "")
3039 (match_operand:TF 1 "register_operand" ""))]
3041 && offsettable_memref_p (operands[0])
3043 || ! TARGET_HARD_QUAD
3044 || ! fp_register_operand (operands[1], TFmode)))"
3045 [(clobber (const_int 0))]
3047 rtx set_src = operands[1];
3049 emit_insn (gen_movdf (adjust_address (operands[0], DFmode, 0),
3050 gen_df_reg (set_src, 0)));
3051 emit_insn (gen_movdf (adjust_address (operands[0], DFmode, 8),
3052 gen_df_reg (set_src, 1)));
3057 ;; SPARC-V9 conditional move instructions
3059 ;; We can handle larger constants here for some flavors, but for now we keep
3060 ;; it simple and only allow those constants supported by all flavors.
3061 ;; Note that emit_conditional_move canonicalizes operands 2,3 so that operand
3062 ;; 3 contains the constant if one is present, but we handle either for
3063 ;; generality (sparc.c puts a constant in operand 2).
3065 (define_mode_iterator I [QI HI SI DI])
3067 (define_expand "mov<I:mode>cc"
3068 [(set (match_operand:I 0 "register_operand" "")
3069 (if_then_else:I (match_operand 1 "comparison_operator" "")
3070 (match_operand:I 2 "arith10_operand" "")
3071 (match_operand:I 3 "arith10_operand" "")))]
3072 "TARGET_V9 && !(<I:MODE>mode == DImode && TARGET_ARCH32)"
3074 enum rtx_code code = GET_CODE (operands[1]);
3076 if (GET_MODE (sparc_compare_op0) == DImode
3080 if (sparc_compare_op1 == const0_rtx
3081 && GET_CODE (sparc_compare_op0) == REG
3082 && GET_MODE (sparc_compare_op0) == DImode
3083 && v9_regcmp_p (code))
3084 operands[1] = gen_rtx_fmt_ee (code, DImode, sparc_compare_op0, const0_rtx);
3086 operands[1] = gen_compare_operator (code);
3089 (define_mode_iterator F [SF DF TF])
3091 (define_expand "mov<F:mode>cc"
3092 [(set (match_operand:F 0 "register_operand" "")
3093 (if_then_else:F (match_operand 1 "comparison_operator" "")
3094 (match_operand:F 2 "register_operand" "")
3095 (match_operand:F 3 "register_operand" "")))]
3096 "TARGET_V9 && TARGET_FPU"
3098 enum rtx_code code = GET_CODE (operands[1]);
3100 if (GET_MODE (sparc_compare_op0) == DImode
3104 if (sparc_compare_op1 == const0_rtx
3105 && GET_CODE (sparc_compare_op0) == REG
3106 && GET_MODE (sparc_compare_op0) == DImode
3107 && v9_regcmp_p (code))
3108 operands[1] = gen_rtx_fmt_ee (code, DImode, sparc_compare_op0, const0_rtx);
3110 operands[1] = gen_compare_operator (code);
3113 ;; Conditional move define_insns
3115 (define_insn "*mov<I:mode>_cc_v9"
3116 [(set (match_operand:I 0 "register_operand" "=r,r")
3117 (if_then_else:I (match_operator 1 "comparison_operator"
3118 [(match_operand 2 "icc_or_fcc_register_operand" "X,X")
3120 (match_operand:I 3 "arith11_operand" "rL,0")
3121 (match_operand:I 4 "arith11_operand" "0,rL")))]
3122 "TARGET_V9 && !(<I:MODE>mode == DImode && TARGET_ARCH32)"
3125 mov%c1\t%x2, %4, %0"
3126 [(set_attr "type" "cmove")])
3128 (define_insn "*mov<I:mode>_cc_reg_sp64"
3129 [(set (match_operand:I 0 "register_operand" "=r,r")
3130 (if_then_else:I (match_operator 1 "v9_register_compare_operator"
3131 [(match_operand:DI 2 "register_operand" "r,r")
3133 (match_operand:I 3 "arith10_operand" "rM,0")
3134 (match_operand:I 4 "arith10_operand" "0,rM")))]
3137 movr%D1\t%2, %r3, %0
3138 movr%d1\t%2, %r4, %0"
3139 [(set_attr "type" "cmove")])
3141 (define_insn "*movsf_cc_v9"
3142 [(set (match_operand:SF 0 "register_operand" "=f,f")
3143 (if_then_else:SF (match_operator 1 "comparison_operator"
3144 [(match_operand 2 "icc_or_fcc_register_operand" "X,X")
3146 (match_operand:SF 3 "register_operand" "f,0")
3147 (match_operand:SF 4 "register_operand" "0,f")))]
3148 "TARGET_V9 && TARGET_FPU"
3150 fmovs%C1\t%x2, %3, %0
3151 fmovs%c1\t%x2, %4, %0"
3152 [(set_attr "type" "fpcmove")])
3154 (define_insn "*movsf_cc_reg_sp64"
3155 [(set (match_operand:SF 0 "register_operand" "=f,f")
3156 (if_then_else:SF (match_operator 1 "v9_register_compare_operator"
3157 [(match_operand:DI 2 "register_operand" "r,r")
3159 (match_operand:SF 3 "register_operand" "f,0")
3160 (match_operand:SF 4 "register_operand" "0,f")))]
3161 "TARGET_ARCH64 && TARGET_FPU"
3163 fmovrs%D1\t%2, %3, %0
3164 fmovrs%d1\t%2, %4, %0"
3165 [(set_attr "type" "fpcrmove")])
3167 ;; Named because invoked by movtf_cc_v9
3168 (define_insn "movdf_cc_v9"
3169 [(set (match_operand:DF 0 "register_operand" "=e,e")
3170 (if_then_else:DF (match_operator 1 "comparison_operator"
3171 [(match_operand 2 "icc_or_fcc_register_operand" "X,X")
3173 (match_operand:DF 3 "register_operand" "e,0")
3174 (match_operand:DF 4 "register_operand" "0,e")))]
3175 "TARGET_V9 && TARGET_FPU"
3177 fmovd%C1\t%x2, %3, %0
3178 fmovd%c1\t%x2, %4, %0"
3179 [(set_attr "type" "fpcmove")
3180 (set_attr "fptype" "double")])
3182 ;; Named because invoked by movtf_cc_reg_sp64
3183 (define_insn "movdf_cc_reg_sp64"
3184 [(set (match_operand:DF 0 "register_operand" "=e,e")
3185 (if_then_else:DF (match_operator 1 "v9_register_compare_operator"
3186 [(match_operand:DI 2 "register_operand" "r,r")
3188 (match_operand:DF 3 "register_operand" "e,0")
3189 (match_operand:DF 4 "register_operand" "0,e")))]
3190 "TARGET_ARCH64 && TARGET_FPU"
3192 fmovrd%D1\t%2, %3, %0
3193 fmovrd%d1\t%2, %4, %0"
3194 [(set_attr "type" "fpcrmove")
3195 (set_attr "fptype" "double")])
3197 (define_insn "*movtf_cc_hq_v9"
3198 [(set (match_operand:TF 0 "register_operand" "=e,e")
3199 (if_then_else:TF (match_operator 1 "comparison_operator"
3200 [(match_operand 2 "icc_or_fcc_register_operand" "X,X")
3202 (match_operand:TF 3 "register_operand" "e,0")
3203 (match_operand:TF 4 "register_operand" "0,e")))]
3204 "TARGET_V9 && TARGET_FPU && TARGET_HARD_QUAD"
3206 fmovq%C1\t%x2, %3, %0
3207 fmovq%c1\t%x2, %4, %0"
3208 [(set_attr "type" "fpcmove")])
3210 (define_insn "*movtf_cc_reg_hq_sp64"
3211 [(set (match_operand:TF 0 "register_operand" "=e,e")
3212 (if_then_else:TF (match_operator 1 "v9_register_compare_operator"
3213 [(match_operand:DI 2 "register_operand" "r,r")
3215 (match_operand:TF 3 "register_operand" "e,0")
3216 (match_operand:TF 4 "register_operand" "0,e")))]
3217 "TARGET_ARCH64 && TARGET_FPU && TARGET_HARD_QUAD"
3219 fmovrq%D1\t%2, %3, %0
3220 fmovrq%d1\t%2, %4, %0"
3221 [(set_attr "type" "fpcrmove")])
3223 (define_insn_and_split "*movtf_cc_v9"
3224 [(set (match_operand:TF 0 "register_operand" "=e,e")
3225 (if_then_else:TF (match_operator 1 "comparison_operator"
3226 [(match_operand 2 "icc_or_fcc_register_operand" "X,X")
3228 (match_operand:TF 3 "register_operand" "e,0")
3229 (match_operand:TF 4 "register_operand" "0,e")))]
3230 "TARGET_V9 && TARGET_FPU && !TARGET_HARD_QUAD"
3232 "&& reload_completed"
3233 [(clobber (const_int 0))]
3235 rtx set_dest = operands[0];
3236 rtx set_srca = operands[3];
3237 rtx set_srcb = operands[4];
3238 int third = rtx_equal_p (set_dest, set_srca);
3240 rtx srca1, srca2, srcb1, srcb2;
3242 dest1 = gen_df_reg (set_dest, 0);
3243 dest2 = gen_df_reg (set_dest, 1);
3244 srca1 = gen_df_reg (set_srca, 0);
3245 srca2 = gen_df_reg (set_srca, 1);
3246 srcb1 = gen_df_reg (set_srcb, 0);
3247 srcb2 = gen_df_reg (set_srcb, 1);
3249 /* Now emit using the real source and destination we found, swapping
3250 the order if we detect overlap. */
3251 if ((third && reg_overlap_mentioned_p (dest1, srcb2))
3252 || (!third && reg_overlap_mentioned_p (dest1, srca2)))
3254 emit_insn (gen_movdf_cc_v9 (dest2, operands[1], operands[2], srca2, srcb2));
3255 emit_insn (gen_movdf_cc_v9 (dest1, operands[1], operands[2], srca1, srcb1));
3259 emit_insn (gen_movdf_cc_v9 (dest1, operands[1], operands[2], srca1, srcb1));
3260 emit_insn (gen_movdf_cc_v9 (dest2, operands[1], operands[2], srca2, srcb2));
3264 [(set_attr "length" "2")])
3266 (define_insn_and_split "*movtf_cc_reg_sp64"
3267 [(set (match_operand:TF 0 "register_operand" "=e,e")
3268 (if_then_else:TF (match_operator 1 "v9_register_compare_operator"
3269 [(match_operand:DI 2 "register_operand" "r,r")
3271 (match_operand:TF 3 "register_operand" "e,0")
3272 (match_operand:TF 4 "register_operand" "0,e")))]
3273 "TARGET_ARCH64 && TARGET_FPU && ! TARGET_HARD_QUAD"
3275 "&& reload_completed"
3276 [(clobber (const_int 0))]
3278 rtx set_dest = operands[0];
3279 rtx set_srca = operands[3];
3280 rtx set_srcb = operands[4];
3281 int third = rtx_equal_p (set_dest, set_srca);
3283 rtx srca1, srca2, srcb1, srcb2;
3285 dest1 = gen_df_reg (set_dest, 0);
3286 dest2 = gen_df_reg (set_dest, 1);
3287 srca1 = gen_df_reg (set_srca, 0);
3288 srca2 = gen_df_reg (set_srca, 1);
3289 srcb1 = gen_df_reg (set_srcb, 0);
3290 srcb2 = gen_df_reg (set_srcb, 1);
3292 /* Now emit using the real source and destination we found, swapping
3293 the order if we detect overlap. */
3294 if ((third && reg_overlap_mentioned_p (dest1, srcb2))
3295 || (!third && reg_overlap_mentioned_p (dest1, srca2)))
3297 emit_insn (gen_movdf_cc_reg_sp64 (dest2, operands[1], operands[2], srca2, srcb2));
3298 emit_insn (gen_movdf_cc_reg_sp64 (dest1, operands[1], operands[2], srca1, srcb1));
3302 emit_insn (gen_movdf_cc_reg_sp64 (dest1, operands[1], operands[2], srca1, srcb1));
3303 emit_insn (gen_movdf_cc_reg_sp64 (dest2, operands[1], operands[2], srca2, srcb2));
3307 [(set_attr "length" "2")])
3310 ;; Zero-extension instructions
3312 ;; These patterns originally accepted general_operands, however, slightly
3313 ;; better code is generated by only accepting register_operands, and then
3314 ;; letting combine generate the ldu[hb] insns.
3316 (define_expand "zero_extendhisi2"
3317 [(set (match_operand:SI 0 "register_operand" "")
3318 (zero_extend:SI (match_operand:HI 1 "register_operand" "")))]
3321 rtx temp = gen_reg_rtx (SImode);
3322 rtx shift_16 = GEN_INT (16);
3323 int op1_subbyte = 0;
3325 if (GET_CODE (operand1) == SUBREG)
3327 op1_subbyte = SUBREG_BYTE (operand1);
3328 op1_subbyte /= GET_MODE_SIZE (SImode);
3329 op1_subbyte *= GET_MODE_SIZE (SImode);
3330 operand1 = XEXP (operand1, 0);
3333 emit_insn (gen_ashlsi3 (temp, gen_rtx_SUBREG (SImode, operand1, op1_subbyte),
3335 emit_insn (gen_lshrsi3 (operand0, temp, shift_16));
3339 (define_insn "*zero_extendhisi2_insn"
3340 [(set (match_operand:SI 0 "register_operand" "=r")
3341 (zero_extend:SI (match_operand:HI 1 "memory_operand" "m")))]
3344 [(set_attr "type" "load")
3345 (set_attr "us3load_type" "3cycle")])
3347 (define_expand "zero_extendqihi2"
3348 [(set (match_operand:HI 0 "register_operand" "")
3349 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))]
3353 (define_insn "*zero_extendqihi2_insn"
3354 [(set (match_operand:HI 0 "register_operand" "=r,r")
3355 (zero_extend:HI (match_operand:QI 1 "input_operand" "r,m")))]
3356 "GET_CODE (operands[1]) != CONST_INT"
3360 [(set_attr "type" "*,load")
3361 (set_attr "us3load_type" "*,3cycle")])
3363 (define_expand "zero_extendqisi2"
3364 [(set (match_operand:SI 0 "register_operand" "")
3365 (zero_extend:SI (match_operand:QI 1 "register_operand" "")))]
3369 (define_insn "*zero_extendqisi2_insn"
3370 [(set (match_operand:SI 0 "register_operand" "=r,r")
3371 (zero_extend:SI (match_operand:QI 1 "input_operand" "r,m")))]
3372 "GET_CODE (operands[1]) != CONST_INT"
3376 [(set_attr "type" "*,load")
3377 (set_attr "us3load_type" "*,3cycle")])
3379 (define_expand "zero_extendqidi2"
3380 [(set (match_operand:DI 0 "register_operand" "")
3381 (zero_extend:DI (match_operand:QI 1 "register_operand" "")))]
3385 (define_insn "*zero_extendqidi2_insn"
3386 [(set (match_operand:DI 0 "register_operand" "=r,r")
3387 (zero_extend:DI (match_operand:QI 1 "input_operand" "r,m")))]
3388 "TARGET_ARCH64 && GET_CODE (operands[1]) != CONST_INT"
3392 [(set_attr "type" "*,load")
3393 (set_attr "us3load_type" "*,3cycle")])
3395 (define_expand "zero_extendhidi2"
3396 [(set (match_operand:DI 0 "register_operand" "")
3397 (zero_extend:DI (match_operand:HI 1 "register_operand" "")))]
3400 rtx temp = gen_reg_rtx (DImode);
3401 rtx shift_48 = GEN_INT (48);
3402 int op1_subbyte = 0;
3404 if (GET_CODE (operand1) == SUBREG)
3406 op1_subbyte = SUBREG_BYTE (operand1);
3407 op1_subbyte /= GET_MODE_SIZE (DImode);
3408 op1_subbyte *= GET_MODE_SIZE (DImode);
3409 operand1 = XEXP (operand1, 0);
3412 emit_insn (gen_ashldi3 (temp, gen_rtx_SUBREG (DImode, operand1, op1_subbyte),
3414 emit_insn (gen_lshrdi3 (operand0, temp, shift_48));
3418 (define_insn "*zero_extendhidi2_insn"
3419 [(set (match_operand:DI 0 "register_operand" "=r")
3420 (zero_extend:DI (match_operand:HI 1 "memory_operand" "m")))]
3423 [(set_attr "type" "load")
3424 (set_attr "us3load_type" "3cycle")])
3426 ;; ??? Write truncdisi pattern using sra?
3428 (define_expand "zero_extendsidi2"
3429 [(set (match_operand:DI 0 "register_operand" "")
3430 (zero_extend:DI (match_operand:SI 1 "register_operand" "")))]
3434 (define_insn "*zero_extendsidi2_insn_sp64"
3435 [(set (match_operand:DI 0 "register_operand" "=r,r")
3436 (zero_extend:DI (match_operand:SI 1 "input_operand" "r,m")))]
3437 "TARGET_ARCH64 && GET_CODE (operands[1]) != CONST_INT"
3441 [(set_attr "type" "shift,load")])
3443 (define_insn_and_split "*zero_extendsidi2_insn_sp32"
3444 [(set (match_operand:DI 0 "register_operand" "=r")
3445 (zero_extend:DI (match_operand:SI 1 "register_operand" "r")))]
3448 "&& reload_completed"
3449 [(set (match_dup 2) (match_dup 3))
3450 (set (match_dup 4) (match_dup 5))]
3454 dest1 = gen_highpart (SImode, operands[0]);
3455 dest2 = gen_lowpart (SImode, operands[0]);
3457 /* Swap the order in case of overlap. */
3458 if (REGNO (dest1) == REGNO (operands[1]))
3460 operands[2] = dest2;
3461 operands[3] = operands[1];
3462 operands[4] = dest1;
3463 operands[5] = const0_rtx;
3467 operands[2] = dest1;
3468 operands[3] = const0_rtx;
3469 operands[4] = dest2;
3470 operands[5] = operands[1];
3473 [(set_attr "length" "2")])
3475 ;; Simplify comparisons of extended values.
3477 (define_insn "*cmp_zero_extendqisi2"
3479 (compare:CC (zero_extend:SI (match_operand:QI 0 "register_operand" "r"))
3482 "andcc\t%0, 0xff, %%g0"
3483 [(set_attr "type" "compare")])
3485 (define_insn "*cmp_zero_qi"
3487 (compare:CC (match_operand:QI 0 "register_operand" "r")
3490 "andcc\t%0, 0xff, %%g0"
3491 [(set_attr "type" "compare")])
3493 (define_insn "*cmp_zero_extendqisi2_set"
3495 (compare:CC (zero_extend:SI (match_operand:QI 1 "register_operand" "r"))
3497 (set (match_operand:SI 0 "register_operand" "=r")
3498 (zero_extend:SI (match_dup 1)))]
3500 "andcc\t%1, 0xff, %0"
3501 [(set_attr "type" "compare")])
3503 (define_insn "*cmp_zero_extendqisi2_andcc_set"
3505 (compare:CC (and:SI (match_operand:SI 1 "register_operand" "r")
3508 (set (match_operand:SI 0 "register_operand" "=r")
3509 (zero_extend:SI (subreg:QI (match_dup 1) 0)))]
3511 "andcc\t%1, 0xff, %0"
3512 [(set_attr "type" "compare")])
3514 (define_insn "*cmp_zero_extendqidi2"
3516 (compare:CCX (zero_extend:DI (match_operand:QI 0 "register_operand" "r"))
3519 "andcc\t%0, 0xff, %%g0"
3520 [(set_attr "type" "compare")])
3522 (define_insn "*cmp_zero_qi_sp64"
3524 (compare:CCX (match_operand:QI 0 "register_operand" "r")
3527 "andcc\t%0, 0xff, %%g0"
3528 [(set_attr "type" "compare")])
3530 (define_insn "*cmp_zero_extendqidi2_set"
3532 (compare:CCX (zero_extend:DI (match_operand:QI 1 "register_operand" "r"))
3534 (set (match_operand:DI 0 "register_operand" "=r")
3535 (zero_extend:DI (match_dup 1)))]
3537 "andcc\t%1, 0xff, %0"
3538 [(set_attr "type" "compare")])
3540 (define_insn "*cmp_zero_extendqidi2_andcc_set"
3542 (compare:CCX (and:DI (match_operand:DI 1 "register_operand" "r")
3545 (set (match_operand:DI 0 "register_operand" "=r")
3546 (zero_extend:DI (subreg:QI (match_dup 1) 0)))]
3548 "andcc\t%1, 0xff, %0"
3549 [(set_attr "type" "compare")])
3551 ;; Similarly, handle {SI,DI}->QI mode truncation followed by a compare.
3553 (define_insn "*cmp_siqi_trunc"
3555 (compare:CC (subreg:QI (match_operand:SI 0 "register_operand" "r") 3)
3558 "andcc\t%0, 0xff, %%g0"
3559 [(set_attr "type" "compare")])
3561 (define_insn "*cmp_siqi_trunc_set"
3563 (compare:CC (subreg:QI (match_operand:SI 1 "register_operand" "r") 3)
3565 (set (match_operand:QI 0 "register_operand" "=r")
3566 (subreg:QI (match_dup 1) 3))]
3568 "andcc\t%1, 0xff, %0"
3569 [(set_attr "type" "compare")])
3571 (define_insn "*cmp_diqi_trunc"
3573 (compare:CC (subreg:QI (match_operand:DI 0 "register_operand" "r") 7)
3576 "andcc\t%0, 0xff, %%g0"
3577 [(set_attr "type" "compare")])
3579 (define_insn "*cmp_diqi_trunc_set"
3581 (compare:CC (subreg:QI (match_operand:DI 1 "register_operand" "r") 7)
3583 (set (match_operand:QI 0 "register_operand" "=r")
3584 (subreg:QI (match_dup 1) 7))]
3586 "andcc\t%1, 0xff, %0"
3587 [(set_attr "type" "compare")])
3590 ;; Sign-extension instructions
3592 ;; These patterns originally accepted general_operands, however, slightly
3593 ;; better code is generated by only accepting register_operands, and then
3594 ;; letting combine generate the lds[hb] insns.
3596 (define_expand "extendhisi2"
3597 [(set (match_operand:SI 0 "register_operand" "")
3598 (sign_extend:SI (match_operand:HI 1 "register_operand" "")))]
3601 rtx temp = gen_reg_rtx (SImode);
3602 rtx shift_16 = GEN_INT (16);
3603 int op1_subbyte = 0;
3605 if (GET_CODE (operand1) == SUBREG)
3607 op1_subbyte = SUBREG_BYTE (operand1);
3608 op1_subbyte /= GET_MODE_SIZE (SImode);
3609 op1_subbyte *= GET_MODE_SIZE (SImode);
3610 operand1 = XEXP (operand1, 0);
3613 emit_insn (gen_ashlsi3 (temp, gen_rtx_SUBREG (SImode, operand1, op1_subbyte),
3615 emit_insn (gen_ashrsi3 (operand0, temp, shift_16));
3619 (define_insn "*sign_extendhisi2_insn"
3620 [(set (match_operand:SI 0 "register_operand" "=r")
3621 (sign_extend:SI (match_operand:HI 1 "memory_operand" "m")))]
3624 [(set_attr "type" "sload")
3625 (set_attr "us3load_type" "3cycle")])
3627 (define_expand "extendqihi2"
3628 [(set (match_operand:HI 0 "register_operand" "")
3629 (sign_extend:HI (match_operand:QI 1 "register_operand" "")))]
3632 rtx temp = gen_reg_rtx (SImode);
3633 rtx shift_24 = GEN_INT (24);
3634 int op1_subbyte = 0;
3635 int op0_subbyte = 0;
3637 if (GET_CODE (operand1) == SUBREG)
3639 op1_subbyte = SUBREG_BYTE (operand1);
3640 op1_subbyte /= GET_MODE_SIZE (SImode);
3641 op1_subbyte *= GET_MODE_SIZE (SImode);
3642 operand1 = XEXP (operand1, 0);
3644 if (GET_CODE (operand0) == SUBREG)
3646 op0_subbyte = SUBREG_BYTE (operand0);
3647 op0_subbyte /= GET_MODE_SIZE (SImode);
3648 op0_subbyte *= GET_MODE_SIZE (SImode);
3649 operand0 = XEXP (operand0, 0);
3651 emit_insn (gen_ashlsi3 (temp, gen_rtx_SUBREG (SImode, operand1, op1_subbyte),
3653 if (GET_MODE (operand0) != SImode)
3654 operand0 = gen_rtx_SUBREG (SImode, operand0, op0_subbyte);
3655 emit_insn (gen_ashrsi3 (operand0, temp, shift_24));
3659 (define_insn "*sign_extendqihi2_insn"
3660 [(set (match_operand:HI 0 "register_operand" "=r")
3661 (sign_extend:HI (match_operand:QI 1 "memory_operand" "m")))]
3664 [(set_attr "type" "sload")
3665 (set_attr "us3load_type" "3cycle")])
3667 (define_expand "extendqisi2"
3668 [(set (match_operand:SI 0 "register_operand" "")
3669 (sign_extend:SI (match_operand:QI 1 "register_operand" "")))]
3672 rtx temp = gen_reg_rtx (SImode);
3673 rtx shift_24 = GEN_INT (24);
3674 int op1_subbyte = 0;
3676 if (GET_CODE (operand1) == SUBREG)
3678 op1_subbyte = SUBREG_BYTE (operand1);
3679 op1_subbyte /= GET_MODE_SIZE (SImode);
3680 op1_subbyte *= GET_MODE_SIZE (SImode);
3681 operand1 = XEXP (operand1, 0);
3684 emit_insn (gen_ashlsi3 (temp, gen_rtx_SUBREG (SImode, operand1, op1_subbyte),
3686 emit_insn (gen_ashrsi3 (operand0, temp, shift_24));
3690 (define_insn "*sign_extendqisi2_insn"
3691 [(set (match_operand:SI 0 "register_operand" "=r")
3692 (sign_extend:SI (match_operand:QI 1 "memory_operand" "m")))]
3695 [(set_attr "type" "sload")
3696 (set_attr "us3load_type" "3cycle")])
3698 (define_expand "extendqidi2"
3699 [(set (match_operand:DI 0 "register_operand" "")
3700 (sign_extend:DI (match_operand:QI 1 "register_operand" "")))]
3703 rtx temp = gen_reg_rtx (DImode);
3704 rtx shift_56 = GEN_INT (56);
3705 int op1_subbyte = 0;
3707 if (GET_CODE (operand1) == SUBREG)
3709 op1_subbyte = SUBREG_BYTE (operand1);
3710 op1_subbyte /= GET_MODE_SIZE (DImode);
3711 op1_subbyte *= GET_MODE_SIZE (DImode);
3712 operand1 = XEXP (operand1, 0);
3715 emit_insn (gen_ashldi3 (temp, gen_rtx_SUBREG (DImode, operand1, op1_subbyte),
3717 emit_insn (gen_ashrdi3 (operand0, temp, shift_56));
3721 (define_insn "*sign_extendqidi2_insn"
3722 [(set (match_operand:DI 0 "register_operand" "=r")
3723 (sign_extend:DI (match_operand:QI 1 "memory_operand" "m")))]
3726 [(set_attr "type" "sload")
3727 (set_attr "us3load_type" "3cycle")])
3729 (define_expand "extendhidi2"
3730 [(set (match_operand:DI 0 "register_operand" "")
3731 (sign_extend:DI (match_operand:HI 1 "register_operand" "")))]
3734 rtx temp = gen_reg_rtx (DImode);
3735 rtx shift_48 = GEN_INT (48);
3736 int op1_subbyte = 0;
3738 if (GET_CODE (operand1) == SUBREG)
3740 op1_subbyte = SUBREG_BYTE (operand1);
3741 op1_subbyte /= GET_MODE_SIZE (DImode);
3742 op1_subbyte *= GET_MODE_SIZE (DImode);
3743 operand1 = XEXP (operand1, 0);
3746 emit_insn (gen_ashldi3 (temp, gen_rtx_SUBREG (DImode, operand1, op1_subbyte),
3748 emit_insn (gen_ashrdi3 (operand0, temp, shift_48));
3752 (define_insn "*sign_extendhidi2_insn"
3753 [(set (match_operand:DI 0 "register_operand" "=r")
3754 (sign_extend:DI (match_operand:HI 1 "memory_operand" "m")))]
3757 [(set_attr "type" "sload")
3758 (set_attr "us3load_type" "3cycle")])
3760 (define_expand "extendsidi2"
3761 [(set (match_operand:DI 0 "register_operand" "")
3762 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))]
3766 (define_insn "*sign_extendsidi2_insn"
3767 [(set (match_operand:DI 0 "register_operand" "=r,r")
3768 (sign_extend:DI (match_operand:SI 1 "input_operand" "r,m")))]
3773 [(set_attr "type" "shift,sload")
3774 (set_attr "us3load_type" "*,3cycle")])
3777 ;; Special pattern for optimizing bit-field compares. This is needed
3778 ;; because combine uses this as a canonical form.
3780 (define_insn "*cmp_zero_extract"
3783 (zero_extract:SI (match_operand:SI 0 "register_operand" "r")
3784 (match_operand:SI 1 "small_int_operand" "I")
3785 (match_operand:SI 2 "small_int_operand" "I"))
3787 "INTVAL (operands[2]) > 19"
3789 int len = INTVAL (operands[1]);
3790 int pos = 32 - INTVAL (operands[2]) - len;
3791 HOST_WIDE_INT mask = ((1 << len) - 1) << pos;
3792 operands[1] = GEN_INT (mask);
3793 return "andcc\t%0, %1, %%g0";
3795 [(set_attr "type" "compare")])
3797 (define_insn "*cmp_zero_extract_sp64"
3800 (zero_extract:DI (match_operand:DI 0 "register_operand" "r")
3801 (match_operand:SI 1 "small_int_operand" "I")
3802 (match_operand:SI 2 "small_int_operand" "I"))
3804 "TARGET_ARCH64 && INTVAL (operands[2]) > 51"
3806 int len = INTVAL (operands[1]);
3807 int pos = 64 - INTVAL (operands[2]) - len;
3808 HOST_WIDE_INT mask = (((unsigned HOST_WIDE_INT) 1 << len) - 1) << pos;
3809 operands[1] = GEN_INT (mask);
3810 return "andcc\t%0, %1, %%g0";
3812 [(set_attr "type" "compare")])
3815 ;; Conversions between float, double and long double.
3817 (define_insn "extendsfdf2"
3818 [(set (match_operand:DF 0 "register_operand" "=e")
3820 (match_operand:SF 1 "register_operand" "f")))]
3823 [(set_attr "type" "fp")
3824 (set_attr "fptype" "double")])
3826 (define_expand "extendsftf2"
3827 [(set (match_operand:TF 0 "nonimmediate_operand" "")
3829 (match_operand:SF 1 "register_operand" "")))]
3830 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
3831 "emit_tfmode_cvt (FLOAT_EXTEND, operands); DONE;")
3833 (define_insn "*extendsftf2_hq"
3834 [(set (match_operand:TF 0 "register_operand" "=e")
3836 (match_operand:SF 1 "register_operand" "f")))]
3837 "TARGET_FPU && TARGET_HARD_QUAD"
3839 [(set_attr "type" "fp")])
3841 (define_expand "extenddftf2"
3842 [(set (match_operand:TF 0 "nonimmediate_operand" "")
3844 (match_operand:DF 1 "register_operand" "")))]
3845 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
3846 "emit_tfmode_cvt (FLOAT_EXTEND, operands); DONE;")
3848 (define_insn "*extenddftf2_hq"
3849 [(set (match_operand:TF 0 "register_operand" "=e")
3851 (match_operand:DF 1 "register_operand" "e")))]
3852 "TARGET_FPU && TARGET_HARD_QUAD"
3854 [(set_attr "type" "fp")])
3856 (define_insn "truncdfsf2"
3857 [(set (match_operand:SF 0 "register_operand" "=f")
3859 (match_operand:DF 1 "register_operand" "e")))]
3862 [(set_attr "type" "fp")
3863 (set_attr "fptype" "double")])
3865 (define_expand "trunctfsf2"
3866 [(set (match_operand:SF 0 "register_operand" "")
3868 (match_operand:TF 1 "general_operand" "")))]
3869 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
3870 "emit_tfmode_cvt (FLOAT_TRUNCATE, operands); DONE;")
3872 (define_insn "*trunctfsf2_hq"
3873 [(set (match_operand:SF 0 "register_operand" "=f")
3875 (match_operand:TF 1 "register_operand" "e")))]
3876 "TARGET_FPU && TARGET_HARD_QUAD"
3878 [(set_attr "type" "fp")])
3880 (define_expand "trunctfdf2"
3881 [(set (match_operand:DF 0 "register_operand" "")
3883 (match_operand:TF 1 "general_operand" "")))]
3884 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
3885 "emit_tfmode_cvt (FLOAT_TRUNCATE, operands); DONE;")
3887 (define_insn "*trunctfdf2_hq"
3888 [(set (match_operand:DF 0 "register_operand" "=e")
3890 (match_operand:TF 1 "register_operand" "e")))]
3891 "TARGET_FPU && TARGET_HARD_QUAD"
3893 [(set_attr "type" "fp")])
3896 ;; Conversion between fixed point and floating point.
3898 (define_insn "floatsisf2"
3899 [(set (match_operand:SF 0 "register_operand" "=f")
3900 (float:SF (match_operand:SI 1 "register_operand" "f")))]
3903 [(set_attr "type" "fp")
3904 (set_attr "fptype" "double")])
3906 (define_insn "floatsidf2"
3907 [(set (match_operand:DF 0 "register_operand" "=e")
3908 (float:DF (match_operand:SI 1 "register_operand" "f")))]
3911 [(set_attr "type" "fp")
3912 (set_attr "fptype" "double")])
3914 (define_expand "floatsitf2"
3915 [(set (match_operand:TF 0 "nonimmediate_operand" "")
3916 (float:TF (match_operand:SI 1 "register_operand" "")))]
3917 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
3918 "emit_tfmode_cvt (FLOAT, operands); DONE;")
3920 (define_insn "*floatsitf2_hq"
3921 [(set (match_operand:TF 0 "register_operand" "=e")
3922 (float:TF (match_operand:SI 1 "register_operand" "f")))]
3923 "TARGET_FPU && TARGET_HARD_QUAD"
3925 [(set_attr "type" "fp")])
3927 (define_expand "floatunssitf2"
3928 [(set (match_operand:TF 0 "nonimmediate_operand" "")
3929 (unsigned_float:TF (match_operand:SI 1 "register_operand" "")))]
3930 "TARGET_FPU && TARGET_ARCH64 && ! TARGET_HARD_QUAD"
3931 "emit_tfmode_cvt (UNSIGNED_FLOAT, operands); DONE;")
3933 ;; Now the same for 64 bit sources.
3935 (define_insn "floatdisf2"
3936 [(set (match_operand:SF 0 "register_operand" "=f")
3937 (float:SF (match_operand:DI 1 "register_operand" "e")))]
3938 "TARGET_V9 && TARGET_FPU"
3940 [(set_attr "type" "fp")
3941 (set_attr "fptype" "double")])
3943 (define_expand "floatunsdisf2"
3944 [(use (match_operand:SF 0 "register_operand" ""))
3945 (use (match_operand:DI 1 "general_operand" ""))]
3946 "TARGET_ARCH64 && TARGET_FPU"
3947 "sparc_emit_floatunsdi (operands, SFmode); DONE;")
3949 (define_insn "floatdidf2"
3950 [(set (match_operand:DF 0 "register_operand" "=e")
3951 (float:DF (match_operand:DI 1 "register_operand" "e")))]
3952 "TARGET_V9 && TARGET_FPU"
3954 [(set_attr "type" "fp")
3955 (set_attr "fptype" "double")])
3957 (define_expand "floatunsdidf2"
3958 [(use (match_operand:DF 0 "register_operand" ""))
3959 (use (match_operand:DI 1 "general_operand" ""))]
3960 "TARGET_ARCH64 && TARGET_FPU"
3961 "sparc_emit_floatunsdi (operands, DFmode); DONE;")
3963 (define_expand "floatditf2"
3964 [(set (match_operand:TF 0 "nonimmediate_operand" "")
3965 (float:TF (match_operand:DI 1 "register_operand" "")))]
3966 "TARGET_FPU && TARGET_V9 && (TARGET_HARD_QUAD || TARGET_ARCH64)"
3967 "emit_tfmode_cvt (FLOAT, operands); DONE;")
3969 (define_insn "*floatditf2_hq"
3970 [(set (match_operand:TF 0 "register_operand" "=e")
3971 (float:TF (match_operand:DI 1 "register_operand" "e")))]
3972 "TARGET_V9 && TARGET_FPU && TARGET_HARD_QUAD"
3974 [(set_attr "type" "fp")])
3976 (define_expand "floatunsditf2"
3977 [(set (match_operand:TF 0 "nonimmediate_operand" "")
3978 (unsigned_float:TF (match_operand:DI 1 "register_operand" "")))]
3979 "TARGET_FPU && TARGET_ARCH64 && ! TARGET_HARD_QUAD"
3980 "emit_tfmode_cvt (UNSIGNED_FLOAT, operands); DONE;")
3982 ;; Convert a float to an actual integer.
3983 ;; Truncation is performed as part of the conversion.
3985 (define_insn "fix_truncsfsi2"
3986 [(set (match_operand:SI 0 "register_operand" "=f")
3987 (fix:SI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
3990 [(set_attr "type" "fp")
3991 (set_attr "fptype" "double")])
3993 (define_insn "fix_truncdfsi2"
3994 [(set (match_operand:SI 0 "register_operand" "=f")
3995 (fix:SI (fix:DF (match_operand:DF 1 "register_operand" "e"))))]
3998 [(set_attr "type" "fp")
3999 (set_attr "fptype" "double")])
4001 (define_expand "fix_trunctfsi2"
4002 [(set (match_operand:SI 0 "register_operand" "")
4003 (fix:SI (match_operand:TF 1 "general_operand" "")))]
4004 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
4005 "emit_tfmode_cvt (FIX, operands); DONE;")
4007 (define_insn "*fix_trunctfsi2_hq"
4008 [(set (match_operand:SI 0 "register_operand" "=f")
4009 (fix:SI (match_operand:TF 1 "register_operand" "e")))]
4010 "TARGET_FPU && TARGET_HARD_QUAD"
4012 [(set_attr "type" "fp")])
4014 (define_expand "fixuns_trunctfsi2"
4015 [(set (match_operand:SI 0 "register_operand" "")
4016 (unsigned_fix:SI (match_operand:TF 1 "general_operand" "")))]
4017 "TARGET_FPU && TARGET_ARCH64 && ! TARGET_HARD_QUAD"
4018 "emit_tfmode_cvt (UNSIGNED_FIX, operands); DONE;")
4020 ;; Now the same, for V9 targets
4022 (define_insn "fix_truncsfdi2"
4023 [(set (match_operand:DI 0 "register_operand" "=e")
4024 (fix:DI (fix:SF (match_operand:SF 1 "register_operand" "f"))))]
4025 "TARGET_V9 && TARGET_FPU"
4027 [(set_attr "type" "fp")
4028 (set_attr "fptype" "double")])
4030 (define_expand "fixuns_truncsfdi2"
4031 [(use (match_operand:DI 0 "register_operand" ""))
4032 (use (match_operand:SF 1 "general_operand" ""))]
4033 "TARGET_ARCH64 && TARGET_FPU"
4034 "sparc_emit_fixunsdi (operands, SFmode); DONE;")
4036 (define_insn "fix_truncdfdi2"
4037 [(set (match_operand:DI 0 "register_operand" "=e")
4038 (fix:DI (fix:DF (match_operand:DF 1 "register_operand" "e"))))]
4039 "TARGET_V9 && TARGET_FPU"
4041 [(set_attr "type" "fp")
4042 (set_attr "fptype" "double")])
4044 (define_expand "fixuns_truncdfdi2"
4045 [(use (match_operand:DI 0 "register_operand" ""))
4046 (use (match_operand:DF 1 "general_operand" ""))]
4047 "TARGET_ARCH64 && TARGET_FPU"
4048 "sparc_emit_fixunsdi (operands, DFmode); DONE;")
4050 (define_expand "fix_trunctfdi2"
4051 [(set (match_operand:DI 0 "register_operand" "")
4052 (fix:DI (match_operand:TF 1 "general_operand" "")))]
4053 "TARGET_V9 && TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
4054 "emit_tfmode_cvt (FIX, operands); DONE;")
4056 (define_insn "*fix_trunctfdi2_hq"
4057 [(set (match_operand:DI 0 "register_operand" "=e")
4058 (fix:DI (match_operand:TF 1 "register_operand" "e")))]
4059 "TARGET_V9 && TARGET_FPU && TARGET_HARD_QUAD"
4061 [(set_attr "type" "fp")])
4063 (define_expand "fixuns_trunctfdi2"
4064 [(set (match_operand:DI 0 "register_operand" "")
4065 (unsigned_fix:DI (match_operand:TF 1 "general_operand" "")))]
4066 "TARGET_FPU && TARGET_ARCH64 && ! TARGET_HARD_QUAD"
4067 "emit_tfmode_cvt (UNSIGNED_FIX, operands); DONE;")
4070 ;; Integer addition/subtraction instructions.
4072 (define_expand "adddi3"
4073 [(set (match_operand:DI 0 "register_operand" "")
4074 (plus:DI (match_operand:DI 1 "register_operand" "")
4075 (match_operand:DI 2 "arith_double_add_operand" "")))]
4078 if (! TARGET_ARCH64)
4080 emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2,
4081 gen_rtx_SET (VOIDmode, operands[0],
4082 gen_rtx_PLUS (DImode, operands[1],
4084 gen_rtx_CLOBBER (VOIDmode,
4085 gen_rtx_REG (CCmode, SPARC_ICC_REG)))));
4090 (define_insn_and_split "adddi3_insn_sp32"
4091 [(set (match_operand:DI 0 "register_operand" "=r")
4092 (plus:DI (match_operand:DI 1 "arith_double_operand" "%r")
4093 (match_operand:DI 2 "arith_double_operand" "rHI")))
4094 (clobber (reg:CC 100))]
4097 "&& reload_completed"
4098 [(parallel [(set (reg:CC_NOOV 100)
4099 (compare:CC_NOOV (plus:SI (match_dup 4)
4103 (plus:SI (match_dup 4) (match_dup 5)))])
4105 (plus:SI (plus:SI (match_dup 7)
4107 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))]
4109 operands[3] = gen_lowpart (SImode, operands[0]);
4110 operands[4] = gen_lowpart (SImode, operands[1]);
4111 operands[5] = gen_lowpart (SImode, operands[2]);
4112 operands[6] = gen_highpart (SImode, operands[0]);
4113 operands[7] = gen_highpart_mode (SImode, DImode, operands[1]);
4114 #if HOST_BITS_PER_WIDE_INT == 32
4115 if (GET_CODE (operands[2]) == CONST_INT)
4117 if (INTVAL (operands[2]) < 0)
4118 operands[8] = constm1_rtx;
4120 operands[8] = const0_rtx;
4124 operands[8] = gen_highpart_mode (SImode, DImode, operands[2]);
4126 [(set_attr "length" "2")])
4128 ;; LTU here means "carry set"
4130 [(set (match_operand:SI 0 "register_operand" "=r")
4131 (plus:SI (plus:SI (match_operand:SI 1 "arith_operand" "%r")
4132 (match_operand:SI 2 "arith_operand" "rI"))
4133 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))]
4136 [(set_attr "type" "ialuX")])
4138 (define_insn_and_split "*addx_extend_sp32"
4139 [(set (match_operand:DI 0 "register_operand" "=r")
4140 (zero_extend:DI (plus:SI (plus:SI
4141 (match_operand:SI 1 "register_or_zero_operand" "%rJ")
4142 (match_operand:SI 2 "arith_operand" "rI"))
4143 (ltu:SI (reg:CC_NOOV 100) (const_int 0)))))]
4146 "&& reload_completed"
4147 [(set (match_dup 3) (plus:SI (plus:SI (match_dup 1) (match_dup 2))
4148 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))
4149 (set (match_dup 4) (const_int 0))]
4150 "operands[3] = gen_lowpart (SImode, operands[0]);
4151 operands[4] = gen_highpart_mode (SImode, DImode, operands[1]);"
4152 [(set_attr "length" "2")])
4154 (define_insn "*addx_extend_sp64"
4155 [(set (match_operand:DI 0 "register_operand" "=r")
4156 (zero_extend:DI (plus:SI (plus:SI (match_operand:SI 1 "register_or_zero_operand" "%rJ")
4157 (match_operand:SI 2 "arith_operand" "rI"))
4158 (ltu:SI (reg:CC_NOOV 100) (const_int 0)))))]
4161 [(set_attr "type" "ialuX")])
4163 (define_insn_and_split ""
4164 [(set (match_operand:DI 0 "register_operand" "=r")
4165 (plus:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
4166 (match_operand:DI 2 "register_operand" "r")))
4167 (clobber (reg:CC 100))]
4170 "&& reload_completed"
4171 [(parallel [(set (reg:CC_NOOV 100)
4172 (compare:CC_NOOV (plus:SI (match_dup 3) (match_dup 1))
4174 (set (match_dup 5) (plus:SI (match_dup 3) (match_dup 1)))])
4176 (plus:SI (plus:SI (match_dup 4) (const_int 0))
4177 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))]
4178 "operands[3] = gen_lowpart (SImode, operands[2]);
4179 operands[4] = gen_highpart (SImode, operands[2]);
4180 operands[5] = gen_lowpart (SImode, operands[0]);
4181 operands[6] = gen_highpart (SImode, operands[0]);"
4182 [(set_attr "length" "2")])
4184 (define_insn "*adddi3_sp64"
4185 [(set (match_operand:DI 0 "register_operand" "=r,r")
4186 (plus:DI (match_operand:DI 1 "register_operand" "%r,r")
4187 (match_operand:DI 2 "arith_add_operand" "rI,O")))]
4193 (define_insn "addsi3"
4194 [(set (match_operand:SI 0 "register_operand" "=r,r,d")
4195 (plus:SI (match_operand:SI 1 "register_operand" "%r,r,d")
4196 (match_operand:SI 2 "arith_add_operand" "rI,O,d")))]
4201 fpadd32s\t%1, %2, %0"
4202 [(set_attr "type" "*,*,fga")
4203 (set_attr "fptype" "*,*,single")])
4205 (define_insn "*cmp_cc_plus"
4206 [(set (reg:CC_NOOV 100)
4207 (compare:CC_NOOV (plus:SI (match_operand:SI 0 "arith_operand" "%r")
4208 (match_operand:SI 1 "arith_operand" "rI"))
4211 "addcc\t%0, %1, %%g0"
4212 [(set_attr "type" "compare")])
4214 (define_insn "*cmp_ccx_plus"
4215 [(set (reg:CCX_NOOV 100)
4216 (compare:CCX_NOOV (plus:DI (match_operand:DI 0 "arith_operand" "%r")
4217 (match_operand:DI 1 "arith_operand" "rI"))
4220 "addcc\t%0, %1, %%g0"
4221 [(set_attr "type" "compare")])
4223 (define_insn "*cmp_cc_plus_set"
4224 [(set (reg:CC_NOOV 100)
4225 (compare:CC_NOOV (plus:SI (match_operand:SI 1 "arith_operand" "%r")
4226 (match_operand:SI 2 "arith_operand" "rI"))
4228 (set (match_operand:SI 0 "register_operand" "=r")
4229 (plus:SI (match_dup 1) (match_dup 2)))]
4232 [(set_attr "type" "compare")])
4234 (define_insn "*cmp_ccx_plus_set"
4235 [(set (reg:CCX_NOOV 100)
4236 (compare:CCX_NOOV (plus:DI (match_operand:DI 1 "arith_operand" "%r")
4237 (match_operand:DI 2 "arith_operand" "rI"))
4239 (set (match_operand:DI 0 "register_operand" "=r")
4240 (plus:DI (match_dup 1) (match_dup 2)))]
4243 [(set_attr "type" "compare")])
4245 (define_expand "subdi3"
4246 [(set (match_operand:DI 0 "register_operand" "")
4247 (minus:DI (match_operand:DI 1 "register_operand" "")
4248 (match_operand:DI 2 "arith_double_add_operand" "")))]
4251 if (! TARGET_ARCH64)
4253 emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2,
4254 gen_rtx_SET (VOIDmode, operands[0],
4255 gen_rtx_MINUS (DImode, operands[1],
4257 gen_rtx_CLOBBER (VOIDmode,
4258 gen_rtx_REG (CCmode, SPARC_ICC_REG)))));
4263 (define_insn_and_split "subdi3_insn_sp32"
4264 [(set (match_operand:DI 0 "register_operand" "=r")
4265 (minus:DI (match_operand:DI 1 "register_operand" "r")
4266 (match_operand:DI 2 "arith_double_operand" "rHI")))
4267 (clobber (reg:CC 100))]
4270 "&& reload_completed"
4271 [(parallel [(set (reg:CC_NOOV 100)
4272 (compare:CC_NOOV (minus:SI (match_dup 4)
4276 (minus:SI (match_dup 4) (match_dup 5)))])
4278 (minus:SI (minus:SI (match_dup 7)
4280 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))]
4282 operands[3] = gen_lowpart (SImode, operands[0]);
4283 operands[4] = gen_lowpart (SImode, operands[1]);
4284 operands[5] = gen_lowpart (SImode, operands[2]);
4285 operands[6] = gen_highpart (SImode, operands[0]);
4286 operands[7] = gen_highpart (SImode, operands[1]);
4287 #if HOST_BITS_PER_WIDE_INT == 32
4288 if (GET_CODE (operands[2]) == CONST_INT)
4290 if (INTVAL (operands[2]) < 0)
4291 operands[8] = constm1_rtx;
4293 operands[8] = const0_rtx;
4297 operands[8] = gen_highpart_mode (SImode, DImode, operands[2]);
4299 [(set_attr "length" "2")])
4301 ;; LTU here means "carry set"
4303 [(set (match_operand:SI 0 "register_operand" "=r")
4304 (minus:SI (minus:SI (match_operand:SI 1 "register_or_zero_operand" "rJ")
4305 (match_operand:SI 2 "arith_operand" "rI"))
4306 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))]
4309 [(set_attr "type" "ialuX")])
4311 (define_insn "*subx_extend_sp64"
4312 [(set (match_operand:DI 0 "register_operand" "=r")
4313 (zero_extend:DI (minus:SI (minus:SI (match_operand:SI 1 "register_or_zero_operand" "rJ")
4314 (match_operand:SI 2 "arith_operand" "rI"))
4315 (ltu:SI (reg:CC_NOOV 100) (const_int 0)))))]
4318 [(set_attr "type" "ialuX")])
4320 (define_insn_and_split "*subx_extend"
4321 [(set (match_operand:DI 0 "register_operand" "=r")
4322 (zero_extend:DI (minus:SI (minus:SI (match_operand:SI 1 "register_or_zero_operand" "rJ")
4323 (match_operand:SI 2 "arith_operand" "rI"))
4324 (ltu:SI (reg:CC_NOOV 100) (const_int 0)))))]
4327 "&& reload_completed"
4328 [(set (match_dup 3) (minus:SI (minus:SI (match_dup 1) (match_dup 2))
4329 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))
4330 (set (match_dup 4) (const_int 0))]
4331 "operands[3] = gen_lowpart (SImode, operands[0]);
4332 operands[4] = gen_highpart (SImode, operands[0]);"
4333 [(set_attr "length" "2")])
4335 (define_insn_and_split ""
4336 [(set (match_operand:DI 0 "register_operand" "=r")
4337 (minus:DI (match_operand:DI 1 "register_operand" "r")
4338 (zero_extend:DI (match_operand:SI 2 "register_operand" "r"))))
4339 (clobber (reg:CC 100))]
4342 "&& reload_completed"
4343 [(parallel [(set (reg:CC_NOOV 100)
4344 (compare:CC_NOOV (minus:SI (match_dup 3) (match_dup 2))
4346 (set (match_dup 5) (minus:SI (match_dup 3) (match_dup 2)))])
4348 (minus:SI (minus:SI (match_dup 4) (const_int 0))
4349 (ltu:SI (reg:CC_NOOV 100) (const_int 0))))]
4350 "operands[3] = gen_lowpart (SImode, operands[1]);
4351 operands[4] = gen_highpart (SImode, operands[1]);
4352 operands[5] = gen_lowpart (SImode, operands[0]);
4353 operands[6] = gen_highpart (SImode, operands[0]);"
4354 [(set_attr "length" "2")])
4356 (define_insn "*subdi3_sp64"
4357 [(set (match_operand:DI 0 "register_operand" "=r,r")
4358 (minus:DI (match_operand:DI 1 "register_operand" "r,r")
4359 (match_operand:DI 2 "arith_add_operand" "rI,O")))]
4365 (define_insn "subsi3"
4366 [(set (match_operand:SI 0 "register_operand" "=r,r,d")
4367 (minus:SI (match_operand:SI 1 "register_operand" "r,r,d")
4368 (match_operand:SI 2 "arith_add_operand" "rI,O,d")))]
4373 fpsub32s\t%1, %2, %0"
4374 [(set_attr "type" "*,*,fga")
4375 (set_attr "fptype" "*,*,single")])
4377 (define_insn "*cmp_minus_cc"
4378 [(set (reg:CC_NOOV 100)
4379 (compare:CC_NOOV (minus:SI (match_operand:SI 0 "register_or_zero_operand" "rJ")
4380 (match_operand:SI 1 "arith_operand" "rI"))
4383 "subcc\t%r0, %1, %%g0"
4384 [(set_attr "type" "compare")])
4386 (define_insn "*cmp_minus_ccx"
4387 [(set (reg:CCX_NOOV 100)
4388 (compare:CCX_NOOV (minus:DI (match_operand:DI 0 "register_operand" "r")
4389 (match_operand:DI 1 "arith_operand" "rI"))
4392 "subcc\t%0, %1, %%g0"
4393 [(set_attr "type" "compare")])
4395 (define_insn "cmp_minus_cc_set"
4396 [(set (reg:CC_NOOV 100)
4397 (compare:CC_NOOV (minus:SI (match_operand:SI 1 "register_or_zero_operand" "rJ")
4398 (match_operand:SI 2 "arith_operand" "rI"))
4400 (set (match_operand:SI 0 "register_operand" "=r")
4401 (minus:SI (match_dup 1) (match_dup 2)))]
4403 "subcc\t%r1, %2, %0"
4404 [(set_attr "type" "compare")])
4406 (define_insn "*cmp_minus_ccx_set"
4407 [(set (reg:CCX_NOOV 100)
4408 (compare:CCX_NOOV (minus:DI (match_operand:DI 1 "register_operand" "r")
4409 (match_operand:DI 2 "arith_operand" "rI"))
4411 (set (match_operand:DI 0 "register_operand" "=r")
4412 (minus:DI (match_dup 1) (match_dup 2)))]
4415 [(set_attr "type" "compare")])
4418 ;; Integer multiply/divide instructions.
4420 ;; The 32-bit multiply/divide instructions are deprecated on v9, but at
4421 ;; least in UltraSPARC I, II and IIi it is a win tick-wise.
4423 (define_insn "mulsi3"
4424 [(set (match_operand:SI 0 "register_operand" "=r")
4425 (mult:SI (match_operand:SI 1 "arith_operand" "%r")
4426 (match_operand:SI 2 "arith_operand" "rI")))]
4429 [(set_attr "type" "imul")])
4431 (define_expand "muldi3"
4432 [(set (match_operand:DI 0 "register_operand" "")
4433 (mult:DI (match_operand:DI 1 "arith_operand" "")
4434 (match_operand:DI 2 "arith_operand" "")))]
4435 "TARGET_ARCH64 || TARGET_V8PLUS"
4439 emit_insn (gen_muldi3_v8plus (operands[0], operands[1], operands[2]));
4444 (define_insn "*muldi3_sp64"
4445 [(set (match_operand:DI 0 "register_operand" "=r")
4446 (mult:DI (match_operand:DI 1 "arith_operand" "%r")
4447 (match_operand:DI 2 "arith_operand" "rI")))]
4450 [(set_attr "type" "imul")])
4452 ;; V8plus wide multiply.
4454 (define_insn "muldi3_v8plus"
4455 [(set (match_operand:DI 0 "register_operand" "=r,h")
4456 (mult:DI (match_operand:DI 1 "arith_operand" "%r,0")
4457 (match_operand:DI 2 "arith_operand" "rI,rI")))
4458 (clobber (match_scratch:SI 3 "=&h,X"))
4459 (clobber (match_scratch:SI 4 "=&h,X"))]
4462 if (sparc_check_64 (operands[1], insn) <= 0)
4463 output_asm_insn ("srl\t%L1, 0, %L1", operands);
4464 if (which_alternative == 1)
4465 output_asm_insn ("sllx\t%H1, 32, %H1", operands);
4466 if (GET_CODE (operands[2]) == CONST_INT)
4468 if (which_alternative == 1)
4469 return "or\t%L1, %H1, %H1\n\tmulx\t%H1, %2, %L0\;srlx\t%L0, 32, %H0";
4471 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";
4473 else if (rtx_equal_p (operands[1], operands[2]))
4475 if (which_alternative == 1)
4476 return "or\t%L1, %H1, %H1\n\tmulx\t%H1, %H1, %L0\;srlx\t%L0, 32, %H0";
4478 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";
4480 if (sparc_check_64 (operands[2], insn) <= 0)
4481 output_asm_insn ("srl\t%L2, 0, %L2", operands);
4482 if (which_alternative == 1)
4483 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";
4485 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";
4487 [(set_attr "type" "multi")
4488 (set_attr "length" "9,8")])
4490 (define_insn "*cmp_mul_set"
4492 (compare:CC (mult:SI (match_operand:SI 1 "arith_operand" "%r")
4493 (match_operand:SI 2 "arith_operand" "rI"))
4495 (set (match_operand:SI 0 "register_operand" "=r")
4496 (mult:SI (match_dup 1) (match_dup 2)))]
4497 "TARGET_V8 || TARGET_SPARCLITE || TARGET_DEPRECATED_V8_INSNS"
4498 "smulcc\t%1, %2, %0"
4499 [(set_attr "type" "imul")])
4501 (define_expand "mulsidi3"
4502 [(set (match_operand:DI 0 "register_operand" "")
4503 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" ""))
4504 (sign_extend:DI (match_operand:SI 2 "arith_operand" ""))))]
4507 if (CONSTANT_P (operands[2]))
4510 emit_insn (gen_const_mulsidi3_v8plus (operands[0], operands[1],
4512 else if (TARGET_ARCH32)
4513 emit_insn (gen_const_mulsidi3_sp32 (operands[0], operands[1],
4516 emit_insn (gen_const_mulsidi3_sp64 (operands[0], operands[1],
4522 emit_insn (gen_mulsidi3_v8plus (operands[0], operands[1], operands[2]));
4527 ;; V9 puts the 64-bit product in a 64-bit register. Only out or global
4528 ;; registers can hold 64-bit values in the V8plus environment.
4530 (define_insn "mulsidi3_v8plus"
4531 [(set (match_operand:DI 0 "register_operand" "=h,r")
4532 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
4533 (sign_extend:DI (match_operand:SI 2 "register_operand" "r,r"))))
4534 (clobber (match_scratch:SI 3 "=X,&h"))]
4537 smul\t%1, %2, %L0\n\tsrlx\t%L0, 32, %H0
4538 smul\t%1, %2, %3\n\tsrlx\t%3, 32, %H0\n\tmov\t%3, %L0"
4539 [(set_attr "type" "multi")
4540 (set_attr "length" "2,3")])
4543 (define_insn "const_mulsidi3_v8plus"
4544 [(set (match_operand:DI 0 "register_operand" "=h,r")
4545 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
4546 (match_operand:DI 2 "small_int_operand" "I,I")))
4547 (clobber (match_scratch:SI 3 "=X,&h"))]
4550 smul\t%1, %2, %L0\n\tsrlx\t%L0, 32, %H0
4551 smul\t%1, %2, %3\n\tsrlx\t%3, 32, %H0\n\tmov\t%3, %L0"
4552 [(set_attr "type" "multi")
4553 (set_attr "length" "2,3")])
4556 (define_insn "*mulsidi3_sp32"
4557 [(set (match_operand:DI 0 "register_operand" "=r")
4558 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
4559 (sign_extend:DI (match_operand:SI 2 "register_operand" "r"))))]
4562 return TARGET_SPARCLET
4563 ? "smuld\t%1, %2, %L0"
4564 : "smul\t%1, %2, %L0\n\trd\t%%y, %H0";
4567 (if_then_else (eq_attr "isa" "sparclet")
4568 (const_string "imul") (const_string "multi")))
4569 (set (attr "length")
4570 (if_then_else (eq_attr "isa" "sparclet")
4571 (const_int 1) (const_int 2)))])
4573 (define_insn "*mulsidi3_sp64"
4574 [(set (match_operand:DI 0 "register_operand" "=r")
4575 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
4576 (sign_extend:DI (match_operand:SI 2 "register_operand" "r"))))]
4577 "TARGET_DEPRECATED_V8_INSNS && TARGET_ARCH64"
4579 [(set_attr "type" "imul")])
4581 ;; Extra pattern, because sign_extend of a constant isn't valid.
4584 (define_insn "const_mulsidi3_sp32"
4585 [(set (match_operand:DI 0 "register_operand" "=r")
4586 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
4587 (match_operand:DI 2 "small_int_operand" "I")))]
4590 return TARGET_SPARCLET
4591 ? "smuld\t%1, %2, %L0"
4592 : "smul\t%1, %2, %L0\n\trd\t%%y, %H0";
4595 (if_then_else (eq_attr "isa" "sparclet")
4596 (const_string "imul") (const_string "multi")))
4597 (set (attr "length")
4598 (if_then_else (eq_attr "isa" "sparclet")
4599 (const_int 1) (const_int 2)))])
4601 (define_insn "const_mulsidi3_sp64"
4602 [(set (match_operand:DI 0 "register_operand" "=r")
4603 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
4604 (match_operand:DI 2 "small_int_operand" "I")))]
4605 "TARGET_DEPRECATED_V8_INSNS && TARGET_ARCH64"
4607 [(set_attr "type" "imul")])
4609 (define_expand "smulsi3_highpart"
4610 [(set (match_operand:SI 0 "register_operand" "")
4612 (lshiftrt:DI (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" ""))
4613 (sign_extend:DI (match_operand:SI 2 "arith_operand" "")))
4615 "TARGET_HARD_MUL && TARGET_ARCH32"
4617 if (CONSTANT_P (operands[2]))
4621 emit_insn (gen_const_smulsi3_highpart_v8plus (operands[0],
4627 emit_insn (gen_const_smulsi3_highpart (operands[0], operands[1], operands[2]));
4632 emit_insn (gen_smulsi3_highpart_v8plus (operands[0], operands[1],
4633 operands[2], GEN_INT (32)));
4639 (define_insn "smulsi3_highpart_v8plus"
4640 [(set (match_operand:SI 0 "register_operand" "=h,r")
4642 (lshiftrt:DI (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
4643 (sign_extend:DI (match_operand:SI 2 "register_operand" "r,r")))
4644 (match_operand:SI 3 "small_int_operand" "I,I"))))
4645 (clobber (match_scratch:SI 4 "=X,&h"))]
4648 smul\t%1, %2, %0\;srlx\t%0, %3, %0
4649 smul\t%1, %2, %4\;srlx\t%4, %3, %0"
4650 [(set_attr "type" "multi")
4651 (set_attr "length" "2")])
4653 ;; The combiner changes TRUNCATE in the previous pattern to SUBREG.
4656 [(set (match_operand:SI 0 "register_operand" "=h,r")
4659 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
4660 (sign_extend:DI (match_operand:SI 2 "register_operand" "r,r")))
4661 (match_operand:SI 3 "small_int_operand" "I,I"))
4663 (clobber (match_scratch:SI 4 "=X,&h"))]
4666 smul\t%1, %2, %0\n\tsrlx\t%0, %3, %0
4667 smul\t%1, %2, %4\n\tsrlx\t%4, %3, %0"
4668 [(set_attr "type" "multi")
4669 (set_attr "length" "2")])
4672 (define_insn "const_smulsi3_highpart_v8plus"
4673 [(set (match_operand:SI 0 "register_operand" "=h,r")
4675 (lshiftrt:DI (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
4676 (match_operand:DI 2 "small_int_operand" "I,I"))
4677 (match_operand:SI 3 "small_int_operand" "I,I"))))
4678 (clobber (match_scratch:SI 4 "=X,&h"))]
4681 smul\t%1, %2, %0\n\tsrlx\t%0, %3, %0
4682 smul\t%1, %2, %4\n\tsrlx\t%4, %3, %0"
4683 [(set_attr "type" "multi")
4684 (set_attr "length" "2")])
4687 (define_insn "*smulsi3_highpart_sp32"
4688 [(set (match_operand:SI 0 "register_operand" "=r")
4690 (lshiftrt:DI (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
4691 (sign_extend:DI (match_operand:SI 2 "register_operand" "r")))
4694 "smul\t%1, %2, %%g0\n\trd\t%%y, %0"
4695 [(set_attr "type" "multi")
4696 (set_attr "length" "2")])
4699 (define_insn "const_smulsi3_highpart"
4700 [(set (match_operand:SI 0 "register_operand" "=r")
4702 (lshiftrt:DI (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
4703 (match_operand:DI 2 "small_int_operand" "i"))
4706 "smul\t%1, %2, %%g0\n\trd\t%%y, %0"
4707 [(set_attr "type" "multi")
4708 (set_attr "length" "2")])
4710 (define_expand "umulsidi3"
4711 [(set (match_operand:DI 0 "register_operand" "")
4712 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" ""))
4713 (zero_extend:DI (match_operand:SI 2 "uns_arith_operand" ""))))]
4716 if (CONSTANT_P (operands[2]))
4719 emit_insn (gen_const_umulsidi3_v8plus (operands[0], operands[1],
4721 else if (TARGET_ARCH32)
4722 emit_insn (gen_const_umulsidi3_sp32 (operands[0], operands[1],
4725 emit_insn (gen_const_umulsidi3_sp64 (operands[0], operands[1],
4731 emit_insn (gen_umulsidi3_v8plus (operands[0], operands[1], operands[2]));
4737 (define_insn "umulsidi3_v8plus"
4738 [(set (match_operand:DI 0 "register_operand" "=h,r")
4739 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
4740 (zero_extend:DI (match_operand:SI 2 "register_operand" "r,r"))))
4741 (clobber (match_scratch:SI 3 "=X,&h"))]
4744 umul\t%1, %2, %L0\n\tsrlx\t%L0, 32, %H0
4745 umul\t%1, %2, %3\n\tsrlx\t%3, 32, %H0\n\tmov\t%3, %L0"
4746 [(set_attr "type" "multi")
4747 (set_attr "length" "2,3")])
4750 (define_insn "*umulsidi3_sp32"
4751 [(set (match_operand:DI 0 "register_operand" "=r")
4752 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
4753 (zero_extend:DI (match_operand:SI 2 "register_operand" "r"))))]
4756 return TARGET_SPARCLET
4757 ? "umuld\t%1, %2, %L0"
4758 : "umul\t%1, %2, %L0\n\trd\t%%y, %H0";
4761 (if_then_else (eq_attr "isa" "sparclet")
4762 (const_string "imul") (const_string "multi")))
4763 (set (attr "length")
4764 (if_then_else (eq_attr "isa" "sparclet")
4765 (const_int 1) (const_int 2)))])
4767 (define_insn "*umulsidi3_sp64"
4768 [(set (match_operand:DI 0 "register_operand" "=r")
4769 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
4770 (zero_extend:DI (match_operand:SI 2 "register_operand" "r"))))]
4771 "TARGET_DEPRECATED_V8_INSNS && TARGET_ARCH64"
4773 [(set_attr "type" "imul")])
4775 ;; Extra pattern, because sign_extend of a constant isn't valid.
4778 (define_insn "const_umulsidi3_sp32"
4779 [(set (match_operand:DI 0 "register_operand" "=r")
4780 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
4781 (match_operand:DI 2 "uns_small_int_operand" "")))]
4784 return TARGET_SPARCLET
4785 ? "umuld\t%1, %s2, %L0"
4786 : "umul\t%1, %s2, %L0\n\trd\t%%y, %H0";
4789 (if_then_else (eq_attr "isa" "sparclet")
4790 (const_string "imul") (const_string "multi")))
4791 (set (attr "length")
4792 (if_then_else (eq_attr "isa" "sparclet")
4793 (const_int 1) (const_int 2)))])
4795 (define_insn "const_umulsidi3_sp64"
4796 [(set (match_operand:DI 0 "register_operand" "=r")
4797 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
4798 (match_operand:DI 2 "uns_small_int_operand" "")))]
4799 "TARGET_DEPRECATED_V8_INSNS && TARGET_ARCH64"
4801 [(set_attr "type" "imul")])
4804 (define_insn "const_umulsidi3_v8plus"
4805 [(set (match_operand:DI 0 "register_operand" "=h,r")
4806 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
4807 (match_operand:DI 2 "uns_small_int_operand" "")))
4808 (clobber (match_scratch:SI 3 "=X,h"))]
4811 umul\t%1, %s2, %L0\n\tsrlx\t%L0, 32, %H0
4812 umul\t%1, %s2, %3\n\tsrlx\t%3, 32, %H0\n\tmov\t%3, %L0"
4813 [(set_attr "type" "multi")
4814 (set_attr "length" "2,3")])
4816 (define_expand "umulsi3_highpart"
4817 [(set (match_operand:SI 0 "register_operand" "")
4819 (lshiftrt:DI (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" ""))
4820 (zero_extend:DI (match_operand:SI 2 "uns_arith_operand" "")))
4822 "TARGET_HARD_MUL && TARGET_ARCH32"
4824 if (CONSTANT_P (operands[2]))
4828 emit_insn (gen_const_umulsi3_highpart_v8plus (operands[0],
4834 emit_insn (gen_const_umulsi3_highpart (operands[0], operands[1], operands[2]));
4839 emit_insn (gen_umulsi3_highpart_v8plus (operands[0], operands[1],
4840 operands[2], GEN_INT (32)));
4846 (define_insn "umulsi3_highpart_v8plus"
4847 [(set (match_operand:SI 0 "register_operand" "=h,r")
4849 (lshiftrt:DI (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
4850 (zero_extend:DI (match_operand:SI 2 "register_operand" "r,r")))
4851 (match_operand:SI 3 "small_int_operand" "I,I"))))
4852 (clobber (match_scratch:SI 4 "=X,h"))]
4855 umul\t%1, %2, %0\n\tsrlx\t%0, %3, %0
4856 umul\t%1, %2, %4\n\tsrlx\t%4, %3, %0"
4857 [(set_attr "type" "multi")
4858 (set_attr "length" "2")])
4861 (define_insn "const_umulsi3_highpart_v8plus"
4862 [(set (match_operand:SI 0 "register_operand" "=h,r")
4864 (lshiftrt:DI (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r,r"))
4865 (match_operand:DI 2 "uns_small_int_operand" ""))
4866 (match_operand:SI 3 "small_int_operand" "I,I"))))
4867 (clobber (match_scratch:SI 4 "=X,h"))]
4870 umul\t%1, %s2, %0\n\tsrlx\t%0, %3, %0
4871 umul\t%1, %s2, %4\n\tsrlx\t%4, %3, %0"
4872 [(set_attr "type" "multi")
4873 (set_attr "length" "2")])
4876 (define_insn "*umulsi3_highpart_sp32"
4877 [(set (match_operand:SI 0 "register_operand" "=r")
4879 (lshiftrt:DI (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
4880 (zero_extend:DI (match_operand:SI 2 "register_operand" "r")))
4883 "umul\t%1, %2, %%g0\n\trd\t%%y, %0"
4884 [(set_attr "type" "multi")
4885 (set_attr "length" "2")])
4888 (define_insn "const_umulsi3_highpart"
4889 [(set (match_operand:SI 0 "register_operand" "=r")
4891 (lshiftrt:DI (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
4892 (match_operand:DI 2 "uns_small_int_operand" ""))
4895 "umul\t%1, %s2, %%g0\n\trd\t%%y, %0"
4896 [(set_attr "type" "multi")
4897 (set_attr "length" "2")])
4899 ;; The V8 architecture specifies that there must be 3 instructions between
4900 ;; a Y register write and a use of it for correct results.
4902 (define_expand "divsi3"
4903 [(parallel [(set (match_operand:SI 0 "register_operand" "=r,r")
4904 (div:SI (match_operand:SI 1 "register_operand" "r,r")
4905 (match_operand:SI 2 "input_operand" "rI,m")))
4906 (clobber (match_scratch:SI 3 "=&r,&r"))])]
4907 "TARGET_V8 || TARGET_DEPRECATED_V8_INSNS"
4911 operands[3] = gen_reg_rtx(SImode);
4912 emit_insn (gen_ashrsi3 (operands[3], operands[1], GEN_INT (31)));
4913 emit_insn (gen_divsi3_sp64 (operands[0], operands[1], operands[2],
4919 (define_insn "divsi3_sp32"
4920 [(set (match_operand:SI 0 "register_operand" "=r,r")
4921 (div:SI (match_operand:SI 1 "register_operand" "r,r")
4922 (match_operand:SI 2 "input_operand" "rI,m")))
4923 (clobber (match_scratch:SI 3 "=&r,&r"))]
4924 "(TARGET_V8 || TARGET_DEPRECATED_V8_INSNS)
4927 if (which_alternative == 0)
4929 return "sra\t%1, 31, %3\n\twr\t%3, 0, %%y\n\tsdiv\t%1, %2, %0";
4931 return "sra\t%1, 31, %3\n\twr\t%3, 0, %%y\n\tnop\n\tnop\n\tnop\n\tsdiv\t%1, %2, %0";
4934 return "sra\t%1, 31, %3\n\twr\t%3, 0, %%y\n\tld\t%2, %3\n\tsdiv\t%1, %3, %0";
4936 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";
4938 [(set_attr "type" "multi")
4939 (set (attr "length")
4940 (if_then_else (eq_attr "isa" "v9")
4941 (const_int 4) (const_int 6)))])
4943 (define_insn "divsi3_sp64"
4944 [(set (match_operand:SI 0 "register_operand" "=r")
4945 (div:SI (match_operand:SI 1 "register_operand" "r")
4946 (match_operand:SI 2 "input_operand" "rI")))
4947 (use (match_operand:SI 3 "register_operand" "r"))]
4948 "TARGET_DEPRECATED_V8_INSNS && TARGET_ARCH64"
4949 "wr\t%%g0, %3, %%y\n\tsdiv\t%1, %2, %0"
4950 [(set_attr "type" "multi")
4951 (set_attr "length" "2")])
4953 (define_insn "divdi3"
4954 [(set (match_operand:DI 0 "register_operand" "=r")
4955 (div:DI (match_operand:DI 1 "register_operand" "r")
4956 (match_operand:DI 2 "arith_operand" "rI")))]
4959 [(set_attr "type" "idiv")])
4961 (define_insn "*cmp_sdiv_cc_set"
4963 (compare:CC (div:SI (match_operand:SI 1 "register_operand" "r")
4964 (match_operand:SI 2 "arith_operand" "rI"))
4966 (set (match_operand:SI 0 "register_operand" "=r")
4967 (div:SI (match_dup 1) (match_dup 2)))
4968 (clobber (match_scratch:SI 3 "=&r"))]
4969 "TARGET_V8 || TARGET_DEPRECATED_V8_INSNS"
4972 return "sra\t%1, 31, %3\n\twr\t%3, 0, %%y\n\tsdivcc\t%1, %2, %0";
4974 return "sra\t%1, 31, %3\n\twr\t%3, 0, %%y\n\tnop\n\tnop\n\tnop\n\tsdivcc\t%1, %2, %0";
4976 [(set_attr "type" "multi")
4977 (set (attr "length")
4978 (if_then_else (eq_attr "isa" "v9")
4979 (const_int 3) (const_int 6)))])
4982 (define_expand "udivsi3"
4983 [(set (match_operand:SI 0 "register_operand" "")
4984 (udiv:SI (match_operand:SI 1 "nonimmediate_operand" "")
4985 (match_operand:SI 2 "input_operand" "")))]
4986 "TARGET_V8 || TARGET_DEPRECATED_V8_INSNS"
4989 ;; The V8 architecture specifies that there must be 3 instructions between
4990 ;; a Y register write and a use of it for correct results.
4992 (define_insn "udivsi3_sp32"
4993 [(set (match_operand:SI 0 "register_operand" "=r,&r,&r")
4994 (udiv:SI (match_operand:SI 1 "nonimmediate_operand" "r,r,m")
4995 (match_operand:SI 2 "input_operand" "rI,m,r")))]
4996 "(TARGET_V8 || TARGET_DEPRECATED_V8_INSNS)
4999 output_asm_insn ("wr\t%%g0, %%g0, %%y", operands);
5000 switch (which_alternative)
5003 return "nop\n\tnop\n\tnop\n\tudiv\t%1, %2, %0";
5005 return "ld\t%2, %0\n\tnop\n\tnop\n\tudiv\t%1, %0, %0";
5007 return "ld\t%1, %0\n\tnop\n\tnop\n\tudiv\t%0, %2, %0";
5010 [(set_attr "type" "multi")
5011 (set_attr "length" "5")])
5013 (define_insn "udivsi3_sp64"
5014 [(set (match_operand:SI 0 "register_operand" "=r")
5015 (udiv:SI (match_operand:SI 1 "nonimmediate_operand" "r")
5016 (match_operand:SI 2 "input_operand" "rI")))]
5017 "TARGET_DEPRECATED_V8_INSNS && TARGET_ARCH64"
5018 "wr\t%%g0, 0, %%y\n\tudiv\t%1, %2, %0"
5019 [(set_attr "type" "multi")
5020 (set_attr "length" "2")])
5022 (define_insn "udivdi3"
5023 [(set (match_operand:DI 0 "register_operand" "=r")
5024 (udiv:DI (match_operand:DI 1 "register_operand" "r")
5025 (match_operand:DI 2 "arith_operand" "rI")))]
5028 [(set_attr "type" "idiv")])
5030 (define_insn "*cmp_udiv_cc_set"
5032 (compare:CC (udiv:SI (match_operand:SI 1 "register_operand" "r")
5033 (match_operand:SI 2 "arith_operand" "rI"))
5035 (set (match_operand:SI 0 "register_operand" "=r")
5036 (udiv:SI (match_dup 1) (match_dup 2)))]
5038 || TARGET_DEPRECATED_V8_INSNS"
5041 return "wr\t%%g0, %%g0, %%y\n\tudivcc\t%1, %2, %0";
5043 return "wr\t%%g0, %%g0, %%y\n\tnop\n\tnop\n\tnop\n\tudivcc\t%1, %2, %0";
5045 [(set_attr "type" "multi")
5046 (set (attr "length")
5047 (if_then_else (eq_attr "isa" "v9")
5048 (const_int 2) (const_int 5)))])
5050 ; sparclet multiply/accumulate insns
5052 (define_insn "*smacsi"
5053 [(set (match_operand:SI 0 "register_operand" "=r")
5054 (plus:SI (mult:SI (match_operand:SI 1 "register_operand" "%r")
5055 (match_operand:SI 2 "arith_operand" "rI"))
5056 (match_operand:SI 3 "register_operand" "0")))]
5059 [(set_attr "type" "imul")])
5061 (define_insn "*smacdi"
5062 [(set (match_operand:DI 0 "register_operand" "=r")
5063 (plus:DI (mult:DI (sign_extend:DI
5064 (match_operand:SI 1 "register_operand" "%r"))
5066 (match_operand:SI 2 "register_operand" "r")))
5067 (match_operand:DI 3 "register_operand" "0")))]
5069 "smacd\t%1, %2, %L0"
5070 [(set_attr "type" "imul")])
5072 (define_insn "*umacdi"
5073 [(set (match_operand:DI 0 "register_operand" "=r")
5074 (plus:DI (mult:DI (zero_extend:DI
5075 (match_operand:SI 1 "register_operand" "%r"))
5077 (match_operand:SI 2 "register_operand" "r")))
5078 (match_operand:DI 3 "register_operand" "0")))]
5080 "umacd\t%1, %2, %L0"
5081 [(set_attr "type" "imul")])
5084 ;; Boolean instructions.
5086 ;; We define DImode `and' so with DImode `not' we can get
5087 ;; DImode `andn'. Other combinations are possible.
5089 (define_mode_iterator V64I [DI V2SI V4HI V8QI])
5090 (define_mode_iterator V32I [SI V2HI V4QI])
5092 (define_expand "and<V64I:mode>3"
5093 [(set (match_operand:V64I 0 "register_operand" "")
5094 (and:V64I (match_operand:V64I 1 "arith_double_operand" "")
5095 (match_operand:V64I 2 "arith_double_operand" "")))]
5099 (define_insn "*and<V64I:mode>3_sp32"
5100 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5101 (and:V64I (match_operand:V64I 1 "arith_double_operand" "%r,b")
5102 (match_operand:V64I 2 "arith_double_operand" "rHI,b")))]
5107 [(set_attr "type" "*,fga")
5108 (set_attr "length" "2,*")
5109 (set_attr "fptype" "*,double")])
5111 (define_insn "*and<V64I:mode>3_sp64"
5112 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5113 (and:V64I (match_operand:V64I 1 "arith_operand" "%r,b")
5114 (match_operand:V64I 2 "arith_operand" "rI,b")))]
5119 [(set_attr "type" "*,fga")
5120 (set_attr "fptype" "*,double")])
5122 (define_insn "and<V32I:mode>3"
5123 [(set (match_operand:V32I 0 "register_operand" "=r,d")
5124 (and:V32I (match_operand:V32I 1 "arith_operand" "%r,d")
5125 (match_operand:V32I 2 "arith_operand" "rI,d")))]
5130 [(set_attr "type" "*,fga")
5131 (set_attr "fptype" "*,single")])
5134 [(set (match_operand:SI 0 "register_operand" "")
5135 (and:SI (match_operand:SI 1 "register_operand" "")
5136 (match_operand:SI 2 "const_compl_high_operand" "")))
5137 (clobber (match_operand:SI 3 "register_operand" ""))]
5139 [(set (match_dup 3) (match_dup 4))
5140 (set (match_dup 0) (and:SI (not:SI (match_dup 3)) (match_dup 1)))]
5142 operands[4] = GEN_INT (~INTVAL (operands[2]));
5145 (define_insn_and_split "*and_not_<V64I:mode>_sp32"
5146 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5147 (and:V64I (not:V64I (match_operand:V64I 1 "register_operand" "%r,b"))
5148 (match_operand:V64I 2 "register_operand" "r,b")))]
5152 fandnot1\t%1, %2, %0"
5153 "&& reload_completed
5154 && ((GET_CODE (operands[0]) == REG
5155 && REGNO (operands[0]) < 32)
5156 || (GET_CODE (operands[0]) == SUBREG
5157 && GET_CODE (SUBREG_REG (operands[0])) == REG
5158 && REGNO (SUBREG_REG (operands[0])) < 32))"
5159 [(set (match_dup 3) (and:SI (not:SI (match_dup 4)) (match_dup 5)))
5160 (set (match_dup 6) (and:SI (not:SI (match_dup 7)) (match_dup 8)))]
5161 "operands[3] = gen_highpart (SImode, operands[0]);
5162 operands[4] = gen_highpart (SImode, operands[1]);
5163 operands[5] = gen_highpart (SImode, operands[2]);
5164 operands[6] = gen_lowpart (SImode, operands[0]);
5165 operands[7] = gen_lowpart (SImode, operands[1]);
5166 operands[8] = gen_lowpart (SImode, operands[2]);"
5167 [(set_attr "type" "*,fga")
5168 (set_attr "length" "2,*")
5169 (set_attr "fptype" "*,double")])
5171 (define_insn "*and_not_<V64I:mode>_sp64"
5172 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5173 (and:V64I (not:V64I (match_operand:V64I 1 "register_operand" "%r,b"))
5174 (match_operand:V64I 2 "register_operand" "r,b")))]
5178 fandnot1\t%1, %2, %0"
5179 [(set_attr "type" "*,fga")
5180 (set_attr "fptype" "*,double")])
5182 (define_insn "*and_not_<V32I:mode>"
5183 [(set (match_operand:V32I 0 "register_operand" "=r,d")
5184 (and:V32I (not:V32I (match_operand:V32I 1 "register_operand" "%r,d"))
5185 (match_operand:V32I 2 "register_operand" "r,d")))]
5189 fandnot1s\t%1, %2, %0"
5190 [(set_attr "type" "*,fga")
5191 (set_attr "fptype" "*,single")])
5193 (define_expand "ior<V64I:mode>3"
5194 [(set (match_operand:V64I 0 "register_operand" "")
5195 (ior:V64I (match_operand:V64I 1 "arith_double_operand" "")
5196 (match_operand:V64I 2 "arith_double_operand" "")))]
5200 (define_insn "*ior<V64I:mode>3_sp32"
5201 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5202 (ior:V64I (match_operand:V64I 1 "arith_double_operand" "%r,b")
5203 (match_operand:V64I 2 "arith_double_operand" "rHI,b")))]
5208 [(set_attr "type" "*,fga")
5209 (set_attr "length" "2,*")
5210 (set_attr "fptype" "*,double")])
5212 (define_insn "*ior<V64I:mode>3_sp64"
5213 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5214 (ior:V64I (match_operand:V64I 1 "arith_operand" "%r,b")
5215 (match_operand:V64I 2 "arith_operand" "rI,b")))]
5220 [(set_attr "type" "*,fga")
5221 (set_attr "fptype" "*,double")])
5223 (define_insn "ior<V32I:mode>3"
5224 [(set (match_operand:V32I 0 "register_operand" "=r,d")
5225 (ior:V32I (match_operand:V32I 1 "arith_operand" "%r,d")
5226 (match_operand:V32I 2 "arith_operand" "rI,d")))]
5231 [(set_attr "type" "*,fga")
5232 (set_attr "fptype" "*,single")])
5235 [(set (match_operand:SI 0 "register_operand" "")
5236 (ior:SI (match_operand:SI 1 "register_operand" "")
5237 (match_operand:SI 2 "const_compl_high_operand" "")))
5238 (clobber (match_operand:SI 3 "register_operand" ""))]
5240 [(set (match_dup 3) (match_dup 4))
5241 (set (match_dup 0) (ior:SI (not:SI (match_dup 3)) (match_dup 1)))]
5243 operands[4] = GEN_INT (~INTVAL (operands[2]));
5246 (define_insn_and_split "*or_not_<V64I:mode>_sp32"
5247 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5248 (ior:V64I (not:V64I (match_operand:V64I 1 "register_operand" "r,b"))
5249 (match_operand:V64I 2 "register_operand" "r,b")))]
5253 fornot1\t%1, %2, %0"
5254 "&& reload_completed
5255 && ((GET_CODE (operands[0]) == REG
5256 && REGNO (operands[0]) < 32)
5257 || (GET_CODE (operands[0]) == SUBREG
5258 && GET_CODE (SUBREG_REG (operands[0])) == REG
5259 && REGNO (SUBREG_REG (operands[0])) < 32))"
5260 [(set (match_dup 3) (ior:SI (not:SI (match_dup 4)) (match_dup 5)))
5261 (set (match_dup 6) (ior:SI (not:SI (match_dup 7)) (match_dup 8)))]
5262 "operands[3] = gen_highpart (SImode, operands[0]);
5263 operands[4] = gen_highpart (SImode, operands[1]);
5264 operands[5] = gen_highpart (SImode, operands[2]);
5265 operands[6] = gen_lowpart (SImode, operands[0]);
5266 operands[7] = gen_lowpart (SImode, operands[1]);
5267 operands[8] = gen_lowpart (SImode, operands[2]);"
5268 [(set_attr "type" "*,fga")
5269 (set_attr "length" "2,*")
5270 (set_attr "fptype" "*,double")])
5272 (define_insn "*or_not_<V64I:mode>_sp64"
5273 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5274 (ior:V64I (not:V64I (match_operand:V64I 1 "register_operand" "r,b"))
5275 (match_operand:V64I 2 "register_operand" "r,b")))]
5279 fornot1\t%1, %2, %0"
5280 [(set_attr "type" "*,fga")
5281 (set_attr "fptype" "*,double")])
5283 (define_insn "*or_not_<V32I:mode>"
5284 [(set (match_operand:V32I 0 "register_operand" "=r,d")
5285 (ior:V32I (not:V32I (match_operand:V32I 1 "register_operand" "r,d"))
5286 (match_operand:V32I 2 "register_operand" "r,d")))]
5290 fornot1s\t%1, %2, %0"
5291 [(set_attr "type" "*,fga")
5292 (set_attr "fptype" "*,single")])
5294 (define_expand "xor<V64I:mode>3"
5295 [(set (match_operand:V64I 0 "register_operand" "")
5296 (xor:V64I (match_operand:V64I 1 "arith_double_operand" "")
5297 (match_operand:V64I 2 "arith_double_operand" "")))]
5301 (define_insn "*xor<V64I:mode>3_sp32"
5302 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5303 (xor:V64I (match_operand:V64I 1 "arith_double_operand" "%r,b")
5304 (match_operand:V64I 2 "arith_double_operand" "rHI,b")))]
5309 [(set_attr "type" "*,fga")
5310 (set_attr "length" "2,*")
5311 (set_attr "fptype" "*,double")])
5313 (define_insn "*xor<V64I:mode>3_sp64"
5314 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5315 (xor:V64I (match_operand:V64I 1 "arith_operand" "%rJ,b")
5316 (match_operand:V64I 2 "arith_operand" "rI,b")))]
5321 [(set_attr "type" "*,fga")
5322 (set_attr "fptype" "*,double")])
5324 (define_insn "xor<V32I:mode>3"
5325 [(set (match_operand:V32I 0 "register_operand" "=r,d")
5326 (xor:V32I (match_operand:V32I 1 "arith_operand" "%rJ,d")
5327 (match_operand:V32I 2 "arith_operand" "rI,d")))]
5332 [(set_attr "type" "*,fga")
5333 (set_attr "fptype" "*,single")])
5336 [(set (match_operand:SI 0 "register_operand" "")
5337 (xor:SI (match_operand:SI 1 "register_operand" "")
5338 (match_operand:SI 2 "const_compl_high_operand" "")))
5339 (clobber (match_operand:SI 3 "register_operand" ""))]
5341 [(set (match_dup 3) (match_dup 4))
5342 (set (match_dup 0) (not:SI (xor:SI (match_dup 3) (match_dup 1))))]
5344 operands[4] = GEN_INT (~INTVAL (operands[2]));
5348 [(set (match_operand:SI 0 "register_operand" "")
5349 (not:SI (xor:SI (match_operand:SI 1 "register_operand" "")
5350 (match_operand:SI 2 "const_compl_high_operand" ""))))
5351 (clobber (match_operand:SI 3 "register_operand" ""))]
5353 [(set (match_dup 3) (match_dup 4))
5354 (set (match_dup 0) (xor:SI (match_dup 3) (match_dup 1)))]
5356 operands[4] = GEN_INT (~INTVAL (operands[2]));
5359 ;; Split DImode logical operations requiring two instructions.
5361 [(set (match_operand:V64I 0 "register_operand" "")
5362 (match_operator:V64I 1 "cc_arith_operator" ; AND, IOR, XOR
5363 [(match_operand:V64I 2 "register_operand" "")
5364 (match_operand:V64I 3 "arith_double_operand" "")]))]
5367 && ((GET_CODE (operands[0]) == REG
5368 && REGNO (operands[0]) < 32)
5369 || (GET_CODE (operands[0]) == SUBREG
5370 && GET_CODE (SUBREG_REG (operands[0])) == REG
5371 && REGNO (SUBREG_REG (operands[0])) < 32))"
5372 [(set (match_dup 4) (match_op_dup:SI 1 [(match_dup 6) (match_dup 8)]))
5373 (set (match_dup 5) (match_op_dup:SI 1 [(match_dup 7) (match_dup 9)]))]
5375 operands[4] = gen_highpart (SImode, operands[0]);
5376 operands[5] = gen_lowpart (SImode, operands[0]);
5377 operands[6] = gen_highpart (SImode, operands[2]);
5378 operands[7] = gen_lowpart (SImode, operands[2]);
5379 #if HOST_BITS_PER_WIDE_INT == 32
5380 if (GET_CODE (operands[3]) == CONST_INT && <V64I:MODE>mode == DImode)
5382 if (INTVAL (operands[3]) < 0)
5383 operands[8] = constm1_rtx;
5385 operands[8] = const0_rtx;
5389 operands[8] = gen_highpart_mode (SImode, <V64I:MODE>mode, operands[3]);
5390 operands[9] = gen_lowpart (SImode, operands[3]);
5393 ;; xnor patterns. Note that (a ^ ~b) == (~a ^ b) == ~(a ^ b).
5394 ;; Combine now canonicalizes to the rightmost expression.
5395 (define_insn_and_split "*xor_not_<V64I:mode>_sp32"
5396 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5397 (not:V64I (xor:V64I (match_operand:V64I 1 "register_operand" "r,b")
5398 (match_operand:V64I 2 "register_operand" "r,b"))))]
5403 "&& reload_completed
5404 && ((GET_CODE (operands[0]) == REG
5405 && REGNO (operands[0]) < 32)
5406 || (GET_CODE (operands[0]) == SUBREG
5407 && GET_CODE (SUBREG_REG (operands[0])) == REG
5408 && REGNO (SUBREG_REG (operands[0])) < 32))"
5409 [(set (match_dup 3) (not:SI (xor:SI (match_dup 4) (match_dup 5))))
5410 (set (match_dup 6) (not:SI (xor:SI (match_dup 7) (match_dup 8))))]
5411 "operands[3] = gen_highpart (SImode, operands[0]);
5412 operands[4] = gen_highpart (SImode, operands[1]);
5413 operands[5] = gen_highpart (SImode, operands[2]);
5414 operands[6] = gen_lowpart (SImode, operands[0]);
5415 operands[7] = gen_lowpart (SImode, operands[1]);
5416 operands[8] = gen_lowpart (SImode, operands[2]);"
5417 [(set_attr "type" "*,fga")
5418 (set_attr "length" "2,*")
5419 (set_attr "fptype" "*,double")])
5421 (define_insn "*xor_not_<V64I:mode>_sp64"
5422 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5423 (not:V64I (xor:V64I (match_operand:V64I 1 "register_or_zero_operand" "rJ,b")
5424 (match_operand:V64I 2 "arith_operand" "rI,b"))))]
5429 [(set_attr "type" "*,fga")
5430 (set_attr "fptype" "*,double")])
5432 (define_insn "*xor_not_<V32I:mode>"
5433 [(set (match_operand:V32I 0 "register_operand" "=r,d")
5434 (not:V32I (xor:V32I (match_operand:V32I 1 "register_or_zero_operand" "rJ,d")
5435 (match_operand:V32I 2 "arith_operand" "rI,d"))))]
5440 [(set_attr "type" "*,fga")
5441 (set_attr "fptype" "*,single")])
5443 ;; These correspond to the above in the case where we also (or only)
5444 ;; want to set the condition code.
5446 (define_insn "*cmp_cc_arith_op"
5449 (match_operator:SI 2 "cc_arith_operator"
5450 [(match_operand:SI 0 "arith_operand" "%r")
5451 (match_operand:SI 1 "arith_operand" "rI")])
5454 "%A2cc\t%0, %1, %%g0"
5455 [(set_attr "type" "compare")])
5457 (define_insn "*cmp_ccx_arith_op"
5460 (match_operator:DI 2 "cc_arith_operator"
5461 [(match_operand:DI 0 "arith_operand" "%r")
5462 (match_operand:DI 1 "arith_operand" "rI")])
5465 "%A2cc\t%0, %1, %%g0"
5466 [(set_attr "type" "compare")])
5468 (define_insn "*cmp_cc_arith_op_set"
5471 (match_operator:SI 3 "cc_arith_operator"
5472 [(match_operand:SI 1 "arith_operand" "%r")
5473 (match_operand:SI 2 "arith_operand" "rI")])
5475 (set (match_operand:SI 0 "register_operand" "=r")
5476 (match_operator:SI 4 "cc_arith_operator" [(match_dup 1) (match_dup 2)]))]
5477 "GET_CODE (operands[3]) == GET_CODE (operands[4])"
5479 [(set_attr "type" "compare")])
5481 (define_insn "*cmp_ccx_arith_op_set"
5484 (match_operator:DI 3 "cc_arith_operator"
5485 [(match_operand:DI 1 "arith_operand" "%r")
5486 (match_operand:DI 2 "arith_operand" "rI")])
5488 (set (match_operand:DI 0 "register_operand" "=r")
5489 (match_operator:DI 4 "cc_arith_operator" [(match_dup 1) (match_dup 2)]))]
5490 "TARGET_ARCH64 && GET_CODE (operands[3]) == GET_CODE (operands[4])"
5492 [(set_attr "type" "compare")])
5494 (define_insn "*cmp_cc_xor_not"
5497 (not:SI (xor:SI (match_operand:SI 0 "register_or_zero_operand" "%rJ")
5498 (match_operand:SI 1 "arith_operand" "rI")))
5501 "xnorcc\t%r0, %1, %%g0"
5502 [(set_attr "type" "compare")])
5504 (define_insn "*cmp_ccx_xor_not"
5507 (not:DI (xor:DI (match_operand:DI 0 "register_or_zero_operand" "%rJ")
5508 (match_operand:DI 1 "arith_operand" "rI")))
5511 "xnorcc\t%r0, %1, %%g0"
5512 [(set_attr "type" "compare")])
5514 (define_insn "*cmp_cc_xor_not_set"
5517 (not:SI (xor:SI (match_operand:SI 1 "register_or_zero_operand" "%rJ")
5518 (match_operand:SI 2 "arith_operand" "rI")))
5520 (set (match_operand:SI 0 "register_operand" "=r")
5521 (not:SI (xor:SI (match_dup 1) (match_dup 2))))]
5523 "xnorcc\t%r1, %2, %0"
5524 [(set_attr "type" "compare")])
5526 (define_insn "*cmp_ccx_xor_not_set"
5529 (not:DI (xor:DI (match_operand:DI 1 "register_or_zero_operand" "%rJ")
5530 (match_operand:DI 2 "arith_operand" "rI")))
5532 (set (match_operand:DI 0 "register_operand" "=r")
5533 (not:DI (xor:DI (match_dup 1) (match_dup 2))))]
5535 "xnorcc\t%r1, %2, %0"
5536 [(set_attr "type" "compare")])
5538 (define_insn "*cmp_cc_arith_op_not"
5541 (match_operator:SI 2 "cc_arith_not_operator"
5542 [(not:SI (match_operand:SI 0 "arith_operand" "rI"))
5543 (match_operand:SI 1 "register_or_zero_operand" "rJ")])
5546 "%B2cc\t%r1, %0, %%g0"
5547 [(set_attr "type" "compare")])
5549 (define_insn "*cmp_ccx_arith_op_not"
5552 (match_operator:DI 2 "cc_arith_not_operator"
5553 [(not:DI (match_operand:DI 0 "arith_operand" "rI"))
5554 (match_operand:DI 1 "register_or_zero_operand" "rJ")])
5557 "%B2cc\t%r1, %0, %%g0"
5558 [(set_attr "type" "compare")])
5560 (define_insn "*cmp_cc_arith_op_not_set"
5563 (match_operator:SI 3 "cc_arith_not_operator"
5564 [(not:SI (match_operand:SI 1 "arith_operand" "rI"))
5565 (match_operand:SI 2 "register_or_zero_operand" "rJ")])
5567 (set (match_operand:SI 0 "register_operand" "=r")
5568 (match_operator:SI 4 "cc_arith_not_operator"
5569 [(not:SI (match_dup 1)) (match_dup 2)]))]
5570 "GET_CODE (operands[3]) == GET_CODE (operands[4])"
5571 "%B3cc\t%r2, %1, %0"
5572 [(set_attr "type" "compare")])
5574 (define_insn "*cmp_ccx_arith_op_not_set"
5577 (match_operator:DI 3 "cc_arith_not_operator"
5578 [(not:DI (match_operand:DI 1 "arith_operand" "rI"))
5579 (match_operand:DI 2 "register_or_zero_operand" "rJ")])
5581 (set (match_operand:DI 0 "register_operand" "=r")
5582 (match_operator:DI 4 "cc_arith_not_operator"
5583 [(not:DI (match_dup 1)) (match_dup 2)]))]
5584 "TARGET_ARCH64 && GET_CODE (operands[3]) == GET_CODE (operands[4])"
5585 "%B3cc\t%r2, %1, %0"
5586 [(set_attr "type" "compare")])
5588 ;; We cannot use the "neg" pseudo insn because the Sun assembler
5589 ;; does not know how to make it work for constants.
5591 (define_expand "negdi2"
5592 [(set (match_operand:DI 0 "register_operand" "=r")
5593 (neg:DI (match_operand:DI 1 "register_operand" "r")))]
5596 if (! TARGET_ARCH64)
5598 emit_insn (gen_rtx_PARALLEL
5601 gen_rtx_SET (VOIDmode, operand0,
5602 gen_rtx_NEG (DImode, operand1)),
5603 gen_rtx_CLOBBER (VOIDmode,
5604 gen_rtx_REG (CCmode,
5610 (define_insn_and_split "*negdi2_sp32"
5611 [(set (match_operand:DI 0 "register_operand" "=r")
5612 (neg:DI (match_operand:DI 1 "register_operand" "r")))
5613 (clobber (reg:CC 100))]
5616 "&& reload_completed"
5617 [(parallel [(set (reg:CC_NOOV 100)
5618 (compare:CC_NOOV (minus:SI (const_int 0) (match_dup 5))
5620 (set (match_dup 4) (minus:SI (const_int 0) (match_dup 5)))])
5621 (set (match_dup 2) (minus:SI (minus:SI (const_int 0) (match_dup 3))
5622 (ltu:SI (reg:CC 100) (const_int 0))))]
5623 "operands[2] = gen_highpart (SImode, operands[0]);
5624 operands[3] = gen_highpart (SImode, operands[1]);
5625 operands[4] = gen_lowpart (SImode, operands[0]);
5626 operands[5] = gen_lowpart (SImode, operands[1]);"
5627 [(set_attr "length" "2")])
5629 (define_insn "*negdi2_sp64"
5630 [(set (match_operand:DI 0 "register_operand" "=r")
5631 (neg:DI (match_operand:DI 1 "register_operand" "r")))]
5633 "sub\t%%g0, %1, %0")
5635 (define_insn "negsi2"
5636 [(set (match_operand:SI 0 "register_operand" "=r")
5637 (neg:SI (match_operand:SI 1 "arith_operand" "rI")))]
5639 "sub\t%%g0, %1, %0")
5641 (define_insn "*cmp_cc_neg"
5642 [(set (reg:CC_NOOV 100)
5643 (compare:CC_NOOV (neg:SI (match_operand:SI 0 "arith_operand" "rI"))
5646 "subcc\t%%g0, %0, %%g0"
5647 [(set_attr "type" "compare")])
5649 (define_insn "*cmp_ccx_neg"
5650 [(set (reg:CCX_NOOV 100)
5651 (compare:CCX_NOOV (neg:DI (match_operand:DI 0 "arith_operand" "rI"))
5654 "subcc\t%%g0, %0, %%g0"
5655 [(set_attr "type" "compare")])
5657 (define_insn "*cmp_cc_set_neg"
5658 [(set (reg:CC_NOOV 100)
5659 (compare:CC_NOOV (neg:SI (match_operand:SI 1 "arith_operand" "rI"))
5661 (set (match_operand:SI 0 "register_operand" "=r")
5662 (neg:SI (match_dup 1)))]
5664 "subcc\t%%g0, %1, %0"
5665 [(set_attr "type" "compare")])
5667 (define_insn "*cmp_ccx_set_neg"
5668 [(set (reg:CCX_NOOV 100)
5669 (compare:CCX_NOOV (neg:DI (match_operand:DI 1 "arith_operand" "rI"))
5671 (set (match_operand:DI 0 "register_operand" "=r")
5672 (neg:DI (match_dup 1)))]
5674 "subcc\t%%g0, %1, %0"
5675 [(set_attr "type" "compare")])
5677 ;; We cannot use the "not" pseudo insn because the Sun assembler
5678 ;; does not know how to make it work for constants.
5679 (define_expand "one_cmpl<V64I:mode>2"
5680 [(set (match_operand:V64I 0 "register_operand" "")
5681 (not:V64I (match_operand:V64I 1 "register_operand" "")))]
5685 (define_insn_and_split "*one_cmpl<V64I:mode>2_sp32"
5686 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5687 (not:V64I (match_operand:V64I 1 "register_operand" "r,b")))]
5692 "&& reload_completed
5693 && ((GET_CODE (operands[0]) == REG
5694 && REGNO (operands[0]) < 32)
5695 || (GET_CODE (operands[0]) == SUBREG
5696 && GET_CODE (SUBREG_REG (operands[0])) == REG
5697 && REGNO (SUBREG_REG (operands[0])) < 32))"
5698 [(set (match_dup 2) (not:SI (xor:SI (match_dup 3) (const_int 0))))
5699 (set (match_dup 4) (not:SI (xor:SI (match_dup 5) (const_int 0))))]
5700 "operands[2] = gen_highpart (SImode, operands[0]);
5701 operands[3] = gen_highpart (SImode, operands[1]);
5702 operands[4] = gen_lowpart (SImode, operands[0]);
5703 operands[5] = gen_lowpart (SImode, operands[1]);"
5704 [(set_attr "type" "*,fga")
5705 (set_attr "length" "2,*")
5706 (set_attr "fptype" "*,double")])
5708 (define_insn "*one_cmpl<V64I:mode>2_sp64"
5709 [(set (match_operand:V64I 0 "register_operand" "=r,b")
5710 (not:V64I (match_operand:V64I 1 "arith_operand" "rI,b")))]
5715 [(set_attr "type" "*,fga")
5716 (set_attr "fptype" "*,double")])
5718 (define_insn "one_cmpl<V32I:mode>2"
5719 [(set (match_operand:V32I 0 "register_operand" "=r,d")
5720 (not:V32I (match_operand:V32I 1 "arith_operand" "rI,d")))]
5725 [(set_attr "type" "*,fga")
5726 (set_attr "fptype" "*,single")])
5728 (define_insn "*cmp_cc_not"
5730 (compare:CC (not:SI (match_operand:SI 0 "arith_operand" "rI"))
5733 "xnorcc\t%%g0, %0, %%g0"
5734 [(set_attr "type" "compare")])
5736 (define_insn "*cmp_ccx_not"
5738 (compare:CCX (not:DI (match_operand:DI 0 "arith_operand" "rI"))
5741 "xnorcc\t%%g0, %0, %%g0"
5742 [(set_attr "type" "compare")])
5744 (define_insn "*cmp_cc_set_not"
5746 (compare:CC (not:SI (match_operand:SI 1 "arith_operand" "rI"))
5748 (set (match_operand:SI 0 "register_operand" "=r")
5749 (not:SI (match_dup 1)))]
5751 "xnorcc\t%%g0, %1, %0"
5752 [(set_attr "type" "compare")])
5754 (define_insn "*cmp_ccx_set_not"
5756 (compare:CCX (not:DI (match_operand:DI 1 "arith_operand" "rI"))
5758 (set (match_operand:DI 0 "register_operand" "=r")
5759 (not:DI (match_dup 1)))]
5761 "xnorcc\t%%g0, %1, %0"
5762 [(set_attr "type" "compare")])
5764 (define_insn "*cmp_cc_set"
5765 [(set (match_operand:SI 0 "register_operand" "=r")
5766 (match_operand:SI 1 "register_operand" "r"))
5768 (compare:CC (match_dup 1)
5772 [(set_attr "type" "compare")])
5774 (define_insn "*cmp_ccx_set64"
5775 [(set (match_operand:DI 0 "register_operand" "=r")
5776 (match_operand:DI 1 "register_operand" "r"))
5778 (compare:CCX (match_dup 1)
5782 [(set_attr "type" "compare")])
5785 ;; Floating point arithmetic instructions.
5787 (define_expand "addtf3"
5788 [(set (match_operand:TF 0 "nonimmediate_operand" "")
5789 (plus:TF (match_operand:TF 1 "general_operand" "")
5790 (match_operand:TF 2 "general_operand" "")))]
5791 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
5792 "emit_tfmode_binop (PLUS, operands); DONE;")
5794 (define_insn "*addtf3_hq"
5795 [(set (match_operand:TF 0 "register_operand" "=e")
5796 (plus:TF (match_operand:TF 1 "register_operand" "e")
5797 (match_operand:TF 2 "register_operand" "e")))]
5798 "TARGET_FPU && TARGET_HARD_QUAD"
5800 [(set_attr "type" "fp")])
5802 (define_insn "adddf3"
5803 [(set (match_operand:DF 0 "register_operand" "=e")
5804 (plus:DF (match_operand:DF 1 "register_operand" "e")
5805 (match_operand:DF 2 "register_operand" "e")))]
5808 [(set_attr "type" "fp")
5809 (set_attr "fptype" "double")])
5811 (define_insn "addsf3"
5812 [(set (match_operand:SF 0 "register_operand" "=f")
5813 (plus:SF (match_operand:SF 1 "register_operand" "f")
5814 (match_operand:SF 2 "register_operand" "f")))]
5817 [(set_attr "type" "fp")])
5819 (define_expand "subtf3"
5820 [(set (match_operand:TF 0 "nonimmediate_operand" "")
5821 (minus:TF (match_operand:TF 1 "general_operand" "")
5822 (match_operand:TF 2 "general_operand" "")))]
5823 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
5824 "emit_tfmode_binop (MINUS, operands); DONE;")
5826 (define_insn "*subtf3_hq"
5827 [(set (match_operand:TF 0 "register_operand" "=e")
5828 (minus:TF (match_operand:TF 1 "register_operand" "e")
5829 (match_operand:TF 2 "register_operand" "e")))]
5830 "TARGET_FPU && TARGET_HARD_QUAD"
5832 [(set_attr "type" "fp")])
5834 (define_insn "subdf3"
5835 [(set (match_operand:DF 0 "register_operand" "=e")
5836 (minus:DF (match_operand:DF 1 "register_operand" "e")
5837 (match_operand:DF 2 "register_operand" "e")))]
5840 [(set_attr "type" "fp")
5841 (set_attr "fptype" "double")])
5843 (define_insn "subsf3"
5844 [(set (match_operand:SF 0 "register_operand" "=f")
5845 (minus:SF (match_operand:SF 1 "register_operand" "f")
5846 (match_operand:SF 2 "register_operand" "f")))]
5849 [(set_attr "type" "fp")])
5851 (define_expand "multf3"
5852 [(set (match_operand:TF 0 "nonimmediate_operand" "")
5853 (mult:TF (match_operand:TF 1 "general_operand" "")
5854 (match_operand:TF 2 "general_operand" "")))]
5855 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
5856 "emit_tfmode_binop (MULT, operands); DONE;")
5858 (define_insn "*multf3_hq"
5859 [(set (match_operand:TF 0 "register_operand" "=e")
5860 (mult:TF (match_operand:TF 1 "register_operand" "e")
5861 (match_operand:TF 2 "register_operand" "e")))]
5862 "TARGET_FPU && TARGET_HARD_QUAD"
5864 [(set_attr "type" "fpmul")])
5866 (define_insn "muldf3"
5867 [(set (match_operand:DF 0 "register_operand" "=e")
5868 (mult:DF (match_operand:DF 1 "register_operand" "e")
5869 (match_operand:DF 2 "register_operand" "e")))]
5872 [(set_attr "type" "fpmul")
5873 (set_attr "fptype" "double")])
5875 (define_insn "mulsf3"
5876 [(set (match_operand:SF 0 "register_operand" "=f")
5877 (mult:SF (match_operand:SF 1 "register_operand" "f")
5878 (match_operand:SF 2 "register_operand" "f")))]
5881 [(set_attr "type" "fpmul")])
5883 (define_insn "*muldf3_extend"
5884 [(set (match_operand:DF 0 "register_operand" "=e")
5885 (mult:DF (float_extend:DF (match_operand:SF 1 "register_operand" "f"))
5886 (float_extend:DF (match_operand:SF 2 "register_operand" "f"))))]
5887 "(TARGET_V8 || TARGET_V9) && TARGET_FPU"
5888 "fsmuld\t%1, %2, %0"
5889 [(set_attr "type" "fpmul")
5890 (set_attr "fptype" "double")])
5892 (define_insn "*multf3_extend"
5893 [(set (match_operand:TF 0 "register_operand" "=e")
5894 (mult:TF (float_extend:TF (match_operand:DF 1 "register_operand" "e"))
5895 (float_extend:TF (match_operand:DF 2 "register_operand" "e"))))]
5896 "(TARGET_V8 || TARGET_V9) && TARGET_FPU && TARGET_HARD_QUAD"
5897 "fdmulq\t%1, %2, %0"
5898 [(set_attr "type" "fpmul")])
5900 (define_expand "divtf3"
5901 [(set (match_operand:TF 0 "nonimmediate_operand" "")
5902 (div:TF (match_operand:TF 1 "general_operand" "")
5903 (match_operand:TF 2 "general_operand" "")))]
5904 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
5905 "emit_tfmode_binop (DIV, operands); DONE;")
5907 ;; don't have timing for quad-prec. divide.
5908 (define_insn "*divtf3_hq"
5909 [(set (match_operand:TF 0 "register_operand" "=e")
5910 (div:TF (match_operand:TF 1 "register_operand" "e")
5911 (match_operand:TF 2 "register_operand" "e")))]
5912 "TARGET_FPU && TARGET_HARD_QUAD"
5914 [(set_attr "type" "fpdivd")])
5916 (define_insn "divdf3"
5917 [(set (match_operand:DF 0 "register_operand" "=e")
5918 (div:DF (match_operand:DF 1 "register_operand" "e")
5919 (match_operand:DF 2 "register_operand" "e")))]
5922 [(set_attr "type" "fpdivd")
5923 (set_attr "fptype" "double")])
5925 (define_insn "divsf3"
5926 [(set (match_operand:SF 0 "register_operand" "=f")
5927 (div:SF (match_operand:SF 1 "register_operand" "f")
5928 (match_operand:SF 2 "register_operand" "f")))]
5931 [(set_attr "type" "fpdivs")])
5933 (define_expand "negtf2"
5934 [(set (match_operand:TF 0 "register_operand" "=e,e")
5935 (neg:TF (match_operand:TF 1 "register_operand" "0,e")))]
5939 (define_insn_and_split "*negtf2_notv9"
5940 [(set (match_operand:TF 0 "register_operand" "=e,e")
5941 (neg:TF (match_operand:TF 1 "register_operand" "0,e")))]
5942 ; We don't use quad float insns here so we don't need TARGET_HARD_QUAD.
5948 "&& reload_completed
5949 && sparc_absnegfloat_split_legitimate (operands[0], operands[1])"
5950 [(set (match_dup 2) (neg:SF (match_dup 3)))
5951 (set (match_dup 4) (match_dup 5))
5952 (set (match_dup 6) (match_dup 7))]
5953 "operands[2] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]));
5954 operands[3] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]));
5955 operands[4] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]) + 1);
5956 operands[5] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]) + 1);
5957 operands[6] = gen_rtx_raw_REG (DFmode, REGNO (operands[0]) + 2);
5958 operands[7] = gen_rtx_raw_REG (DFmode, REGNO (operands[1]) + 2);"
5959 [(set_attr "type" "fpmove,*")
5960 (set_attr "length" "*,2")])
5962 (define_insn_and_split "*negtf2_v9"
5963 [(set (match_operand:TF 0 "register_operand" "=e,e")
5964 (neg:TF (match_operand:TF 1 "register_operand" "0,e")))]
5965 ; We don't use quad float insns here so we don't need TARGET_HARD_QUAD.
5966 "TARGET_FPU && TARGET_V9"
5970 "&& reload_completed
5971 && sparc_absnegfloat_split_legitimate (operands[0], operands[1])"
5972 [(set (match_dup 2) (neg:DF (match_dup 3)))
5973 (set (match_dup 4) (match_dup 5))]
5974 "operands[2] = gen_rtx_raw_REG (DFmode, REGNO (operands[0]));
5975 operands[3] = gen_rtx_raw_REG (DFmode, REGNO (operands[1]));
5976 operands[4] = gen_rtx_raw_REG (DFmode, REGNO (operands[0]) + 2);
5977 operands[5] = gen_rtx_raw_REG (DFmode, REGNO (operands[1]) + 2);"
5978 [(set_attr "type" "fpmove,*")
5979 (set_attr "length" "*,2")
5980 (set_attr "fptype" "double")])
5982 (define_expand "negdf2"
5983 [(set (match_operand:DF 0 "register_operand" "")
5984 (neg:DF (match_operand:DF 1 "register_operand" "")))]
5988 (define_insn_and_split "*negdf2_notv9"
5989 [(set (match_operand:DF 0 "register_operand" "=e,e")
5990 (neg:DF (match_operand:DF 1 "register_operand" "0,e")))]
5991 "TARGET_FPU && ! TARGET_V9"
5995 "&& reload_completed
5996 && sparc_absnegfloat_split_legitimate (operands[0], operands[1])"
5997 [(set (match_dup 2) (neg:SF (match_dup 3)))
5998 (set (match_dup 4) (match_dup 5))]
5999 "operands[2] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]));
6000 operands[3] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]));
6001 operands[4] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]) + 1);
6002 operands[5] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]) + 1);"
6003 [(set_attr "type" "fpmove,*")
6004 (set_attr "length" "*,2")])
6006 (define_insn "*negdf2_v9"
6007 [(set (match_operand:DF 0 "register_operand" "=e")
6008 (neg:DF (match_operand:DF 1 "register_operand" "e")))]
6009 "TARGET_FPU && TARGET_V9"
6011 [(set_attr "type" "fpmove")
6012 (set_attr "fptype" "double")])
6014 (define_insn "negsf2"
6015 [(set (match_operand:SF 0 "register_operand" "=f")
6016 (neg:SF (match_operand:SF 1 "register_operand" "f")))]
6019 [(set_attr "type" "fpmove")])
6021 (define_expand "abstf2"
6022 [(set (match_operand:TF 0 "register_operand" "")
6023 (abs:TF (match_operand:TF 1 "register_operand" "")))]
6027 (define_insn_and_split "*abstf2_notv9"
6028 [(set (match_operand:TF 0 "register_operand" "=e,e")
6029 (abs:TF (match_operand:TF 1 "register_operand" "0,e")))]
6030 ; We don't use quad float insns here so we don't need TARGET_HARD_QUAD.
6031 "TARGET_FPU && ! TARGET_V9"
6035 "&& reload_completed
6036 && sparc_absnegfloat_split_legitimate (operands[0], operands[1])"
6037 [(set (match_dup 2) (abs:SF (match_dup 3)))
6038 (set (match_dup 4) (match_dup 5))
6039 (set (match_dup 6) (match_dup 7))]
6040 "operands[2] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]));
6041 operands[3] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]));
6042 operands[4] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]) + 1);
6043 operands[5] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]) + 1);
6044 operands[6] = gen_rtx_raw_REG (DFmode, REGNO (operands[0]) + 2);
6045 operands[7] = gen_rtx_raw_REG (DFmode, REGNO (operands[1]) + 2);"
6046 [(set_attr "type" "fpmove,*")
6047 (set_attr "length" "*,2")])
6049 (define_insn "*abstf2_hq_v9"
6050 [(set (match_operand:TF 0 "register_operand" "=e,e")
6051 (abs:TF (match_operand:TF 1 "register_operand" "0,e")))]
6052 "TARGET_FPU && TARGET_V9 && TARGET_HARD_QUAD"
6056 [(set_attr "type" "fpmove")
6057 (set_attr "fptype" "double,*")])
6059 (define_insn_and_split "*abstf2_v9"
6060 [(set (match_operand:TF 0 "register_operand" "=e,e")
6061 (abs:TF (match_operand:TF 1 "register_operand" "0,e")))]
6062 "TARGET_FPU && TARGET_V9 && !TARGET_HARD_QUAD"
6066 "&& reload_completed
6067 && sparc_absnegfloat_split_legitimate (operands[0], operands[1])"
6068 [(set (match_dup 2) (abs:DF (match_dup 3)))
6069 (set (match_dup 4) (match_dup 5))]
6070 "operands[2] = gen_rtx_raw_REG (DFmode, REGNO (operands[0]));
6071 operands[3] = gen_rtx_raw_REG (DFmode, REGNO (operands[1]));
6072 operands[4] = gen_rtx_raw_REG (DFmode, REGNO (operands[0]) + 2);
6073 operands[5] = gen_rtx_raw_REG (DFmode, REGNO (operands[1]) + 2);"
6074 [(set_attr "type" "fpmove,*")
6075 (set_attr "length" "*,2")
6076 (set_attr "fptype" "double,*")])
6078 (define_expand "absdf2"
6079 [(set (match_operand:DF 0 "register_operand" "")
6080 (abs:DF (match_operand:DF 1 "register_operand" "")))]
6084 (define_insn_and_split "*absdf2_notv9"
6085 [(set (match_operand:DF 0 "register_operand" "=e,e")
6086 (abs:DF (match_operand:DF 1 "register_operand" "0,e")))]
6087 "TARGET_FPU && ! TARGET_V9"
6091 "&& reload_completed
6092 && sparc_absnegfloat_split_legitimate (operands[0], operands[1])"
6093 [(set (match_dup 2) (abs:SF (match_dup 3)))
6094 (set (match_dup 4) (match_dup 5))]
6095 "operands[2] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]));
6096 operands[3] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]));
6097 operands[4] = gen_rtx_raw_REG (SFmode, REGNO (operands[0]) + 1);
6098 operands[5] = gen_rtx_raw_REG (SFmode, REGNO (operands[1]) + 1);"
6099 [(set_attr "type" "fpmove,*")
6100 (set_attr "length" "*,2")])
6102 (define_insn "*absdf2_v9"
6103 [(set (match_operand:DF 0 "register_operand" "=e")
6104 (abs:DF (match_operand:DF 1 "register_operand" "e")))]
6105 "TARGET_FPU && TARGET_V9"
6107 [(set_attr "type" "fpmove")
6108 (set_attr "fptype" "double")])
6110 (define_insn "abssf2"
6111 [(set (match_operand:SF 0 "register_operand" "=f")
6112 (abs:SF (match_operand:SF 1 "register_operand" "f")))]
6115 [(set_attr "type" "fpmove")])
6117 (define_expand "sqrttf2"
6118 [(set (match_operand:TF 0 "nonimmediate_operand" "")
6119 (sqrt:TF (match_operand:TF 1 "general_operand" "")))]
6120 "TARGET_FPU && (TARGET_HARD_QUAD || TARGET_ARCH64)"
6121 "emit_tfmode_unop (SQRT, operands); DONE;")
6123 (define_insn "*sqrttf2_hq"
6124 [(set (match_operand:TF 0 "register_operand" "=e")
6125 (sqrt:TF (match_operand:TF 1 "register_operand" "e")))]
6126 "TARGET_FPU && TARGET_HARD_QUAD"
6128 [(set_attr "type" "fpsqrtd")])
6130 (define_insn "sqrtdf2"
6131 [(set (match_operand:DF 0 "register_operand" "=e")
6132 (sqrt:DF (match_operand:DF 1 "register_operand" "e")))]
6135 [(set_attr "type" "fpsqrtd")
6136 (set_attr "fptype" "double")])
6138 (define_insn "sqrtsf2"
6139 [(set (match_operand:SF 0 "register_operand" "=f")
6140 (sqrt:SF (match_operand:SF 1 "register_operand" "f")))]
6143 [(set_attr "type" "fpsqrts")])
6146 ;; Arithmetic shift instructions.
6148 (define_insn "ashlsi3"
6149 [(set (match_operand:SI 0 "register_operand" "=r")
6150 (ashift:SI (match_operand:SI 1 "register_operand" "r")
6151 (match_operand:SI 2 "arith_operand" "rI")))]
6154 if (GET_CODE (operands[2]) == CONST_INT)
6155 operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
6156 return "sll\t%1, %2, %0";
6159 (if_then_else (match_operand 2 "const_one_operand" "")
6160 (const_string "ialu") (const_string "shift")))])
6162 (define_expand "ashldi3"
6163 [(set (match_operand:DI 0 "register_operand" "=r")
6164 (ashift:DI (match_operand:DI 1 "register_operand" "r")
6165 (match_operand:SI 2 "arith_operand" "rI")))]
6166 "TARGET_ARCH64 || TARGET_V8PLUS"
6168 if (! TARGET_ARCH64)
6170 if (GET_CODE (operands[2]) == CONST_INT)
6172 emit_insn (gen_ashldi3_v8plus (operands[0], operands[1], operands[2]));
6177 (define_insn "*ashldi3_sp64"
6178 [(set (match_operand:DI 0 "register_operand" "=r")
6179 (ashift:DI (match_operand:DI 1 "register_operand" "r")
6180 (match_operand:SI 2 "arith_operand" "rI")))]
6183 if (GET_CODE (operands[2]) == CONST_INT)
6184 operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
6185 return "sllx\t%1, %2, %0";
6188 (if_then_else (match_operand 2 "const_one_operand" "")
6189 (const_string "ialu") (const_string "shift")))])
6192 (define_insn "ashldi3_v8plus"
6193 [(set (match_operand:DI 0 "register_operand" "=&h,&h,r")
6194 (ashift:DI (match_operand:DI 1 "arith_operand" "rI,0,rI")
6195 (match_operand:SI 2 "arith_operand" "rI,rI,rI")))
6196 (clobber (match_scratch:SI 3 "=X,X,&h"))]
6198 "* return output_v8plus_shift (operands, insn, \"sllx\");"
6199 [(set_attr "type" "multi")
6200 (set_attr "length" "5,5,6")])
6202 ;; Optimize (1LL<<x)-1
6203 ;; XXX this also needs to be fixed to handle equal subregs
6204 ;; XXX first before we could re-enable it.
6206 ; [(set (match_operand:DI 0 "register_operand" "=h")
6207 ; (plus:DI (ashift:DI (const_int 1)
6208 ; (match_operand:SI 1 "arith_operand" "rI"))
6210 ; "0 && TARGET_V8PLUS"
6212 ; if (GET_CODE (operands[1]) == REG && REGNO (operands[1]) == REGNO (operands[0]))
6213 ; return "mov\t1, %L0\;sllx\t%L0, %1, %L0\;sub\t%L0, 1, %L0\;srlx\t%L0, 32, %H0";
6214 ; return "mov\t1, %H0\;sllx\t%H0, %1, %L0\;sub\t%L0, 1, %L0\;srlx\t%L0, 32, %H0";
6216 ; [(set_attr "type" "multi")
6217 ; (set_attr "length" "4")])
6219 (define_insn "*cmp_cc_ashift_1"
6220 [(set (reg:CC_NOOV 100)
6221 (compare:CC_NOOV (ashift:SI (match_operand:SI 0 "register_operand" "r")
6225 "addcc\t%0, %0, %%g0"
6226 [(set_attr "type" "compare")])
6228 (define_insn "*cmp_cc_set_ashift_1"
6229 [(set (reg:CC_NOOV 100)
6230 (compare:CC_NOOV (ashift:SI (match_operand:SI 1 "register_operand" "r")
6233 (set (match_operand:SI 0 "register_operand" "=r")
6234 (ashift:SI (match_dup 1) (const_int 1)))]
6237 [(set_attr "type" "compare")])
6239 (define_insn "ashrsi3"
6240 [(set (match_operand:SI 0 "register_operand" "=r")
6241 (ashiftrt:SI (match_operand:SI 1 "register_operand" "r")
6242 (match_operand:SI 2 "arith_operand" "rI")))]
6245 if (GET_CODE (operands[2]) == CONST_INT)
6246 operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
6247 return "sra\t%1, %2, %0";
6249 [(set_attr "type" "shift")])
6251 (define_insn "*ashrsi3_extend"
6252 [(set (match_operand:DI 0 "register_operand" "=r")
6253 (sign_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "r")
6254 (match_operand:SI 2 "arith_operand" "r"))))]
6257 [(set_attr "type" "shift")])
6259 ;; This handles the case as above, but with constant shift instead of
6260 ;; register. Combiner "simplifies" it for us a little bit though.
6261 (define_insn "*ashrsi3_extend2"
6262 [(set (match_operand:DI 0 "register_operand" "=r")
6263 (ashiftrt:DI (ashift:DI (subreg:DI (match_operand:SI 1 "register_operand" "r") 0)
6265 (match_operand:SI 2 "small_int_operand" "I")))]
6266 "TARGET_ARCH64 && INTVAL (operands[2]) >= 32 && INTVAL (operands[2]) < 64"
6268 operands[2] = GEN_INT (INTVAL (operands[2]) - 32);
6269 return "sra\t%1, %2, %0";
6271 [(set_attr "type" "shift")])
6273 (define_expand "ashrdi3"
6274 [(set (match_operand:DI 0 "register_operand" "=r")
6275 (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
6276 (match_operand:SI 2 "arith_operand" "rI")))]
6277 "TARGET_ARCH64 || TARGET_V8PLUS"
6279 if (! TARGET_ARCH64)
6281 if (GET_CODE (operands[2]) == CONST_INT)
6282 FAIL; /* prefer generic code in this case */
6283 emit_insn (gen_ashrdi3_v8plus (operands[0], operands[1], operands[2]));
6288 (define_insn "*ashrdi3_sp64"
6289 [(set (match_operand:DI 0 "register_operand" "=r")
6290 (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
6291 (match_operand:SI 2 "arith_operand" "rI")))]
6295 if (GET_CODE (operands[2]) == CONST_INT)
6296 operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
6297 return "srax\t%1, %2, %0";
6299 [(set_attr "type" "shift")])
6302 (define_insn "ashrdi3_v8plus"
6303 [(set (match_operand:DI 0 "register_operand" "=&h,&h,r")
6304 (ashiftrt:DI (match_operand:DI 1 "arith_operand" "rI,0,rI")
6305 (match_operand:SI 2 "arith_operand" "rI,rI,rI")))
6306 (clobber (match_scratch:SI 3 "=X,X,&h"))]
6308 "* return output_v8plus_shift (operands, insn, \"srax\");"
6309 [(set_attr "type" "multi")
6310 (set_attr "length" "5,5,6")])
6312 (define_insn "lshrsi3"
6313 [(set (match_operand:SI 0 "register_operand" "=r")
6314 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
6315 (match_operand:SI 2 "arith_operand" "rI")))]
6318 if (GET_CODE (operands[2]) == CONST_INT)
6319 operands[2] = GEN_INT (INTVAL (operands[2]) & 0x1f);
6320 return "srl\t%1, %2, %0";
6322 [(set_attr "type" "shift")])
6324 ;; This handles the case where
6325 ;; (zero_extend:DI (lshiftrt:SI (match_operand:SI) (match_operand:SI))),
6326 ;; but combiner "simplifies" it for us.
6327 (define_insn "*lshrsi3_extend"
6328 [(set (match_operand:DI 0 "register_operand" "=r")
6329 (and:DI (subreg:DI (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
6330 (match_operand:SI 2 "arith_operand" "r")) 0)
6331 (match_operand 3 "const_int_operand" "")))]
6332 "TARGET_ARCH64 && (unsigned HOST_WIDE_INT) INTVAL (operands[3]) == 0xffffffff"
6334 [(set_attr "type" "shift")])
6336 ;; This handles the case where
6337 ;; (lshiftrt:DI (zero_extend:DI (match_operand:SI)) (const_int >=0 < 32))
6338 ;; but combiner "simplifies" it for us.
6339 (define_insn "*lshrsi3_extend2"
6340 [(set (match_operand:DI 0 "register_operand" "=r")
6341 (zero_extract:DI (subreg:DI (match_operand:SI 1 "register_operand" "r") 0)
6342 (match_operand 2 "small_int_operand" "I")
6344 "TARGET_ARCH64 && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) < 32"
6346 operands[2] = GEN_INT (32 - INTVAL (operands[2]));
6347 return "srl\t%1, %2, %0";
6349 [(set_attr "type" "shift")])
6351 (define_expand "lshrdi3"
6352 [(set (match_operand:DI 0 "register_operand" "=r")
6353 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
6354 (match_operand:SI 2 "arith_operand" "rI")))]
6355 "TARGET_ARCH64 || TARGET_V8PLUS"
6357 if (! TARGET_ARCH64)
6359 if (GET_CODE (operands[2]) == CONST_INT)
6361 emit_insn (gen_lshrdi3_v8plus (operands[0], operands[1], operands[2]));
6366 (define_insn "*lshrdi3_sp64"
6367 [(set (match_operand:DI 0 "register_operand" "=r")
6368 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
6369 (match_operand:SI 2 "arith_operand" "rI")))]
6372 if (GET_CODE (operands[2]) == CONST_INT)
6373 operands[2] = GEN_INT (INTVAL (operands[2]) & 0x3f);
6374 return "srlx\t%1, %2, %0";
6376 [(set_attr "type" "shift")])
6379 (define_insn "lshrdi3_v8plus"
6380 [(set (match_operand:DI 0 "register_operand" "=&h,&h,r")
6381 (lshiftrt:DI (match_operand:DI 1 "arith_operand" "rI,0,rI")
6382 (match_operand:SI 2 "arith_operand" "rI,rI,rI")))
6383 (clobber (match_scratch:SI 3 "=X,X,&h"))]
6385 "* return output_v8plus_shift (operands, insn, \"srlx\");"
6386 [(set_attr "type" "multi")
6387 (set_attr "length" "5,5,6")])
6390 [(set (match_operand:SI 0 "register_operand" "=r")
6391 (ashiftrt:SI (subreg:SI (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
6393 (match_operand:SI 2 "small_int_operand" "I")))]
6394 "TARGET_ARCH64 && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) < 32"
6396 operands[2] = GEN_INT (INTVAL (operands[2]) + 32);
6397 return "srax\t%1, %2, %0";
6399 [(set_attr "type" "shift")])
6402 [(set (match_operand:SI 0 "register_operand" "=r")
6403 (lshiftrt:SI (subreg:SI (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
6405 (match_operand:SI 2 "small_int_operand" "I")))]
6406 "TARGET_ARCH64 && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) < 32"
6408 operands[2] = GEN_INT (INTVAL (operands[2]) + 32);
6409 return "srlx\t%1, %2, %0";
6411 [(set_attr "type" "shift")])
6414 [(set (match_operand:SI 0 "register_operand" "=r")
6415 (ashiftrt:SI (subreg:SI (ashiftrt:DI (match_operand:DI 1 "register_operand" "r")
6416 (match_operand:SI 2 "small_int_operand" "I")) 4)
6417 (match_operand:SI 3 "small_int_operand" "I")))]
6419 && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) >= 32
6420 && (unsigned HOST_WIDE_INT) INTVAL (operands[3]) < 32
6421 && (unsigned HOST_WIDE_INT) (INTVAL (operands[2]) + INTVAL (operands[3])) < 64"
6423 operands[2] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[3]));
6425 return "srax\t%1, %2, %0";
6427 [(set_attr "type" "shift")])
6430 [(set (match_operand:SI 0 "register_operand" "=r")
6431 (lshiftrt:SI (subreg:SI (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
6432 (match_operand:SI 2 "small_int_operand" "I")) 4)
6433 (match_operand:SI 3 "small_int_operand" "I")))]
6435 && (unsigned HOST_WIDE_INT) INTVAL (operands[2]) >= 32
6436 && (unsigned HOST_WIDE_INT) INTVAL (operands[3]) < 32
6437 && (unsigned HOST_WIDE_INT) (INTVAL (operands[2]) + INTVAL (operands[3])) < 64"
6439 operands[2] = GEN_INT (INTVAL (operands[2]) + INTVAL (operands[3]));
6441 return "srlx\t%1, %2, %0";
6443 [(set_attr "type" "shift")])
6446 ;; Unconditional and other jump instructions.
6449 [(set (pc) (label_ref (match_operand 0 "" "")))]
6451 "* return output_ubranch (operands[0], 0, insn);"
6452 [(set_attr "type" "uncond_branch")])
6454 (define_expand "tablejump"
6455 [(parallel [(set (pc) (match_operand 0 "register_operand" "r"))
6456 (use (label_ref (match_operand 1 "" "")))])]
6459 gcc_assert (GET_MODE (operands[0]) == CASE_VECTOR_MODE);
6461 /* In pic mode, our address differences are against the base of the
6462 table. Add that base value back in; CSE ought to be able to combine
6463 the two address loads. */
6467 tmp = gen_rtx_LABEL_REF (Pmode, operands[1]);
6469 if (CASE_VECTOR_MODE != Pmode)
6470 tmp2 = gen_rtx_SIGN_EXTEND (Pmode, tmp2);
6471 tmp = gen_rtx_PLUS (Pmode, tmp2, tmp);
6472 operands[0] = memory_address (Pmode, tmp);
6476 (define_insn "*tablejump_sp32"
6477 [(set (pc) (match_operand:SI 0 "address_operand" "p"))
6478 (use (label_ref (match_operand 1 "" "")))]
6481 [(set_attr "type" "uncond_branch")])
6483 (define_insn "*tablejump_sp64"
6484 [(set (pc) (match_operand:DI 0 "address_operand" "p"))
6485 (use (label_ref (match_operand 1 "" "")))]
6488 [(set_attr "type" "uncond_branch")])
6491 ;; Jump to subroutine instructions.
6493 (define_expand "call"
6494 ;; Note that this expression is not used for generating RTL.
6495 ;; All the RTL is generated explicitly below.
6496 [(call (match_operand 0 "call_operand" "")
6497 (match_operand 3 "" "i"))]
6498 ;; operands[2] is next_arg_register
6499 ;; operands[3] is struct_value_size_rtx.
6504 gcc_assert (MEM_P (operands[0]) && GET_MODE (operands[0]) == FUNCTION_MODE);
6506 gcc_assert (GET_CODE (operands[3]) == CONST_INT);
6508 if (GET_CODE (XEXP (operands[0], 0)) == LABEL_REF)
6510 /* This is really a PIC sequence. We want to represent
6511 it as a funny jump so its delay slots can be filled.
6513 ??? But if this really *is* a CALL, will not it clobber the
6514 call-clobbered registers? We lose this if it is a JUMP_INSN.
6515 Why cannot we have delay slots filled if it were a CALL? */
6517 /* We accept negative sizes for untyped calls. */
6518 if (! TARGET_ARCH64 && INTVAL (operands[3]) != 0)
6523 gen_rtx_SET (VOIDmode, pc_rtx, XEXP (operands[0], 0)),
6525 gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 15)))));
6531 gen_rtx_SET (VOIDmode, pc_rtx, XEXP (operands[0], 0)),
6532 gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 15)))));
6536 fn_rtx = operands[0];
6538 /* We accept negative sizes for untyped calls. */
6539 if (! TARGET_ARCH64 && INTVAL (operands[3]) != 0)
6540 sparc_emit_call_insn
6543 gen_rtvec (3, gen_rtx_CALL (VOIDmode, fn_rtx, const0_rtx),
6545 gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 15)))),
6548 sparc_emit_call_insn
6551 gen_rtvec (2, gen_rtx_CALL (VOIDmode, fn_rtx, const0_rtx),
6552 gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 15)))),
6560 ;; We can't use the same pattern for these two insns, because then registers
6561 ;; in the address may not be properly reloaded.
6563 (define_insn "*call_address_sp32"
6564 [(call (mem:SI (match_operand:SI 0 "address_operand" "p"))
6565 (match_operand 1 "" ""))
6566 (clobber (reg:SI 15))]
6567 ;;- Do not use operand 1 for most machines.
6570 [(set_attr "type" "call")])
6572 (define_insn "*call_symbolic_sp32"
6573 [(call (mem:SI (match_operand:SI 0 "symbolic_operand" "s"))
6574 (match_operand 1 "" ""))
6575 (clobber (reg:SI 15))]
6576 ;;- Do not use operand 1 for most machines.
6579 [(set_attr "type" "call")])
6581 (define_insn "*call_address_sp64"
6582 [(call (mem:DI (match_operand:DI 0 "address_operand" "p"))
6583 (match_operand 1 "" ""))
6584 (clobber (reg:DI 15))]
6585 ;;- Do not use operand 1 for most machines.
6588 [(set_attr "type" "call")])
6590 (define_insn "*call_symbolic_sp64"
6591 [(call (mem:DI (match_operand:DI 0 "symbolic_operand" "s"))
6592 (match_operand 1 "" ""))
6593 (clobber (reg:DI 15))]
6594 ;;- Do not use operand 1 for most machines.
6597 [(set_attr "type" "call")])
6599 ;; This is a call that wants a structure value.
6600 ;; There is no such critter for v9 (??? we may need one anyway).
6601 (define_insn "*call_address_struct_value_sp32"
6602 [(call (mem:SI (match_operand:SI 0 "address_operand" "p"))
6603 (match_operand 1 "" ""))
6604 (match_operand 2 "immediate_operand" "")
6605 (clobber (reg:SI 15))]
6606 ;;- Do not use operand 1 for most machines.
6607 "! TARGET_ARCH64 && GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) > 0"
6609 operands[2] = GEN_INT (INTVAL (operands[2]) & 0xfff);
6610 return "call\t%a0, %1\n\t nop\n\tunimp\t%2";
6612 [(set_attr "type" "call_no_delay_slot")
6613 (set_attr "length" "3")])
6615 ;; This is a call that wants a structure value.
6616 ;; There is no such critter for v9 (??? we may need one anyway).
6617 (define_insn "*call_symbolic_struct_value_sp32"
6618 [(call (mem:SI (match_operand:SI 0 "symbolic_operand" "s"))
6619 (match_operand 1 "" ""))
6620 (match_operand 2 "immediate_operand" "")
6621 (clobber (reg:SI 15))]
6622 ;;- Do not use operand 1 for most machines.
6623 "! TARGET_ARCH64 && GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) > 0"
6625 operands[2] = GEN_INT (INTVAL (operands[2]) & 0xfff);
6626 return "call\t%a0, %1\n\t nop\n\tunimp\t%2";
6628 [(set_attr "type" "call_no_delay_slot")
6629 (set_attr "length" "3")])
6631 ;; This is a call that may want a structure value. This is used for
6633 (define_insn "*call_address_untyped_struct_value_sp32"
6634 [(call (mem:SI (match_operand:SI 0 "address_operand" "p"))
6635 (match_operand 1 "" ""))
6636 (match_operand 2 "immediate_operand" "")
6637 (clobber (reg:SI 15))]
6638 ;;- Do not use operand 1 for most machines.
6639 "! TARGET_ARCH64 && GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0"
6640 "call\t%a0, %1\n\t nop\n\tnop"
6641 [(set_attr "type" "call_no_delay_slot")
6642 (set_attr "length" "3")])
6644 ;; This is a call that may want a structure value. This is used for
6646 (define_insn "*call_symbolic_untyped_struct_value_sp32"
6647 [(call (mem:SI (match_operand:SI 0 "symbolic_operand" "s"))
6648 (match_operand 1 "" ""))
6649 (match_operand 2 "immediate_operand" "")
6650 (clobber (reg:SI 15))]
6651 ;;- Do not use operand 1 for most machines.
6652 "! TARGET_ARCH64 && GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0"
6653 "call\t%a0, %1\n\t nop\n\tnop"
6654 [(set_attr "type" "call_no_delay_slot")
6655 (set_attr "length" "3")])
6657 (define_expand "call_value"
6658 ;; Note that this expression is not used for generating RTL.
6659 ;; All the RTL is generated explicitly below.
6660 [(set (match_operand 0 "register_operand" "=rf")
6661 (call (match_operand 1 "" "")
6662 (match_operand 4 "" "")))]
6663 ;; operand 2 is stack_size_rtx
6664 ;; operand 3 is next_arg_register
6670 gcc_assert (MEM_P (operands[1]) && GET_MODE (operands[1]) == FUNCTION_MODE);
6672 fn_rtx = operands[1];
6675 gen_rtx_SET (VOIDmode, operands[0],
6676 gen_rtx_CALL (VOIDmode, fn_rtx, const0_rtx)),
6677 gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (Pmode, 15)));
6679 sparc_emit_call_insn (gen_rtx_PARALLEL (VOIDmode, vec), XEXP (fn_rtx, 0));
6684 (define_insn "*call_value_address_sp32"
6685 [(set (match_operand 0 "" "=rf")
6686 (call (mem:SI (match_operand:SI 1 "address_operand" "p"))
6687 (match_operand 2 "" "")))
6688 (clobber (reg:SI 15))]
6689 ;;- Do not use operand 2 for most machines.
6692 [(set_attr "type" "call")])
6694 (define_insn "*call_value_symbolic_sp32"
6695 [(set (match_operand 0 "" "=rf")
6696 (call (mem:SI (match_operand:SI 1 "symbolic_operand" "s"))
6697 (match_operand 2 "" "")))
6698 (clobber (reg:SI 15))]
6699 ;;- Do not use operand 2 for most machines.
6702 [(set_attr "type" "call")])
6704 (define_insn "*call_value_address_sp64"
6705 [(set (match_operand 0 "" "")
6706 (call (mem:DI (match_operand:DI 1 "address_operand" "p"))
6707 (match_operand 2 "" "")))
6708 (clobber (reg:DI 15))]
6709 ;;- Do not use operand 2 for most machines.
6712 [(set_attr "type" "call")])
6714 (define_insn "*call_value_symbolic_sp64"
6715 [(set (match_operand 0 "" "")
6716 (call (mem:DI (match_operand:DI 1 "symbolic_operand" "s"))
6717 (match_operand 2 "" "")))
6718 (clobber (reg:DI 15))]
6719 ;;- Do not use operand 2 for most machines.
6722 [(set_attr "type" "call")])
6724 (define_expand "untyped_call"
6725 [(parallel [(call (match_operand 0 "" "")
6727 (match_operand:BLK 1 "memory_operand" "")
6728 (match_operand 2 "" "")])]
6731 rtx valreg1 = gen_rtx_REG (DImode, 8);
6732 rtx valreg2 = gen_rtx_REG (TARGET_ARCH64 ? TFmode : DFmode, 32);
6733 rtx result = operands[1];
6735 /* Pass constm1 to indicate that it may expect a structure value, but
6736 we don't know what size it is. */
6737 emit_call_insn (GEN_CALL (operands[0], const0_rtx, NULL, constm1_rtx));
6739 /* Save the function value registers. */
6740 emit_move_insn (adjust_address (result, DImode, 0), valreg1);
6741 emit_move_insn (adjust_address (result, TARGET_ARCH64 ? TFmode : DFmode, 8),
6744 /* The optimizer does not know that the call sets the function value
6745 registers we stored in the result block. We avoid problems by
6746 claiming that all hard registers are used and clobbered at this
6748 emit_insn (gen_blockage ());
6753 ;; Tail call instructions.
6755 (define_expand "sibcall"
6756 [(parallel [(call (match_operand 0 "call_operand" "") (const_int 0))
6761 (define_insn "*sibcall_symbolic_sp32"
6762 [(call (mem:SI (match_operand:SI 0 "symbolic_operand" "s"))
6763 (match_operand 1 "" ""))
6766 "* return output_sibcall(insn, operands[0]);"
6767 [(set_attr "type" "sibcall")])
6769 (define_insn "*sibcall_symbolic_sp64"
6770 [(call (mem:DI (match_operand:DI 0 "symbolic_operand" "s"))
6771 (match_operand 1 "" ""))
6774 "* return output_sibcall(insn, operands[0]);"
6775 [(set_attr "type" "sibcall")])
6777 (define_expand "sibcall_value"
6778 [(parallel [(set (match_operand 0 "register_operand" "=rf")
6779 (call (match_operand 1 "" "") (const_int 0)))
6784 (define_insn "*sibcall_value_symbolic_sp32"
6785 [(set (match_operand 0 "" "=rf")
6786 (call (mem:SI (match_operand:SI 1 "symbolic_operand" "s"))
6787 (match_operand 2 "" "")))
6790 "* return output_sibcall(insn, operands[1]);"
6791 [(set_attr "type" "sibcall")])
6793 (define_insn "*sibcall_value_symbolic_sp64"
6794 [(set (match_operand 0 "" "")
6795 (call (mem:DI (match_operand:DI 1 "symbolic_operand" "s"))
6796 (match_operand 2 "" "")))
6799 "* return output_sibcall(insn, operands[1]);"
6800 [(set_attr "type" "sibcall")])
6803 ;; Special instructions.
6805 (define_expand "prologue"
6809 sparc_expand_prologue ();
6813 ;; The "save register window" insn is modelled as follows so that the DWARF-2
6814 ;; backend automatically emits the required call frame debugging information
6815 ;; while it is parsing it. Therefore, the pattern should not be modified
6816 ;; without first studying the impact of the changes on the debug info.
6817 ;; [(set (%fp) (%sp))
6818 ;; (set (%sp) (unspec_volatile [(%sp) (-frame_size)] UNSPECV_SAVEW))
6819 ;; (set (%i7) (%o7))]
6821 (define_insn "save_register_window<P:mode>"
6822 [(set (reg:P 30) (reg:P 14))
6823 (set (reg:P 14) (unspec_volatile:P [(reg:P 14)
6824 (match_operand:P 0 "arith_operand" "rI")] UNSPECV_SAVEW))
6825 (set (reg:P 31) (reg:P 15))]
6827 "save\t%%sp, %0, %%sp"
6828 [(set_attr "type" "savew")])
6830 (define_expand "epilogue"
6834 sparc_expand_epilogue ();
6837 (define_expand "sibcall_epilogue"
6841 sparc_expand_epilogue ();
6845 (define_expand "return"
6847 "sparc_can_use_return_insn_p ()"
6850 (define_insn "*return_internal"
6853 "* return output_return (insn);"
6854 [(set_attr "type" "return")
6855 (set (attr "length")
6856 (cond [(eq_attr "leaf_function" "true")
6857 (if_then_else (eq_attr "empty_delay_slot" "true")
6860 (eq_attr "calls_eh_return" "true")
6861 (if_then_else (eq_attr "delayed_branch" "true")
6862 (if_then_else (eq_attr "isa" "v9")
6865 (if_then_else (eq_attr "isa" "v9")
6868 (eq_attr "empty_delay_slot" "true")
6869 (if_then_else (eq_attr "delayed_branch" "true")
6874 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
6875 ;; all of memory. This blocks insns from being moved across this point.
6877 (define_insn "blockage"
6878 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
6881 [(set_attr "length" "0")])
6883 ;; Prepare to return any type including a structure value.
6885 (define_expand "untyped_return"
6886 [(match_operand:BLK 0 "memory_operand" "")
6887 (match_operand 1 "" "")]
6890 rtx valreg1 = gen_rtx_REG (DImode, 24);
6891 rtx valreg2 = gen_rtx_REG (TARGET_ARCH64 ? TFmode : DFmode, 32);
6892 rtx result = operands[0];
6894 if (! TARGET_ARCH64)
6896 rtx rtnreg = gen_rtx_REG (SImode, (current_function_uses_only_leaf_regs
6898 rtx value = gen_reg_rtx (SImode);
6900 /* Fetch the instruction where we will return to and see if it's an unimp
6901 instruction (the most significant 10 bits will be zero). If so,
6902 update the return address to skip the unimp instruction. */
6903 emit_move_insn (value,
6904 gen_rtx_MEM (SImode, plus_constant (rtnreg, 8)));
6905 emit_insn (gen_lshrsi3 (value, value, GEN_INT (22)));
6906 emit_insn (gen_update_return (rtnreg, value));
6909 /* Reload the function value registers. */
6910 emit_move_insn (valreg1, adjust_address (result, DImode, 0));
6911 emit_move_insn (valreg2,
6912 adjust_address (result, TARGET_ARCH64 ? TFmode : DFmode, 8));
6914 /* Put USE insns before the return. */
6918 /* Construct the return. */
6919 expand_naked_return ();
6924 ;; Adjust the return address conditionally. If the value of op1 is equal
6925 ;; to all zero then adjust the return address i.e. op0 = op0 + 4.
6926 ;; This is technically *half* the check required by the 32-bit SPARC
6927 ;; psABI. This check only ensures that an "unimp" insn was written by
6928 ;; the caller, but doesn't check to see if the expected size matches
6929 ;; (this is encoded in the 12 lower bits). This check is obsolete and
6930 ;; only used by the above code "untyped_return".
6932 (define_insn "update_return"
6933 [(unspec:SI [(match_operand:SI 0 "register_operand" "r")
6934 (match_operand:SI 1 "register_operand" "r")] UNSPEC_UPDATE_RETURN)]
6937 if (flag_delayed_branch)
6938 return "cmp\t%1, 0\n\tbe,a\t.+8\n\t add\t%0, 4, %0";
6940 return "cmp\t%1, 0\n\tbne\t.+12\n\t nop\n\tadd\t%0, 4, %0";
6942 [(set (attr "type") (const_string "multi"))
6943 (set (attr "length")
6944 (if_then_else (eq_attr "delayed_branch" "true")
6953 (define_expand "indirect_jump"
6954 [(set (pc) (match_operand 0 "address_operand" "p"))]
6958 (define_insn "*branch_sp32"
6959 [(set (pc) (match_operand:SI 0 "address_operand" "p"))]
6962 [(set_attr "type" "uncond_branch")])
6964 (define_insn "*branch_sp64"
6965 [(set (pc) (match_operand:DI 0 "address_operand" "p"))]
6968 [(set_attr "type" "uncond_branch")])
6970 (define_expand "nonlocal_goto"
6971 [(match_operand:SI 0 "general_operand" "")
6972 (match_operand:SI 1 "general_operand" "")
6973 (match_operand:SI 2 "general_operand" "")
6974 (match_operand:SI 3 "" "")]
6977 rtx lab = operands[1];
6978 rtx stack = operands[2];
6979 rtx fp = operands[3];
6982 /* Trap instruction to flush all the register windows. */
6983 emit_insn (gen_flush_register_windows ());
6985 /* Load the fp value for the containing fn into %fp. This is needed
6986 because STACK refers to %fp. Note that virtual register instantiation
6987 fails if the virtual %fp isn't set from a register. */
6988 if (GET_CODE (fp) != REG)
6989 fp = force_reg (Pmode, fp);
6990 emit_move_insn (virtual_stack_vars_rtx, fp);
6992 /* Find the containing function's current nonlocal goto handler,
6993 which will do any cleanups and then jump to the label. */
6994 labreg = gen_rtx_REG (Pmode, 8);
6995 emit_move_insn (labreg, lab);
6997 /* Restore %fp from stack pointer value for containing function.
6998 The restore insn that follows will move this to %sp,
6999 and reload the appropriate value into %fp. */
7000 emit_move_insn (hard_frame_pointer_rtx, stack);
7002 emit_use (stack_pointer_rtx);
7003 emit_use (static_chain_rtx);
7005 /* ??? The V9-specific version was disabled in rev 1.65. */
7006 emit_jump_insn (gen_goto_handler_and_restore (labreg));
7011 ;; Special trap insn to flush register windows.
7012 (define_insn "flush_register_windows"
7013 [(unspec_volatile [(const_int 0)] UNSPECV_FLUSHW)]
7015 { return TARGET_V9 ? "flushw" : "ta\t3"; }
7016 [(set_attr "type" "flushw")])
7018 (define_insn "goto_handler_and_restore"
7019 [(unspec_volatile [(match_operand 0 "register_operand" "=r")] UNSPECV_GOTO)]
7020 "GET_MODE (operands[0]) == Pmode"
7022 if (flag_delayed_branch)
7023 return "jmp\t%0\n\t restore";
7025 return "mov\t%0,%%g1\n\trestore\n\tjmp\t%%g1\n\t nop";
7027 [(set (attr "type") (const_string "multi"))
7028 (set (attr "length")
7029 (if_then_else (eq_attr "delayed_branch" "true")
7033 ;; For __builtin_setjmp we need to flush register windows iff the function
7034 ;; calls alloca as well, because otherwise the register window might be
7035 ;; saved after %sp adjustment and thus setjmp would crash
7036 (define_expand "builtin_setjmp_setup"
7037 [(match_operand 0 "register_operand" "r")]
7040 emit_insn (gen_do_builtin_setjmp_setup ());
7044 (define_insn "do_builtin_setjmp_setup"
7045 [(unspec_volatile [(const_int 0)] UNSPECV_SETJMP)]
7048 if (! cfun->calls_alloca)
7052 fputs ("\tflushw\n", asm_out_file);
7054 fprintf (asm_out_file, "\tst%c\t%%l7, [%%sp+%d]\n",
7055 TARGET_ARCH64 ? 'x' : 'w',
7056 SPARC_STACK_BIAS + 7 * UNITS_PER_WORD);
7057 fprintf (asm_out_file, "\tst%c\t%%fp, [%%sp+%d]\n",
7058 TARGET_ARCH64 ? 'x' : 'w',
7059 SPARC_STACK_BIAS + 14 * UNITS_PER_WORD);
7060 fprintf (asm_out_file, "\tst%c\t%%i7, [%%sp+%d]\n",
7061 TARGET_ARCH64 ? 'x' : 'w',
7062 SPARC_STACK_BIAS + 15 * UNITS_PER_WORD);
7065 [(set_attr "type" "multi")
7066 (set (attr "length")
7067 (cond [(eq_attr "calls_alloca" "false")
7069 (eq_attr "isa" "!v9")
7071 (eq_attr "pic" "true")
7072 (const_int 4)] (const_int 3)))])
7074 ;; Pattern for use after a setjmp to store FP and the return register
7075 ;; into the stack area.
7077 (define_expand "setjmp"
7083 mem = gen_rtx_MEM (Pmode,
7084 plus_constant (stack_pointer_rtx,
7085 SPARC_STACK_BIAS + 14 * UNITS_PER_WORD));
7086 emit_insn (gen_rtx_SET (VOIDmode, mem, frame_pointer_rtx));
7088 mem = gen_rtx_MEM (Pmode,
7089 plus_constant (stack_pointer_rtx,
7090 SPARC_STACK_BIAS + 15 * UNITS_PER_WORD));
7091 emit_insn (gen_rtx_SET (VOIDmode, mem, gen_rtx_REG (Pmode, 31)));
7095 ;; Special pattern for the FLUSH instruction.
7097 ; We do SImode and DImode versions of this to quiet down genrecog's complaints
7098 ; of the define_insn otherwise missing a mode. We make "flush", aka
7099 ; gen_flush, the default one since sparc_initialize_trampoline uses
7100 ; it on SImode mem values.
7102 (define_insn "flush"
7103 [(unspec_volatile [(match_operand:SI 0 "memory_operand" "m")] UNSPECV_FLUSH)]
7105 { return TARGET_V9 ? "flush\t%f0" : "iflush\t%f0"; }
7106 [(set_attr "type" "iflush")])
7108 (define_insn "flushdi"
7109 [(unspec_volatile [(match_operand:DI 0 "memory_operand" "m")] UNSPECV_FLUSH)]
7111 { return TARGET_V9 ? "flush\t%f0" : "iflush\t%f0"; }
7112 [(set_attr "type" "iflush")])
7115 ;; Find first set instructions.
7117 ;; The scan instruction searches from the most significant bit while ffs
7118 ;; searches from the least significant bit. The bit index and treatment of
7119 ;; zero also differ. It takes at least 7 instructions to get the proper
7120 ;; result. Here is an obvious 8 instruction sequence.
7123 (define_insn "ffssi2"
7124 [(set (match_operand:SI 0 "register_operand" "=&r")
7125 (ffs:SI (match_operand:SI 1 "register_operand" "r")))
7126 (clobber (match_scratch:SI 2 "=&r"))]
7127 "TARGET_SPARCLITE || TARGET_SPARCLET"
7129 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";
7131 [(set_attr "type" "multi")
7132 (set_attr "length" "8")])
7134 ;; ??? This should be a define expand, so that the extra instruction have
7135 ;; a chance of being optimized away.
7137 ;; Disabled because none of the UltraSPARCs implement popc. The HAL R1
7138 ;; does, but no one uses that and we don't have a switch for it.
7140 ;(define_insn "ffsdi2"
7141 ; [(set (match_operand:DI 0 "register_operand" "=&r")
7142 ; (ffs:DI (match_operand:DI 1 "register_operand" "r")))
7143 ; (clobber (match_scratch:DI 2 "=&r"))]
7145 ; "neg\t%1, %2\;xnor\t%1, %2, %2\;popc\t%2, %0\;movzr\t%1, 0, %0"
7146 ; [(set_attr "type" "multi")
7147 ; (set_attr "length" "4")])
7151 ;; Peepholes go at the end.
7153 ;; Optimize consecutive loads or stores into ldd and std when possible.
7154 ;; The conditions in which we do this are very restricted and are
7155 ;; explained in the code for {registers,memory}_ok_for_ldd functions.
7158 [(set (match_operand:SI 0 "memory_operand" "")
7160 (set (match_operand:SI 1 "memory_operand" "")
7163 && mems_ok_for_ldd_peep (operands[0], operands[1], NULL_RTX)"
7166 "operands[0] = widen_memory_access (operands[0], DImode, 0);")
7169 [(set (match_operand:SI 0 "memory_operand" "")
7171 (set (match_operand:SI 1 "memory_operand" "")
7174 && mems_ok_for_ldd_peep (operands[1], operands[0], NULL_RTX)"
7177 "operands[1] = widen_memory_access (operands[1], DImode, 0);")
7180 [(set (match_operand:SI 0 "register_operand" "")
7181 (match_operand:SI 1 "memory_operand" ""))
7182 (set (match_operand:SI 2 "register_operand" "")
7183 (match_operand:SI 3 "memory_operand" ""))]
7184 "registers_ok_for_ldd_peep (operands[0], operands[2])
7185 && mems_ok_for_ldd_peep (operands[1], operands[3], operands[0])"
7188 "operands[1] = widen_memory_access (operands[1], DImode, 0);
7189 operands[0] = gen_rtx_REG (DImode, REGNO (operands[0]));")
7192 [(set (match_operand:SI 0 "memory_operand" "")
7193 (match_operand:SI 1 "register_operand" ""))
7194 (set (match_operand:SI 2 "memory_operand" "")
7195 (match_operand:SI 3 "register_operand" ""))]
7196 "registers_ok_for_ldd_peep (operands[1], operands[3])
7197 && mems_ok_for_ldd_peep (operands[0], operands[2], NULL_RTX)"
7200 "operands[0] = widen_memory_access (operands[0], DImode, 0);
7201 operands[1] = gen_rtx_REG (DImode, REGNO (operands[1]));")
7204 [(set (match_operand:SF 0 "register_operand" "")
7205 (match_operand:SF 1 "memory_operand" ""))
7206 (set (match_operand:SF 2 "register_operand" "")
7207 (match_operand:SF 3 "memory_operand" ""))]
7208 "registers_ok_for_ldd_peep (operands[0], operands[2])
7209 && mems_ok_for_ldd_peep (operands[1], operands[3], operands[0])"
7212 "operands[1] = widen_memory_access (operands[1], DFmode, 0);
7213 operands[0] = gen_rtx_REG (DFmode, REGNO (operands[0]));")
7216 [(set (match_operand:SF 0 "memory_operand" "")
7217 (match_operand:SF 1 "register_operand" ""))
7218 (set (match_operand:SF 2 "memory_operand" "")
7219 (match_operand:SF 3 "register_operand" ""))]
7220 "registers_ok_for_ldd_peep (operands[1], operands[3])
7221 && mems_ok_for_ldd_peep (operands[0], operands[2], NULL_RTX)"
7224 "operands[0] = widen_memory_access (operands[0], DFmode, 0);
7225 operands[1] = gen_rtx_REG (DFmode, REGNO (operands[1]));")
7228 [(set (match_operand:SI 0 "register_operand" "")
7229 (match_operand:SI 1 "memory_operand" ""))
7230 (set (match_operand:SI 2 "register_operand" "")
7231 (match_operand:SI 3 "memory_operand" ""))]
7232 "registers_ok_for_ldd_peep (operands[2], operands[0])
7233 && mems_ok_for_ldd_peep (operands[3], operands[1], operands[0])"
7236 "operands[3] = widen_memory_access (operands[3], DImode, 0);
7237 operands[2] = gen_rtx_REG (DImode, REGNO (operands[2]));")
7240 [(set (match_operand:SI 0 "memory_operand" "")
7241 (match_operand:SI 1 "register_operand" ""))
7242 (set (match_operand:SI 2 "memory_operand" "")
7243 (match_operand:SI 3 "register_operand" ""))]
7244 "registers_ok_for_ldd_peep (operands[3], operands[1])
7245 && mems_ok_for_ldd_peep (operands[2], operands[0], NULL_RTX)"
7248 "operands[2] = widen_memory_access (operands[2], DImode, 0);
7249 operands[3] = gen_rtx_REG (DImode, REGNO (operands[3]));
7253 [(set (match_operand:SF 0 "register_operand" "")
7254 (match_operand:SF 1 "memory_operand" ""))
7255 (set (match_operand:SF 2 "register_operand" "")
7256 (match_operand:SF 3 "memory_operand" ""))]
7257 "registers_ok_for_ldd_peep (operands[2], operands[0])
7258 && mems_ok_for_ldd_peep (operands[3], operands[1], operands[0])"
7261 "operands[3] = widen_memory_access (operands[3], DFmode, 0);
7262 operands[2] = gen_rtx_REG (DFmode, REGNO (operands[2]));")
7265 [(set (match_operand:SF 0 "memory_operand" "")
7266 (match_operand:SF 1 "register_operand" ""))
7267 (set (match_operand:SF 2 "memory_operand" "")
7268 (match_operand:SF 3 "register_operand" ""))]
7269 "registers_ok_for_ldd_peep (operands[3], operands[1])
7270 && mems_ok_for_ldd_peep (operands[2], operands[0], NULL_RTX)"
7273 "operands[2] = widen_memory_access (operands[2], DFmode, 0);
7274 operands[3] = gen_rtx_REG (DFmode, REGNO (operands[3]));")
7276 ;; Optimize the case of following a reg-reg move with a test
7277 ;; of reg just moved. Don't allow floating point regs for operand 0 or 1.
7278 ;; This can result from a float to fix conversion.
7281 [(set (match_operand:SI 0 "register_operand" "")
7282 (match_operand:SI 1 "register_operand" ""))
7284 (compare:CC (match_operand:SI 2 "register_operand" "")
7286 "(rtx_equal_p (operands[2], operands[0])
7287 || rtx_equal_p (operands[2], operands[1]))
7288 && ! SPARC_FP_REG_P (REGNO (operands[0]))
7289 && ! SPARC_FP_REG_P (REGNO (operands[1]))"
7290 [(parallel [(set (match_dup 0) (match_dup 1))
7292 (compare:CC (match_dup 1) (const_int 0)))])]
7296 [(set (match_operand:DI 0 "register_operand" "")
7297 (match_operand:DI 1 "register_operand" ""))
7299 (compare:CCX (match_operand:DI 2 "register_operand" "")
7302 && (rtx_equal_p (operands[2], operands[0])
7303 || rtx_equal_p (operands[2], operands[1]))
7304 && ! SPARC_FP_REG_P (REGNO (operands[0]))
7305 && ! SPARC_FP_REG_P (REGNO (operands[1]))"
7306 [(parallel [(set (match_dup 0) (match_dup 1))
7308 (compare:CCX (match_dup 1) (const_int 0)))])]
7312 ;; Prefetch instructions.
7314 ;; ??? UltraSPARC-III note: A memory operation loading into the floating point register
7315 ;; ??? file, if it hits the prefetch cache, has a chance to dual-issue with other memory
7316 ;; ??? operations. With DFA we might be able to model this, but it requires a lot of
7318 (define_expand "prefetch"
7319 [(match_operand 0 "address_operand" "")
7320 (match_operand 1 "const_int_operand" "")
7321 (match_operand 2 "const_int_operand" "")]
7325 emit_insn (gen_prefetch_64 (operands[0], operands[1], operands[2]));
7327 emit_insn (gen_prefetch_32 (operands[0], operands[1], operands[2]));
7331 (define_insn "prefetch_64"
7332 [(prefetch (match_operand:DI 0 "address_operand" "p")
7333 (match_operand:DI 1 "const_int_operand" "n")
7334 (match_operand:DI 2 "const_int_operand" "n"))]
7337 static const char * const prefetch_instr[2][2] = {
7339 "prefetch\t[%a0], 1", /* no locality: prefetch for one read */
7340 "prefetch\t[%a0], 0", /* medium to high locality: prefetch for several reads */
7343 "prefetch\t[%a0], 3", /* no locality: prefetch for one write */
7344 "prefetch\t[%a0], 2", /* medium to high locality: prefetch for several writes */
7347 int read_or_write = INTVAL (operands[1]);
7348 int locality = INTVAL (operands[2]);
7350 gcc_assert (read_or_write == 0 || read_or_write == 1);
7351 gcc_assert (locality >= 0 && locality < 4);
7352 return prefetch_instr [read_or_write][locality == 0 ? 0 : 1];
7354 [(set_attr "type" "load")])
7356 (define_insn "prefetch_32"
7357 [(prefetch (match_operand:SI 0 "address_operand" "p")
7358 (match_operand:SI 1 "const_int_operand" "n")
7359 (match_operand:SI 2 "const_int_operand" "n"))]
7362 static const char * const prefetch_instr[2][2] = {
7364 "prefetch\t[%a0], 1", /* no locality: prefetch for one read */
7365 "prefetch\t[%a0], 0", /* medium to high locality: prefetch for several reads */
7368 "prefetch\t[%a0], 3", /* no locality: prefetch for one write */
7369 "prefetch\t[%a0], 2", /* medium to high locality: prefetch for several writes */
7372 int read_or_write = INTVAL (operands[1]);
7373 int locality = INTVAL (operands[2]);
7375 gcc_assert (read_or_write == 0 || read_or_write == 1);
7376 gcc_assert (locality >= 0 && locality < 4);
7377 return prefetch_instr [read_or_write][locality == 0 ? 0 : 1];
7379 [(set_attr "type" "load")])
7382 ;; Trap instructions.
7385 [(trap_if (const_int 1) (const_int 5))]
7388 [(set_attr "type" "trap")])
7390 (define_expand "conditional_trap"
7391 [(trap_if (match_operator 0 "noov_compare_operator" [(match_dup 2) (match_dup 3)])
7392 (match_operand:SI 1 "arith_operand" ""))]
7394 "operands[2] = gen_compare_reg (GET_CODE (operands[0]));
7395 if (GET_MODE (operands[2]) != CCmode && GET_MODE (operands[2]) != CCXmode)
7397 operands[3] = const0_rtx;")
7400 [(trap_if (match_operator 0 "noov_compare_operator" [(reg:CC 100) (const_int 0)])
7401 (match_operand:SI 1 "arith_operand" "rM"))]
7405 return "t%C0\t%%icc, %1";
7409 [(set_attr "type" "trap")])
7412 [(trap_if (match_operator 0 "noov_compare_operator" [(reg:CCX 100) (const_int 0)])
7413 (match_operand:SI 1 "arith_operand" "rM"))]
7416 [(set_attr "type" "trap")])
7419 ;; TLS support instructions.
7421 (define_insn "tgd_hi22"
7422 [(set (match_operand:SI 0 "register_operand" "=r")
7423 (high:SI (unspec:SI [(match_operand 1 "tgd_symbolic_operand" "")]
7426 "sethi\\t%%tgd_hi22(%a1), %0")
7428 (define_insn "tgd_lo10"
7429 [(set (match_operand:SI 0 "register_operand" "=r")
7430 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
7431 (unspec:SI [(match_operand 2 "tgd_symbolic_operand" "")]
7434 "add\\t%1, %%tgd_lo10(%a2), %0")
7436 (define_insn "tgd_add32"
7437 [(set (match_operand:SI 0 "register_operand" "=r")
7438 (plus:SI (match_operand:SI 1 "register_operand" "r")
7439 (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7440 (match_operand 3 "tgd_symbolic_operand" "")]
7442 "TARGET_TLS && TARGET_ARCH32"
7443 "add\\t%1, %2, %0, %%tgd_add(%a3)")
7445 (define_insn "tgd_add64"
7446 [(set (match_operand:DI 0 "register_operand" "=r")
7447 (plus:DI (match_operand:DI 1 "register_operand" "r")
7448 (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7449 (match_operand 3 "tgd_symbolic_operand" "")]
7451 "TARGET_TLS && TARGET_ARCH64"
7452 "add\\t%1, %2, %0, %%tgd_add(%a3)")
7454 (define_insn "tgd_call32"
7455 [(set (match_operand 0 "register_operand" "=r")
7456 (call (mem:SI (unspec:SI [(match_operand:SI 1 "symbolic_operand" "s")
7457 (match_operand 2 "tgd_symbolic_operand" "")]
7459 (match_operand 3 "" "")))
7460 (clobber (reg:SI 15))]
7461 "TARGET_TLS && TARGET_ARCH32"
7462 "call\t%a1, %%tgd_call(%a2)%#"
7463 [(set_attr "type" "call")])
7465 (define_insn "tgd_call64"
7466 [(set (match_operand 0 "register_operand" "=r")
7467 (call (mem:DI (unspec:DI [(match_operand:DI 1 "symbolic_operand" "s")
7468 (match_operand 2 "tgd_symbolic_operand" "")]
7470 (match_operand 3 "" "")))
7471 (clobber (reg:DI 15))]
7472 "TARGET_TLS && TARGET_ARCH64"
7473 "call\t%a1, %%tgd_call(%a2)%#"
7474 [(set_attr "type" "call")])
7476 (define_insn "tldm_hi22"
7477 [(set (match_operand:SI 0 "register_operand" "=r")
7478 (high:SI (unspec:SI [(const_int 0)] UNSPEC_TLSLDM)))]
7480 "sethi\\t%%tldm_hi22(%&), %0")
7482 (define_insn "tldm_lo10"
7483 [(set (match_operand:SI 0 "register_operand" "=r")
7484 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
7485 (unspec:SI [(const_int 0)] UNSPEC_TLSLDM)))]
7487 "add\\t%1, %%tldm_lo10(%&), %0")
7489 (define_insn "tldm_add32"
7490 [(set (match_operand:SI 0 "register_operand" "=r")
7491 (plus:SI (match_operand:SI 1 "register_operand" "r")
7492 (unspec:SI [(match_operand:SI 2 "register_operand" "r")]
7494 "TARGET_TLS && TARGET_ARCH32"
7495 "add\\t%1, %2, %0, %%tldm_add(%&)")
7497 (define_insn "tldm_add64"
7498 [(set (match_operand:DI 0 "register_operand" "=r")
7499 (plus:DI (match_operand:DI 1 "register_operand" "r")
7500 (unspec:DI [(match_operand:SI 2 "register_operand" "r")]
7502 "TARGET_TLS && TARGET_ARCH64"
7503 "add\\t%1, %2, %0, %%tldm_add(%&)")
7505 (define_insn "tldm_call32"
7506 [(set (match_operand 0 "register_operand" "=r")
7507 (call (mem:SI (unspec:SI [(match_operand:SI 1 "symbolic_operand" "s")]
7509 (match_operand 2 "" "")))
7510 (clobber (reg:SI 15))]
7511 "TARGET_TLS && TARGET_ARCH32"
7512 "call\t%a1, %%tldm_call(%&)%#"
7513 [(set_attr "type" "call")])
7515 (define_insn "tldm_call64"
7516 [(set (match_operand 0 "register_operand" "=r")
7517 (call (mem:DI (unspec:DI [(match_operand:DI 1 "symbolic_operand" "s")]
7519 (match_operand 2 "" "")))
7520 (clobber (reg:DI 15))]
7521 "TARGET_TLS && TARGET_ARCH64"
7522 "call\t%a1, %%tldm_call(%&)%#"
7523 [(set_attr "type" "call")])
7525 (define_insn "tldo_hix22"
7526 [(set (match_operand:SI 0 "register_operand" "=r")
7527 (high:SI (unspec:SI [(match_operand 1 "tld_symbolic_operand" "")]
7530 "sethi\\t%%tldo_hix22(%a1), %0")
7532 (define_insn "tldo_lox10"
7533 [(set (match_operand:SI 0 "register_operand" "=r")
7534 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
7535 (unspec:SI [(match_operand 2 "tld_symbolic_operand" "")]
7538 "xor\\t%1, %%tldo_lox10(%a2), %0")
7540 (define_insn "tldo_add32"
7541 [(set (match_operand:SI 0 "register_operand" "=r")
7542 (plus:SI (match_operand:SI 1 "register_operand" "r")
7543 (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7544 (match_operand 3 "tld_symbolic_operand" "")]
7546 "TARGET_TLS && TARGET_ARCH32"
7547 "add\\t%1, %2, %0, %%tldo_add(%a3)")
7549 (define_insn "tldo_add64"
7550 [(set (match_operand:DI 0 "register_operand" "=r")
7551 (plus:DI (match_operand:DI 1 "register_operand" "r")
7552 (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7553 (match_operand 3 "tld_symbolic_operand" "")]
7555 "TARGET_TLS && TARGET_ARCH64"
7556 "add\\t%1, %2, %0, %%tldo_add(%a3)")
7558 (define_insn "tie_hi22"
7559 [(set (match_operand:SI 0 "register_operand" "=r")
7560 (high:SI (unspec:SI [(match_operand 1 "tie_symbolic_operand" "")]
7563 "sethi\\t%%tie_hi22(%a1), %0")
7565 (define_insn "tie_lo10"
7566 [(set (match_operand:SI 0 "register_operand" "=r")
7567 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
7568 (unspec:SI [(match_operand 2 "tie_symbolic_operand" "")]
7571 "add\\t%1, %%tie_lo10(%a2), %0")
7573 (define_insn "tie_ld32"
7574 [(set (match_operand:SI 0 "register_operand" "=r")
7575 (unspec:SI [(match_operand:SI 1 "register_operand" "r")
7576 (match_operand:SI 2 "register_operand" "r")
7577 (match_operand 3 "tie_symbolic_operand" "")]
7579 "TARGET_TLS && TARGET_ARCH32"
7580 "ld\\t[%1 + %2], %0, %%tie_ld(%a3)"
7581 [(set_attr "type" "load")])
7583 (define_insn "tie_ld64"
7584 [(set (match_operand:DI 0 "register_operand" "=r")
7585 (unspec:DI [(match_operand:DI 1 "register_operand" "r")
7586 (match_operand:SI 2 "register_operand" "r")
7587 (match_operand 3 "tie_symbolic_operand" "")]
7589 "TARGET_TLS && TARGET_ARCH64"
7590 "ldx\\t[%1 + %2], %0, %%tie_ldx(%a3)"
7591 [(set_attr "type" "load")])
7593 (define_insn "tie_add32"
7594 [(set (match_operand:SI 0 "register_operand" "=r")
7595 (plus:SI (match_operand:SI 1 "register_operand" "r")
7596 (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7597 (match_operand 3 "tie_symbolic_operand" "")]
7599 "TARGET_SUN_TLS && TARGET_ARCH32"
7600 "add\\t%1, %2, %0, %%tie_add(%a3)")
7602 (define_insn "tie_add64"
7603 [(set (match_operand:DI 0 "register_operand" "=r")
7604 (plus:DI (match_operand:DI 1 "register_operand" "r")
7605 (unspec:DI [(match_operand:DI 2 "register_operand" "r")
7606 (match_operand 3 "tie_symbolic_operand" "")]
7608 "TARGET_SUN_TLS && TARGET_ARCH64"
7609 "add\\t%1, %2, %0, %%tie_add(%a3)")
7611 (define_insn "tle_hix22_sp32"
7612 [(set (match_operand:SI 0 "register_operand" "=r")
7613 (high:SI (unspec:SI [(match_operand 1 "tle_symbolic_operand" "")]
7615 "TARGET_TLS && TARGET_ARCH32"
7616 "sethi\\t%%tle_hix22(%a1), %0")
7618 (define_insn "tle_lox10_sp32"
7619 [(set (match_operand:SI 0 "register_operand" "=r")
7620 (lo_sum:SI (match_operand:SI 1 "register_operand" "r")
7621 (unspec:SI [(match_operand 2 "tle_symbolic_operand" "")]
7623 "TARGET_TLS && TARGET_ARCH32"
7624 "xor\\t%1, %%tle_lox10(%a2), %0")
7626 (define_insn "tle_hix22_sp64"
7627 [(set (match_operand:DI 0 "register_operand" "=r")
7628 (high:DI (unspec:DI [(match_operand 1 "tle_symbolic_operand" "")]
7630 "TARGET_TLS && TARGET_ARCH64"
7631 "sethi\\t%%tle_hix22(%a1), %0")
7633 (define_insn "tle_lox10_sp64"
7634 [(set (match_operand:DI 0 "register_operand" "=r")
7635 (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
7636 (unspec:DI [(match_operand 2 "tle_symbolic_operand" "")]
7638 "TARGET_TLS && TARGET_ARCH64"
7639 "xor\\t%1, %%tle_lox10(%a2), %0")
7641 ;; Now patterns combining tldo_add{32,64} with some integer loads or stores
7642 (define_insn "*tldo_ldub_sp32"
7643 [(set (match_operand:QI 0 "register_operand" "=r")
7644 (mem:QI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7645 (match_operand 3 "tld_symbolic_operand" "")]
7647 (match_operand:SI 1 "register_operand" "r"))))]
7648 "TARGET_TLS && TARGET_ARCH32"
7649 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
7650 [(set_attr "type" "load")
7651 (set_attr "us3load_type" "3cycle")])
7653 (define_insn "*tldo_ldub1_sp32"
7654 [(set (match_operand:HI 0 "register_operand" "=r")
7655 (zero_extend:HI (mem:QI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7656 (match_operand 3 "tld_symbolic_operand" "")]
7658 (match_operand:SI 1 "register_operand" "r")))))]
7659 "TARGET_TLS && TARGET_ARCH32"
7660 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
7661 [(set_attr "type" "load")
7662 (set_attr "us3load_type" "3cycle")])
7664 (define_insn "*tldo_ldub2_sp32"
7665 [(set (match_operand:SI 0 "register_operand" "=r")
7666 (zero_extend:SI (mem:QI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7667 (match_operand 3 "tld_symbolic_operand" "")]
7669 (match_operand:SI 1 "register_operand" "r")))))]
7670 "TARGET_TLS && TARGET_ARCH32"
7671 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
7672 [(set_attr "type" "load")
7673 (set_attr "us3load_type" "3cycle")])
7675 (define_insn "*tldo_ldsb1_sp32"
7676 [(set (match_operand:HI 0 "register_operand" "=r")
7677 (sign_extend:HI (mem:QI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7678 (match_operand 3 "tld_symbolic_operand" "")]
7680 (match_operand:SI 1 "register_operand" "r")))))]
7681 "TARGET_TLS && TARGET_ARCH32"
7682 "ldsb\t[%1 + %2], %0, %%tldo_add(%3)"
7683 [(set_attr "type" "sload")
7684 (set_attr "us3load_type" "3cycle")])
7686 (define_insn "*tldo_ldsb2_sp32"
7687 [(set (match_operand:SI 0 "register_operand" "=r")
7688 (sign_extend:SI (mem:QI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7689 (match_operand 3 "tld_symbolic_operand" "")]
7691 (match_operand:SI 1 "register_operand" "r")))))]
7692 "TARGET_TLS && TARGET_ARCH32"
7693 "ldsb\t[%1 + %2], %0, %%tldo_add(%3)"
7694 [(set_attr "type" "sload")
7695 (set_attr "us3load_type" "3cycle")])
7697 (define_insn "*tldo_ldub_sp64"
7698 [(set (match_operand:QI 0 "register_operand" "=r")
7699 (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7700 (match_operand 3 "tld_symbolic_operand" "")]
7702 (match_operand:DI 1 "register_operand" "r"))))]
7703 "TARGET_TLS && TARGET_ARCH64"
7704 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
7705 [(set_attr "type" "load")
7706 (set_attr "us3load_type" "3cycle")])
7708 (define_insn "*tldo_ldub1_sp64"
7709 [(set (match_operand:HI 0 "register_operand" "=r")
7710 (zero_extend:HI (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7711 (match_operand 3 "tld_symbolic_operand" "")]
7713 (match_operand:DI 1 "register_operand" "r")))))]
7714 "TARGET_TLS && TARGET_ARCH64"
7715 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
7716 [(set_attr "type" "load")
7717 (set_attr "us3load_type" "3cycle")])
7719 (define_insn "*tldo_ldub2_sp64"
7720 [(set (match_operand:SI 0 "register_operand" "=r")
7721 (zero_extend:SI (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7722 (match_operand 3 "tld_symbolic_operand" "")]
7724 (match_operand:DI 1 "register_operand" "r")))))]
7725 "TARGET_TLS && TARGET_ARCH64"
7726 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
7727 [(set_attr "type" "load")
7728 (set_attr "us3load_type" "3cycle")])
7730 (define_insn "*tldo_ldub3_sp64"
7731 [(set (match_operand:DI 0 "register_operand" "=r")
7732 (zero_extend:DI (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7733 (match_operand 3 "tld_symbolic_operand" "")]
7735 (match_operand:DI 1 "register_operand" "r")))))]
7736 "TARGET_TLS && TARGET_ARCH64"
7737 "ldub\t[%1 + %2], %0, %%tldo_add(%3)"
7738 [(set_attr "type" "load")
7739 (set_attr "us3load_type" "3cycle")])
7741 (define_insn "*tldo_ldsb1_sp64"
7742 [(set (match_operand:HI 0 "register_operand" "=r")
7743 (sign_extend:HI (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7744 (match_operand 3 "tld_symbolic_operand" "")]
7746 (match_operand:DI 1 "register_operand" "r")))))]
7747 "TARGET_TLS && TARGET_ARCH64"
7748 "ldsb\t[%1 + %2], %0, %%tldo_add(%3)"
7749 [(set_attr "type" "sload")
7750 (set_attr "us3load_type" "3cycle")])
7752 (define_insn "*tldo_ldsb2_sp64"
7753 [(set (match_operand:SI 0 "register_operand" "=r")
7754 (sign_extend:SI (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7755 (match_operand 3 "tld_symbolic_operand" "")]
7757 (match_operand:DI 1 "register_operand" "r")))))]
7758 "TARGET_TLS && TARGET_ARCH64"
7759 "ldsb\t[%1 + %2], %0, %%tldo_add(%3)"
7760 [(set_attr "type" "sload")
7761 (set_attr "us3load_type" "3cycle")])
7763 (define_insn "*tldo_ldsb3_sp64"
7764 [(set (match_operand:DI 0 "register_operand" "=r")
7765 (sign_extend:DI (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7766 (match_operand 3 "tld_symbolic_operand" "")]
7768 (match_operand:DI 1 "register_operand" "r")))))]
7769 "TARGET_TLS && TARGET_ARCH64"
7770 "ldsb\t[%1 + %2], %0, %%tldo_add(%3)"
7771 [(set_attr "type" "sload")
7772 (set_attr "us3load_type" "3cycle")])
7774 (define_insn "*tldo_lduh_sp32"
7775 [(set (match_operand:HI 0 "register_operand" "=r")
7776 (mem:HI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7777 (match_operand 3 "tld_symbolic_operand" "")]
7779 (match_operand:SI 1 "register_operand" "r"))))]
7780 "TARGET_TLS && TARGET_ARCH32"
7781 "lduh\t[%1 + %2], %0, %%tldo_add(%3)"
7782 [(set_attr "type" "load")
7783 (set_attr "us3load_type" "3cycle")])
7785 (define_insn "*tldo_lduh1_sp32"
7786 [(set (match_operand:SI 0 "register_operand" "=r")
7787 (zero_extend:SI (mem:HI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7788 (match_operand 3 "tld_symbolic_operand" "")]
7790 (match_operand:SI 1 "register_operand" "r")))))]
7791 "TARGET_TLS && TARGET_ARCH32"
7792 "lduh\t[%1 + %2], %0, %%tldo_add(%3)"
7793 [(set_attr "type" "load")
7794 (set_attr "us3load_type" "3cycle")])
7796 (define_insn "*tldo_ldsh1_sp32"
7797 [(set (match_operand:SI 0 "register_operand" "=r")
7798 (sign_extend:SI (mem:HI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7799 (match_operand 3 "tld_symbolic_operand" "")]
7801 (match_operand:SI 1 "register_operand" "r")))))]
7802 "TARGET_TLS && TARGET_ARCH32"
7803 "ldsh\t[%1 + %2], %0, %%tldo_add(%3)"
7804 [(set_attr "type" "sload")
7805 (set_attr "us3load_type" "3cycle")])
7807 (define_insn "*tldo_lduh_sp64"
7808 [(set (match_operand:HI 0 "register_operand" "=r")
7809 (mem:HI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7810 (match_operand 3 "tld_symbolic_operand" "")]
7812 (match_operand:DI 1 "register_operand" "r"))))]
7813 "TARGET_TLS && TARGET_ARCH64"
7814 "lduh\t[%1 + %2], %0, %%tldo_add(%3)"
7815 [(set_attr "type" "load")
7816 (set_attr "us3load_type" "3cycle")])
7818 (define_insn "*tldo_lduh1_sp64"
7819 [(set (match_operand:SI 0 "register_operand" "=r")
7820 (zero_extend:SI (mem:HI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7821 (match_operand 3 "tld_symbolic_operand" "")]
7823 (match_operand:DI 1 "register_operand" "r")))))]
7824 "TARGET_TLS && TARGET_ARCH64"
7825 "lduh\t[%1 + %2], %0, %%tldo_add(%3)"
7826 [(set_attr "type" "load")
7827 (set_attr "us3load_type" "3cycle")])
7829 (define_insn "*tldo_lduh2_sp64"
7830 [(set (match_operand:DI 0 "register_operand" "=r")
7831 (zero_extend:DI (mem:HI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7832 (match_operand 3 "tld_symbolic_operand" "")]
7834 (match_operand:DI 1 "register_operand" "r")))))]
7835 "TARGET_TLS && TARGET_ARCH64"
7836 "lduh\t[%1 + %2], %0, %%tldo_add(%3)"
7837 [(set_attr "type" "load")
7838 (set_attr "us3load_type" "3cycle")])
7840 (define_insn "*tldo_ldsh1_sp64"
7841 [(set (match_operand:SI 0 "register_operand" "=r")
7842 (sign_extend:SI (mem:HI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7843 (match_operand 3 "tld_symbolic_operand" "")]
7845 (match_operand:DI 1 "register_operand" "r")))))]
7846 "TARGET_TLS && TARGET_ARCH64"
7847 "ldsh\t[%1 + %2], %0, %%tldo_add(%3)"
7848 [(set_attr "type" "sload")
7849 (set_attr "us3load_type" "3cycle")])
7851 (define_insn "*tldo_ldsh2_sp64"
7852 [(set (match_operand:DI 0 "register_operand" "=r")
7853 (sign_extend:DI (mem:HI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7854 (match_operand 3 "tld_symbolic_operand" "")]
7856 (match_operand:DI 1 "register_operand" "r")))))]
7857 "TARGET_TLS && TARGET_ARCH64"
7858 "ldsh\t[%1 + %2], %0, %%tldo_add(%3)"
7859 [(set_attr "type" "sload")
7860 (set_attr "us3load_type" "3cycle")])
7862 (define_insn "*tldo_lduw_sp32"
7863 [(set (match_operand:SI 0 "register_operand" "=r")
7864 (mem:SI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7865 (match_operand 3 "tld_symbolic_operand" "")]
7867 (match_operand:SI 1 "register_operand" "r"))))]
7868 "TARGET_TLS && TARGET_ARCH32"
7869 "ld\t[%1 + %2], %0, %%tldo_add(%3)"
7870 [(set_attr "type" "load")])
7872 (define_insn "*tldo_lduw_sp64"
7873 [(set (match_operand:SI 0 "register_operand" "=r")
7874 (mem:SI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7875 (match_operand 3 "tld_symbolic_operand" "")]
7877 (match_operand:DI 1 "register_operand" "r"))))]
7878 "TARGET_TLS && TARGET_ARCH64"
7879 "lduw\t[%1 + %2], %0, %%tldo_add(%3)"
7880 [(set_attr "type" "load")])
7882 (define_insn "*tldo_lduw1_sp64"
7883 [(set (match_operand:DI 0 "register_operand" "=r")
7884 (zero_extend:DI (mem:SI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7885 (match_operand 3 "tld_symbolic_operand" "")]
7887 (match_operand:DI 1 "register_operand" "r")))))]
7888 "TARGET_TLS && TARGET_ARCH64"
7889 "lduw\t[%1 + %2], %0, %%tldo_add(%3)"
7890 [(set_attr "type" "load")])
7892 (define_insn "*tldo_ldsw1_sp64"
7893 [(set (match_operand:DI 0 "register_operand" "=r")
7894 (sign_extend:DI (mem:SI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7895 (match_operand 3 "tld_symbolic_operand" "")]
7897 (match_operand:DI 1 "register_operand" "r")))))]
7898 "TARGET_TLS && TARGET_ARCH64"
7899 "ldsw\t[%1 + %2], %0, %%tldo_add(%3)"
7900 [(set_attr "type" "sload")
7901 (set_attr "us3load_type" "3cycle")])
7903 (define_insn "*tldo_ldx_sp64"
7904 [(set (match_operand:DI 0 "register_operand" "=r")
7905 (mem:DI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7906 (match_operand 3 "tld_symbolic_operand" "")]
7908 (match_operand:DI 1 "register_operand" "r"))))]
7909 "TARGET_TLS && TARGET_ARCH64"
7910 "ldx\t[%1 + %2], %0, %%tldo_add(%3)"
7911 [(set_attr "type" "load")])
7913 (define_insn "*tldo_stb_sp32"
7914 [(set (mem:QI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7915 (match_operand 3 "tld_symbolic_operand" "")]
7917 (match_operand:SI 1 "register_operand" "r")))
7918 (match_operand:QI 0 "register_operand" "=r"))]
7919 "TARGET_TLS && TARGET_ARCH32"
7920 "stb\t%0, [%1 + %2], %%tldo_add(%3)"
7921 [(set_attr "type" "store")])
7923 (define_insn "*tldo_stb_sp64"
7924 [(set (mem:QI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7925 (match_operand 3 "tld_symbolic_operand" "")]
7927 (match_operand:DI 1 "register_operand" "r")))
7928 (match_operand:QI 0 "register_operand" "=r"))]
7929 "TARGET_TLS && TARGET_ARCH64"
7930 "stb\t%0, [%1 + %2], %%tldo_add(%3)"
7931 [(set_attr "type" "store")])
7933 (define_insn "*tldo_sth_sp32"
7934 [(set (mem:HI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7935 (match_operand 3 "tld_symbolic_operand" "")]
7937 (match_operand:SI 1 "register_operand" "r")))
7938 (match_operand:HI 0 "register_operand" "=r"))]
7939 "TARGET_TLS && TARGET_ARCH32"
7940 "sth\t%0, [%1 + %2], %%tldo_add(%3)"
7941 [(set_attr "type" "store")])
7943 (define_insn "*tldo_sth_sp64"
7944 [(set (mem:HI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7945 (match_operand 3 "tld_symbolic_operand" "")]
7947 (match_operand:DI 1 "register_operand" "r")))
7948 (match_operand:HI 0 "register_operand" "=r"))]
7949 "TARGET_TLS && TARGET_ARCH64"
7950 "sth\t%0, [%1 + %2], %%tldo_add(%3)"
7951 [(set_attr "type" "store")])
7953 (define_insn "*tldo_stw_sp32"
7954 [(set (mem:SI (plus:SI (unspec:SI [(match_operand:SI 2 "register_operand" "r")
7955 (match_operand 3 "tld_symbolic_operand" "")]
7957 (match_operand:SI 1 "register_operand" "r")))
7958 (match_operand:SI 0 "register_operand" "=r"))]
7959 "TARGET_TLS && TARGET_ARCH32"
7960 "st\t%0, [%1 + %2], %%tldo_add(%3)"
7961 [(set_attr "type" "store")])
7963 (define_insn "*tldo_stw_sp64"
7964 [(set (mem:SI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7965 (match_operand 3 "tld_symbolic_operand" "")]
7967 (match_operand:DI 1 "register_operand" "r")))
7968 (match_operand:SI 0 "register_operand" "=r"))]
7969 "TARGET_TLS && TARGET_ARCH64"
7970 "stw\t%0, [%1 + %2], %%tldo_add(%3)"
7971 [(set_attr "type" "store")])
7973 (define_insn "*tldo_stx_sp64"
7974 [(set (mem:DI (plus:DI (unspec:DI [(match_operand:SI 2 "register_operand" "r")
7975 (match_operand 3 "tld_symbolic_operand" "")]
7977 (match_operand:DI 1 "register_operand" "r")))
7978 (match_operand:DI 0 "register_operand" "=r"))]
7979 "TARGET_TLS && TARGET_ARCH64"
7980 "stx\t%0, [%1 + %2], %%tldo_add(%3)"
7981 [(set_attr "type" "store")])
7984 ;; Stack protector instructions.
7986 (define_expand "stack_protect_set"
7987 [(match_operand 0 "memory_operand" "")
7988 (match_operand 1 "memory_operand" "")]
7991 #ifdef TARGET_THREAD_SSP_OFFSET
7992 rtx tlsreg = gen_rtx_REG (Pmode, 7);
7993 rtx addr = gen_rtx_PLUS (Pmode, tlsreg, GEN_INT (TARGET_THREAD_SSP_OFFSET));
7994 operands[1] = gen_rtx_MEM (Pmode, addr);
7997 emit_insn (gen_stack_protect_setdi (operands[0], operands[1]));
7999 emit_insn (gen_stack_protect_setsi (operands[0], operands[1]));
8003 (define_insn "stack_protect_setsi"
8004 [(set (match_operand:SI 0 "memory_operand" "=m")
8005 (unspec:SI [(match_operand:SI 1 "memory_operand" "m")] UNSPEC_SP_SET))
8006 (set (match_scratch:SI 2 "=&r") (const_int 0))]
8008 "ld\t%1, %2\;st\t%2, %0\;mov\t0, %2"
8009 [(set_attr "type" "multi")
8010 (set_attr "length" "3")])
8012 (define_insn "stack_protect_setdi"
8013 [(set (match_operand:DI 0 "memory_operand" "=m")
8014 (unspec:DI [(match_operand:DI 1 "memory_operand" "m")] UNSPEC_SP_SET))
8015 (set (match_scratch:DI 2 "=&r") (const_int 0))]
8017 "ldx\t%1, %2\;stx\t%2, %0\;mov\t0, %2"
8018 [(set_attr "type" "multi")
8019 (set_attr "length" "3")])
8021 (define_expand "stack_protect_test"
8022 [(match_operand 0 "memory_operand" "")
8023 (match_operand 1 "memory_operand" "")
8024 (match_operand 2 "" "")]
8027 #ifdef TARGET_THREAD_SSP_OFFSET
8028 rtx tlsreg = gen_rtx_REG (Pmode, 7);
8029 rtx addr = gen_rtx_PLUS (Pmode, tlsreg, GEN_INT (TARGET_THREAD_SSP_OFFSET));
8030 operands[1] = gen_rtx_MEM (Pmode, addr);
8034 rtx temp = gen_reg_rtx (Pmode);
8035 emit_insn (gen_stack_protect_testdi (temp, operands[0], operands[1]));
8036 sparc_compare_op0 = temp;
8037 sparc_compare_op1 = const0_rtx;
8041 emit_insn (gen_stack_protect_testsi (operands[0], operands[1]));
8042 sparc_compare_op0 = operands[0];
8043 sparc_compare_op1 = operands[1];
8044 sparc_compare_emitted = gen_rtx_REG (CCmode, SPARC_ICC_REG);
8046 emit_jump_insn (gen_beq (operands[2]));
8050 (define_insn "stack_protect_testsi"
8052 (unspec:CC [(match_operand:SI 0 "memory_operand" "m")
8053 (match_operand:SI 1 "memory_operand" "m")]
8055 (set (match_scratch:SI 3 "=r") (const_int 0))
8056 (clobber (match_scratch:SI 2 "=&r"))]
8058 "ld\t%0, %2\;ld\t%1, %3\;xorcc\t%2, %3, %2\;mov\t0, %3"
8059 [(set_attr "type" "multi")
8060 (set_attr "length" "4")])
8062 (define_insn "stack_protect_testdi"
8063 [(set (match_operand:DI 0 "register_operand" "=&r")
8064 (unspec:DI [(match_operand:DI 1 "memory_operand" "m")
8065 (match_operand:DI 2 "memory_operand" "m")]
8067 (set (match_scratch:DI 3 "=r") (const_int 0))]
8069 "ldx\t%1, %0\;ldx\t%2, %3\;xor\t%0, %3, %0\;mov\t0, %3"
8070 [(set_attr "type" "multi")
8071 (set_attr "length" "4")])
8074 ;; Vector instructions.
8076 (define_insn "addv2si3"
8077 [(set (match_operand:V2SI 0 "register_operand" "=e")
8078 (plus:V2SI (match_operand:V2SI 1 "register_operand" "e")
8079 (match_operand:V2SI 2 "register_operand" "e")))]
8081 "fpadd32\t%1, %2, %0"
8082 [(set_attr "type" "fga")
8083 (set_attr "fptype" "double")])
8085 (define_insn "addv4hi3"
8086 [(set (match_operand:V4HI 0 "register_operand" "=e")
8087 (plus:V4HI (match_operand:V4HI 1 "register_operand" "e")
8088 (match_operand:V4HI 2 "register_operand" "e")))]
8090 "fpadd16\t%1, %2, %0"
8091 [(set_attr "type" "fga")
8092 (set_attr "fptype" "double")])
8094 ;; fpadd32s is emitted by the addsi3 pattern.
8096 (define_insn "addv2hi3"
8097 [(set (match_operand:V2HI 0 "register_operand" "=f")
8098 (plus:V2HI (match_operand:V2HI 1 "register_operand" "f")
8099 (match_operand:V2HI 2 "register_operand" "f")))]
8101 "fpadd16s\t%1, %2, %0"
8102 [(set_attr "type" "fga")
8103 (set_attr "fptype" "single")])
8105 (define_insn "subv2si3"
8106 [(set (match_operand:V2SI 0 "register_operand" "=e")
8107 (minus:V2SI (match_operand:V2SI 1 "register_operand" "e")
8108 (match_operand:V2SI 2 "register_operand" "e")))]
8110 "fpsub32\t%1, %2, %0"
8111 [(set_attr "type" "fga")
8112 (set_attr "fptype" "double")])
8114 (define_insn "subv4hi3"
8115 [(set (match_operand:V4HI 0 "register_operand" "=e")
8116 (minus:V4HI (match_operand:V4HI 1 "register_operand" "e")
8117 (match_operand:V4HI 2 "register_operand" "e")))]
8119 "fpsub16\t%1, %2, %0"
8120 [(set_attr "type" "fga")
8121 (set_attr "fptype" "double")])
8123 ;; fpsub32s is emitted by the subsi3 pattern.
8125 (define_insn "subv2hi3"
8126 [(set (match_operand:V2HI 0 "register_operand" "=f")
8127 (minus:V2HI (match_operand:V2HI 1 "register_operand" "f")
8128 (match_operand:V2HI 2 "register_operand" "f")))]
8130 "fpsub16s\t%1, %2, %0"
8131 [(set_attr "type" "fga")
8132 (set_attr "fptype" "single")])
8134 ;; All other logical instructions have integer equivalents so they
8135 ;; are defined together.
8137 ;; (ior (not (op1)) (not (op2))) is the canonical form of NAND.
8139 (define_insn "*nand<V64mode>_vis"
8140 [(set (match_operand:V64 0 "register_operand" "=e")
8141 (ior:V64 (not:V64 (match_operand:V64 1 "register_operand" "e"))
8142 (not:V64 (match_operand:V64 2 "register_operand" "e"))))]
8145 [(set_attr "type" "fga")
8146 (set_attr "fptype" "double")])
8148 (define_insn "*nand<V32mode>_vis"
8149 [(set (match_operand:V32 0 "register_operand" "=f")
8150 (ior:V32 (not:V32 (match_operand:V32 1 "register_operand" "f"))
8151 (not:V32 (match_operand:V32 2 "register_operand" "f"))))]
8153 "fnands\t%1, %2, %0"
8154 [(set_attr "type" "fga")
8155 (set_attr "fptype" "single")])
8157 ;; Hard to generate VIS instructions. We have builtins for these.
8159 (define_insn "fpack16_vis"
8160 [(set (match_operand:V4QI 0 "register_operand" "=f")
8161 (unspec:V4QI [(match_operand:V4HI 1 "register_operand" "e")]
8165 [(set_attr "type" "fga")
8166 (set_attr "fptype" "double")])
8168 (define_insn "fpackfix_vis"
8169 [(set (match_operand:V2HI 0 "register_operand" "=f")
8170 (unspec:V2HI [(match_operand:V2SI 1 "register_operand" "e")]
8174 [(set_attr "type" "fga")
8175 (set_attr "fptype" "double")])
8177 (define_insn "fpack32_vis"
8178 [(set (match_operand:V8QI 0 "register_operand" "=e")
8179 (unspec:V8QI [(match_operand:V2SI 1 "register_operand" "e")
8180 (match_operand:V8QI 2 "register_operand" "e")]
8183 "fpack32\t%1, %2, %0"
8184 [(set_attr "type" "fga")
8185 (set_attr "fptype" "double")])
8187 (define_insn "fexpand_vis"
8188 [(set (match_operand:V4HI 0 "register_operand" "=e")
8189 (unspec:V4HI [(match_operand:V4QI 1 "register_operand" "f")]
8193 [(set_attr "type" "fga")
8194 (set_attr "fptype" "double")])
8196 ;; It may be possible to describe this operation as (1 indexed):
8197 ;; (vec_select (vec_duplicate (vec_duplicate (vec_concat 1 2)))
8198 ;; 1,5,10,14,19,23,28,32)
8199 ;; Note that (vec_merge:V8QI [(V4QI) (V4QI)] (10101010 = 170) doesn't work
8200 ;; because vec_merge expects all the operands to be of the same type.
8201 (define_insn "fpmerge_vis"
8202 [(set (match_operand:V8QI 0 "register_operand" "=e")
8203 (unspec:V8QI [(match_operand:V4QI 1 "register_operand" "f")
8204 (match_operand:V4QI 2 "register_operand" "f")]
8207 "fpmerge\t%1, %2, %0"
8208 [(set_attr "type" "fga")
8209 (set_attr "fptype" "double")])
8211 ;; Partitioned multiply instructions
8212 (define_insn "fmul8x16_vis"
8213 [(set (match_operand:V4HI 0 "register_operand" "=e")
8214 (mult:V4HI (match_operand:V4QI 1 "register_operand" "f")
8215 (match_operand:V4HI 2 "register_operand" "e")))]
8217 "fmul8x16\t%1, %2, %0"
8218 [(set_attr "type" "fpmul")
8219 (set_attr "fptype" "double")])
8221 ;; Only one of the following two insns can be a multiply.
8222 (define_insn "fmul8x16au_vis"
8223 [(set (match_operand:V4HI 0 "register_operand" "=e")
8224 (mult:V4HI (match_operand:V4QI 1 "register_operand" "f")
8225 (match_operand:V2HI 2 "register_operand" "f")))]
8227 "fmul8x16au\t%1, %2, %0"
8228 [(set_attr "type" "fpmul")
8229 (set_attr "fptype" "double")])
8231 (define_insn "fmul8x16al_vis"
8232 [(set (match_operand:V4HI 0 "register_operand" "=e")
8233 (unspec:V4HI [(match_operand:V4QI 1 "register_operand" "f")
8234 (match_operand:V2HI 2 "register_operand" "f")]
8237 "fmul8x16al\t%1, %2, %0"
8238 [(set_attr "type" "fpmul")
8239 (set_attr "fptype" "double")])
8241 ;; Only one of the following two insns can be a multiply.
8242 (define_insn "fmul8sux16_vis"
8243 [(set (match_operand:V4HI 0 "register_operand" "=e")
8244 (mult:V4HI (match_operand:V8QI 1 "register_operand" "e")
8245 (match_operand:V4HI 2 "register_operand" "e")))]
8247 "fmul8sux16\t%1, %2, %0"
8248 [(set_attr "type" "fpmul")
8249 (set_attr "fptype" "double")])
8251 (define_insn "fmul8ulx16_vis"
8252 [(set (match_operand:V4HI 0 "register_operand" "=e")
8253 (unspec:V4HI [(match_operand:V8QI 1 "register_operand" "e")
8254 (match_operand:V4HI 2 "register_operand" "e")]
8257 "fmul8ulx16\t%1, %2, %0"
8258 [(set_attr "type" "fpmul")
8259 (set_attr "fptype" "double")])
8261 ;; Only one of the following two insns can be a multiply.
8262 (define_insn "fmuld8sux16_vis"
8263 [(set (match_operand:V2SI 0 "register_operand" "=e")
8264 (mult:V2SI (match_operand:V4QI 1 "register_operand" "f")
8265 (match_operand:V2HI 2 "register_operand" "f")))]
8267 "fmuld8sux16\t%1, %2, %0"
8268 [(set_attr "type" "fpmul")
8269 (set_attr "fptype" "double")])
8271 (define_insn "fmuld8ulx16_vis"
8272 [(set (match_operand:V2SI 0 "register_operand" "=e")
8273 (unspec:V2SI [(match_operand:V4QI 1 "register_operand" "f")
8274 (match_operand:V2HI 2 "register_operand" "f")]
8277 "fmuld8ulx16\t%1, %2, %0"
8278 [(set_attr "type" "fpmul")
8279 (set_attr "fptype" "double")])
8281 ;; Using faligndata only makes sense after an alignaddr since the choice of
8282 ;; bytes to take out of each operand is dependent on the results of the last
8284 (define_insn "faligndata<V64I:mode>_vis"
8285 [(set (match_operand:V64I 0 "register_operand" "=e")
8286 (unspec:V64I [(match_operand:V64I 1 "register_operand" "e")
8287 (match_operand:V64I 2 "register_operand" "e")]
8290 "faligndata\t%1, %2, %0"
8291 [(set_attr "type" "fga")
8292 (set_attr "fptype" "double")])
8294 (define_insn "alignaddr<P:mode>_vis"
8295 [(set (match_operand:P 0 "register_operand" "=r")
8296 (unspec:P [(match_operand:P 1 "register_or_zero_operand" "rJ")
8297 (match_operand:P 2 "register_or_zero_operand" "rJ")]
8300 "alignaddr\t%r1, %r2, %0")
8302 (define_insn "pdist_vis"
8303 [(set (match_operand:DI 0 "register_operand" "=e")
8304 (unspec:DI [(match_operand:V8QI 1 "register_operand" "e")
8305 (match_operand:V8QI 2 "register_operand" "e")
8306 (match_operand:DI 3 "register_operand" "0")]
8310 [(set_attr "type" "fga")
8311 (set_attr "fptype" "double")])