1 ;; Machine description for DEC Alpha for GNU C compiler
2 ;; Copyright (C) 1992, 93, 94, 95, 96, 97, 1998 Free Software Foundation, Inc.
3 ;; Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu)
5 ;; This file is part of GNU CC.
7 ;; GNU CC is free software; you can redistribute it and/or modify
8 ;; it under the terms of the GNU General Public License as published by
9 ;; the Free Software Foundation; either version 2, or (at your option)
12 ;; GNU CC is distributed in the hope that it will be useful,
13 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
14 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 ;; GNU General Public License for more details.
17 ;; You should have received a copy of the GNU General Public License
18 ;; along with GNU CC; see the file COPYING. If not, write to
19 ;; the Free Software Foundation, 59 Temple Place - Suite 330,
20 ;; Boston, MA 02111-1307, USA.
22 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
24 ;; Uses of UNSPEC in this file:
37 ;; 2 builtin_setjmp_receiver
40 ;; 5 prologue_stack_probe_loop
42 ;; Processor type -- this attribute must exactly match the processor_type
43 ;; enumeration in alpha.h.
45 (define_attr "cpu" "ev4,ev5,ev6"
46 (const (symbol_ref "alpha_cpu")))
48 ;; Define an insn type attribute. This is used in function unit delay
49 ;; computations, among other purposes. For the most part, we use the names
50 ;; defined in the EV4 documentation, but add a few that we have to know about
54 "ild,fld,ldsym,ist,fst,ibr,fbr,jsr,iadd,ilog,shift,icmov,fcmov,icmp,imul,fadd,fmul,fcpys,fdiv,fsqrt,misc,mvi,ftoi,itof"
55 (const_string "iadd"))
57 ;; Define the operand size an insn operates on. Used primarily by mul
58 ;; and div operations that have size dependant timings.
60 (define_attr "opsize" "si,di,udi" (const_string "di"))
62 ;; The TRAP_TYPE attribute marks instructions that may generate traps
63 ;; (which are imprecise and may need a trapb if software completion
66 (define_attr "trap" "no,yes" (const_string "no"))
68 ;; The length of an instruction sequence in bytes.
70 (define_attr "length" "" (const_int 4))
72 ;; On EV4 there are two classes of resources to consider: resources needed
73 ;; to issue, and resources needed to execute. IBUS[01] are in the first
74 ;; category. ABOX, BBOX, EBOX, FBOX, IMUL & FDIV make up the second.
75 ;; (There are a few other register-like resources, but ...)
77 ; First, describe all of the issue constraints with single cycle delays.
78 ; All insns need a bus, but all except loads require one or the other.
79 (define_function_unit "ev4_ibus0" 1 0
80 (and (eq_attr "cpu" "ev4")
81 (eq_attr "type" "fst,fbr,iadd,imul,ilog,shift,icmov,icmp"))
84 (define_function_unit "ev4_ibus1" 1 0
85 (and (eq_attr "cpu" "ev4")
86 (eq_attr "type" "ist,ibr,jsr,fadd,fcmov,fcpys,fmul,fdiv,misc"))
89 ; Memory delivers its result in three cycles. Actually return one and
90 ; take care of this in adjust_cost, since we want to handle user-defined
92 (define_function_unit "ev4_abox" 1 0
93 (and (eq_attr "cpu" "ev4")
94 (eq_attr "type" "ild,fld,ldsym,ist,fst"))
97 ; Branches have no delay cost, but do tie up the unit for two cycles.
98 (define_function_unit "ev4_bbox" 1 1
99 (and (eq_attr "cpu" "ev4")
100 (eq_attr "type" "ibr,fbr,jsr"))
103 ; Arithmetic insns are normally have their results available after
104 ; two cycles. There are a number of exceptions. They are encoded in
105 ; ADJUST_COST. Some of the other insns have similar exceptions.
106 (define_function_unit "ev4_ebox" 1 0
107 (and (eq_attr "cpu" "ev4")
108 (eq_attr "type" "iadd,ilog,shift,icmov,icmp,misc"))
111 (define_function_unit "imul" 1 0
112 (and (eq_attr "cpu" "ev4")
113 (and (eq_attr "type" "imul")
114 (eq_attr "opsize" "si")))
117 (define_function_unit "imul" 1 0
118 (and (eq_attr "cpu" "ev4")
119 (and (eq_attr "type" "imul")
120 (eq_attr "opsize" "!si")))
123 (define_function_unit "ev4_fbox" 1 0
124 (and (eq_attr "cpu" "ev4")
125 (eq_attr "type" "fadd,fmul,fcpys,fcmov"))
128 (define_function_unit "fdiv" 1 0
129 (and (eq_attr "cpu" "ev4")
130 (and (eq_attr "type" "fdiv")
131 (eq_attr "opsize" "si")))
134 (define_function_unit "fdiv" 1 0
135 (and (eq_attr "cpu" "ev4")
136 (and (eq_attr "type" "fdiv")
137 (eq_attr "opsize" "di")))
140 ;; EV5 scheduling. EV5 can issue 4 insns per clock.
142 ;; EV5 has two asymetric integer units. Model this with E0 & E1 along
143 ;; with the combined resource EBOX.
145 (define_function_unit "ev5_ebox" 2 0
146 (and (eq_attr "cpu" "ev5")
147 (eq_attr "type" "!fbr,fcmov,fadd,fmul,fcpys,fdiv"))
150 ; Memory takes at least 2 clocks. Return one from here and fix up with
151 ; user-defined latencies in adjust_cost.
152 ; ??? How to: "An instruction of class LD cannot be issued in the _second_
153 ; cycle after an instruction of class ST is issued."
154 (define_function_unit "ev5_ebox" 2 0
155 (and (eq_attr "cpu" "ev5")
156 (eq_attr "type" "ild,fld,ldsym"))
159 ; Stores, shifts, multiplies can only issue to E0
160 (define_function_unit "ev5_e0" 1 0
161 (and (eq_attr "cpu" "ev5")
162 (eq_attr "type" "ist,fst,shift,imul"))
165 ; Motion video insns also issue only to E0, and take two ticks.
166 (define_function_unit "ev5_e0" 1 0
167 (and (eq_attr "cpu" "ev5")
168 (eq_attr "type" "mvi"))
171 ; Conditional moves always take 2 ticks.
172 (define_function_unit "ev5_ebox" 2 0
173 (and (eq_attr "cpu" "ev5")
174 (eq_attr "type" "icmov"))
177 ; Branches can only issue to E1
178 (define_function_unit "ev5_e1" 1 0
179 (and (eq_attr "cpu" "ev5")
180 (eq_attr "type" "ibr,jsr"))
183 ; Multiplies also use the integer multiplier.
184 ; ??? How to: "No instruction can be issued to pipe E0 exactly two
185 ; cycles before an integer multiplication completes."
186 (define_function_unit "imul" 1 0
187 (and (eq_attr "cpu" "ev5")
188 (and (eq_attr "type" "imul")
189 (eq_attr "opsize" "si")))
192 (define_function_unit "imul" 1 0
193 (and (eq_attr "cpu" "ev5")
194 (and (eq_attr "type" "imul")
195 (eq_attr "opsize" "di")))
198 (define_function_unit "imul" 1 0
199 (and (eq_attr "cpu" "ev5")
200 (and (eq_attr "type" "imul")
201 (eq_attr "opsize" "udi")))
204 ;; Similarly for the FPU we have two asymetric units. But fcpys can issue
205 ;; on either so we have to play the game again.
207 (define_function_unit "ev5_fbox" 2 0
208 (and (eq_attr "cpu" "ev5")
209 (eq_attr "type" "fadd,fcmov,fmul,fcpys,fbr,fdiv"))
212 (define_function_unit "ev5_fm" 1 0
213 (and (eq_attr "cpu" "ev5")
214 (eq_attr "type" "fmul"))
217 ; Add and cmov as you would expect; fbr never produces a result;
218 ; fdiv issues through fa to the divider,
219 (define_function_unit "ev5_fa" 1 0
220 (and (eq_attr "cpu" "ev5")
221 (eq_attr "type" "fadd,fcmov,fbr,fdiv"))
224 ; ??? How to: "No instruction can be issued to pipe FA exactly five
225 ; cycles before a floating point divide completes."
226 (define_function_unit "fdiv" 1 0
227 (and (eq_attr "cpu" "ev5")
228 (and (eq_attr "type" "fdiv")
229 (eq_attr "opsize" "si")))
230 15 15) ; 15 to 31 data dependant
232 (define_function_unit "fdiv" 1 0
233 (and (eq_attr "cpu" "ev5")
234 (and (eq_attr "type" "fdiv")
235 (eq_attr "opsize" "di")))
236 22 22) ; 22 to 60 data dependant
238 ;; EV6 scheduling. EV6 can issue 4 insns per clock.
240 ;; EV6 has two symmetric pairs ("clusters") of two asymetric integer units
241 ;; ("upper" and "lower"), yielding pipe names U0, U1, L0, L1.
243 ;; Conditional moves decompose into two independant primitives, each
244 ;; taking one cycle. Since ev6 is out-of-order, we can't see anything
246 (define_function_unit "ev6_ebox" 4 0
247 (and (eq_attr "cpu" "ev6")
248 (eq_attr "type" "icmov"))
251 (define_function_unit "ev6_ebox" 4 0
252 (and (eq_attr "cpu" "ev6")
253 (eq_attr "type" "!fbr,fcmov,fadd,fmul,fcpys,fdiv,fsqrt"))
256 ;; Integer loads take at least 3 clocks, and only issue to lower units.
257 ;; Return one from here and fix up with user-defined latencies in adjust_cost.
258 (define_function_unit "ev6_l" 2 0
259 (and (eq_attr "cpu" "ev6")
260 (eq_attr "type" "ild,ldsym,ist,fst"))
263 ;; FP loads take at least 4 clocks. Return two from here...
264 (define_function_unit "ev6_l" 2 0
265 (and (eq_attr "cpu" "ev6")
266 (eq_attr "type" "fld"))
269 ;; Motion video insns also issue only to U0, and take three ticks.
270 (define_function_unit "ev6_u0" 1 0
271 (and (eq_attr "cpu" "ev6")
272 (eq_attr "type" "mvi"))
275 (define_function_unit "ev6_u" 2 0
276 (and (eq_attr "cpu" "ev6")
277 (eq_attr "type" "mvi"))
280 ;; Shifts issue to either upper pipe.
281 (define_function_unit "ev6_u" 2 0
282 (and (eq_attr "cpu" "ev6")
283 (eq_attr "type" "shift"))
286 ;; Multiplies issue only to U1, and all take 7 ticks.
287 ;; Rather than create a new function unit just for U1, reuse IMUL
288 (define_function_unit "imul" 1 0
289 (and (eq_attr "cpu" "ev6")
290 (eq_attr "type" "imul"))
293 (define_function_unit "ev6_u" 2 0
294 (and (eq_attr "cpu" "ev6")
295 (eq_attr "type" "imul"))
298 ;; Branches issue to either upper pipe
299 (define_function_unit "ev6_u" 2 0
300 (and (eq_attr "cpu" "ev6")
301 (eq_attr "type" "ibr"))
304 ;; Calls only issue to L0.
305 (define_function_unit "ev6_l0" 1 0
306 (and (eq_attr "cpu" "ev6")
307 (eq_attr "type" "jsr"))
310 (define_function_unit "ev6_l" 2 0
311 (and (eq_attr "cpu" "ev6")
312 (eq_attr "type" "jsr"))
315 ;; Ftoi/itof only issue to lower pipes
316 (define_function_unit "ev6_l" 2 0
317 (and (eq_attr "cpu" "ev6")
318 (eq_attr "type" "ftoi"))
321 (define_function_unit "ev6_l" 2 0
322 (and (eq_attr "cpu" "ev6")
323 (eq_attr "type" "itof"))
326 ;; For the FPU we are very similar to EV5, except there's no insn that
327 ;; can issue to fm & fa, so we get to leave that out.
329 (define_function_unit "ev6_fm" 1 0
330 (and (eq_attr "cpu" "ev6")
331 (eq_attr "type" "fmul"))
334 (define_function_unit "ev6_fa" 1 0
335 (and (eq_attr "cpu" "ev6")
336 (eq_attr "type" "fadd,fcpys,fbr,fdiv,fsqrt"))
339 (define_function_unit "ev6_fa" 1 0
340 (and (eq_attr "cpu" "ev6")
341 (eq_attr "type" "fcmov"))
344 (define_function_unit "fdiv" 1 0
345 (and (eq_attr "cpu" "ev6")
346 (and (eq_attr "type" "fdiv")
347 (eq_attr "opsize" "si")))
350 (define_function_unit "fdiv" 1 0
351 (and (eq_attr "cpu" "ev6")
352 (and (eq_attr "type" "fdiv")
353 (eq_attr "opsize" "di")))
356 (define_function_unit "fsqrt" 1 0
357 (and (eq_attr "cpu" "ev6")
358 (and (eq_attr "type" "fsqrt")
359 (eq_attr "opsize" "si")))
362 (define_function_unit "fsqrt" 1 0
363 (and (eq_attr "cpu" "ev6")
364 (and (eq_attr "type" "fsqrt")
365 (eq_attr "opsize" "di")))
368 ; ??? The FPU communicates with memory and the integer register file
369 ; via two fp store units. We need a slot in the fst immediately, and
370 ; a slot in LOW after the operand data is ready. At which point the
371 ; data may be moved either to the store queue or the integer register
372 ; file and the insn retired.
375 ;; First define the arithmetic insns. Note that the 32-bit forms also
378 ;; Handle 32-64 bit extension from memory to a floating point register
379 ;; specially, since this ocurrs frequently in int->double conversions.
380 ;; This is done with a define_split after reload converting the plain
381 ;; sign-extension into a load+unspec, which of course results in lds+cvtlq.
383 ;; Note that while we must retain the =f case in the insn for reload's
384 ;; benefit, it should be eliminated after reload, so we should never emit
385 ;; code for that case. But we don't reject the possibility.
387 (define_insn "extendsidi2"
388 [(set (match_operand:DI 0 "register_operand" "=r,r,?f")
389 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "r,m,m")))]
394 lds %0,%1\;cvtlq %0,%0"
395 [(set_attr "type" "iadd,ild,fld")
396 (set_attr "length" "*,*,8")])
398 ;; Due to issues with CLASS_CANNOT_CHANGE_SIZE, we cannot use a subreg here.
400 [(set (match_operand:DI 0 "hard_fp_register_operand" "")
401 (sign_extend:DI (match_operand:SI 1 "memory_operand" "")))]
403 [(set (match_dup 2) (match_dup 1))
404 (set (match_dup 0) (unspec:DI [(match_dup 2)] 4))]
405 "operands[2] = gen_rtx_REG (SImode, REGNO (operands[0]));")
408 [(set (match_operand:DI 0 "register_operand" "=f")
409 (unspec:DI [(match_operand:SI 1 "register_operand" "f")] 4))]
412 [(set_attr "type" "fadd")])
414 ;; Do addsi3 the way expand_binop would do if we didn't have one. This
415 ;; generates better code. We have the anonymous addsi3 pattern below in
416 ;; case combine wants to make it.
417 (define_expand "addsi3"
418 [(set (match_operand:SI 0 "register_operand" "")
419 (plus:SI (match_operand:SI 1 "reg_or_0_operand" "")
420 (match_operand:SI 2 "add_operand" "")))]
423 { emit_insn (gen_rtx_SET (VOIDmode, gen_lowpart (DImode, operands[0]),
424 gen_rtx_PLUS (DImode,
425 gen_lowpart (DImode, operands[1]),
426 gen_lowpart (DImode, operands[2]))));
431 [(set (match_operand:SI 0 "register_operand" "=r,r,r,r")
432 (plus:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ,rJ,rJ,rJ")
433 (match_operand:SI 2 "add_operand" "rI,O,K,L")))]
442 [(set (match_operand:SI 0 "register_operand" "")
443 (plus:SI (match_operand:SI 1 "register_operand" "")
444 (match_operand:SI 2 "const_int_operand" "")))]
445 "! add_operand (operands[2], SImode)"
446 [(set (match_dup 0) (plus:SI (match_dup 1) (match_dup 3)))
447 (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 4)))]
450 HOST_WIDE_INT val = INTVAL (operands[2]);
451 HOST_WIDE_INT low = (val & 0xffff) - 2 * (val & 0x8000);
452 HOST_WIDE_INT rest = val - low;
454 operands[3] = GEN_INT (rest);
455 operands[4] = GEN_INT (low);
459 [(set (match_operand:DI 0 "register_operand" "=r,r")
461 (plus:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ,rJ")
462 (match_operand:SI 2 "sext_add_operand" "rI,O"))))]
469 [(set (match_operand:DI 0 "register_operand" "")
471 (plus:SI (match_operand:SI 1 "register_operand" "")
472 (match_operand:SI 2 "const_int_operand" ""))))
473 (clobber (match_operand:SI 3 "register_operand" ""))]
474 "! sext_add_operand (operands[2], SImode) && INTVAL (operands[2]) > 0
475 && INTVAL (operands[2]) % 4 == 0"
476 [(set (match_dup 3) (match_dup 4))
477 (set (match_dup 0) (sign_extend:DI (plus:SI (mult:SI (match_dup 3)
482 HOST_WIDE_INT val = INTVAL (operands[2]) / 4;
488 operands[4] = GEN_INT (val);
489 operands[5] = GEN_INT (mult);
493 [(set (match_operand:DI 0 "register_operand" "")
495 (plus:SI (match_operator:SI 1 "comparison_operator"
496 [(match_operand 2 "" "")
497 (match_operand 3 "" "")])
498 (match_operand:SI 4 "add_operand" ""))))
499 (clobber (match_operand:DI 5 "register_operand" ""))]
501 [(set (match_dup 5) (match_dup 6))
502 (set (match_dup 0) (sign_extend:DI (plus:SI (match_dup 7) (match_dup 4))))]
505 operands[6] = gen_rtx_fmt_ee (GET_CODE (operands[1]), DImode,
506 operands[2], operands[3]);
507 operands[7] = gen_lowpart (SImode, operands[5]);
510 (define_insn "adddi3"
511 [(set (match_operand:DI 0 "register_operand" "=r,r,r,r")
512 (plus:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ,rJ,rJ")
513 (match_operand:DI 2 "add_operand" "rI,O,K,L")))]
521 ;; Don't do this if we are adjusting SP since we don't want to do
524 [(set (match_operand:DI 0 "register_operand" "")
525 (plus:DI (match_operand:DI 1 "register_operand" "")
526 (match_operand:DI 2 "const_int_operand" "")))]
527 "! add_operand (operands[2], DImode)
528 && REGNO (operands[0]) != STACK_POINTER_REGNUM"
529 [(set (match_dup 0) (plus:DI (match_dup 1) (match_dup 3)))
530 (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 4)))]
533 HOST_WIDE_INT val = INTVAL (operands[2]);
534 HOST_WIDE_INT low = (val & 0xffff) - 2 * (val & 0x8000);
535 HOST_WIDE_INT rest = val - low;
537 operands[3] = GEN_INT (rest);
538 operands[4] = GEN_INT (low);
542 [(set (match_operand:SI 0 "register_operand" "=r,r")
543 (plus:SI (mult:SI (match_operand:SI 1 "reg_or_0_operand" "rJ,rJ")
544 (match_operand:SI 2 "const48_operand" "I,I"))
545 (match_operand:SI 3 "sext_add_operand" "rI,O")))]
552 [(set (match_operand:DI 0 "register_operand" "=r,r")
554 (plus:SI (mult:SI (match_operand:SI 1 "reg_or_0_operand" "rJ,rJ")
555 (match_operand:SI 2 "const48_operand" "I,I"))
556 (match_operand:SI 3 "sext_add_operand" "rI,O"))))]
563 [(set (match_operand:DI 0 "register_operand" "")
565 (plus:SI (mult:SI (match_operator:SI 1 "comparison_operator"
566 [(match_operand 2 "" "")
567 (match_operand 3 "" "")])
568 (match_operand:SI 4 "const48_operand" ""))
569 (match_operand:SI 5 "add_operand" ""))))
570 (clobber (match_operand:DI 6 "register_operand" ""))]
572 [(set (match_dup 6) (match_dup 7))
574 (sign_extend:DI (plus:SI (mult:SI (match_dup 8) (match_dup 4))
578 operands[7] = gen_rtx_fmt_ee (GET_CODE (operands[1]), DImode,
579 operands[2], operands[3]);
580 operands[8] = gen_lowpart (SImode, operands[6]);
584 [(set (match_operand:DI 0 "register_operand" "=r,r")
585 (plus:DI (mult:DI (match_operand:DI 1 "reg_or_0_operand" "rJ,rJ")
586 (match_operand:DI 2 "const48_operand" "I,I"))
587 (match_operand:DI 3 "reg_or_8bit_operand" "rI,O")))]
593 ;; These variants of the above insns can occur if the third operand
594 ;; is the frame pointer. This is a kludge, but there doesn't
595 ;; seem to be a way around it. Only recognize them while reloading.
598 [(set (match_operand:DI 0 "some_operand" "=&r")
599 (plus:DI (plus:DI (match_operand:DI 1 "some_operand" "r")
600 (match_operand:DI 2 "some_operand" "r"))
601 (match_operand:DI 3 "some_operand" "rIOKL")))]
606 [(set (match_operand:DI 0 "register_operand" "")
607 (plus:DI (plus:DI (match_operand:DI 1 "register_operand" "")
608 (match_operand:DI 2 "register_operand" ""))
609 (match_operand:DI 3 "add_operand" "")))]
611 [(set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))
612 (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 3)))]
616 [(set (match_operand:SI 0 "some_operand" "=&r")
617 (plus:SI (plus:SI (mult:SI (match_operand:SI 1 "some_operand" "rJ")
618 (match_operand:SI 2 "const48_operand" "I"))
619 (match_operand:SI 3 "some_operand" "r"))
620 (match_operand:SI 4 "some_operand" "rIOKL")))]
625 [(set (match_operand:SI 0 "register_operand" "r")
626 (plus:SI (plus:SI (mult:SI (match_operand:SI 1 "reg_or_0_operand" "")
627 (match_operand:SI 2 "const48_operand" ""))
628 (match_operand:SI 3 "register_operand" ""))
629 (match_operand:SI 4 "add_operand" "rIOKL")))]
632 (plus:SI (mult:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
633 (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 4)))]
637 [(set (match_operand:DI 0 "some_operand" "=&r")
640 (mult:SI (match_operand:SI 1 "some_operand" "rJ")
641 (match_operand:SI 2 "const48_operand" "I"))
642 (match_operand:SI 3 "some_operand" "r"))
643 (match_operand:SI 4 "some_operand" "rIOKL"))))]
648 [(set (match_operand:DI 0 "register_operand" "")
651 (mult:SI (match_operand:SI 1 "reg_or_0_operand" "")
652 (match_operand:SI 2 "const48_operand" ""))
653 (match_operand:SI 3 "register_operand" ""))
654 (match_operand:SI 4 "add_operand" ""))))]
657 (plus:SI (mult:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
658 (set (match_dup 0) (sign_extend:DI (plus:SI (match_dup 5) (match_dup 4))))]
660 { operands[5] = gen_lowpart (SImode, operands[0]);
664 [(set (match_operand:DI 0 "some_operand" "=&r")
665 (plus:DI (plus:DI (mult:DI (match_operand:DI 1 "some_operand" "rJ")
666 (match_operand:DI 2 "const48_operand" "I"))
667 (match_operand:DI 3 "some_operand" "r"))
668 (match_operand:DI 4 "some_operand" "rIOKL")))]
673 [(set (match_operand:DI 0 "register_operand" "=")
674 (plus:DI (plus:DI (mult:DI (match_operand:DI 1 "reg_or_0_operand" "")
675 (match_operand:DI 2 "const48_operand" ""))
676 (match_operand:DI 3 "register_operand" ""))
677 (match_operand:DI 4 "add_operand" "")))]
680 (plus:DI (mult:DI (match_dup 1) (match_dup 2)) (match_dup 3)))
681 (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 4)))]
684 (define_insn "negsi2"
685 [(set (match_operand:SI 0 "register_operand" "=r")
686 (neg:SI (match_operand:SI 1 "reg_or_8bit_operand" "rI")))]
691 [(set (match_operand:DI 0 "register_operand" "=r")
692 (sign_extend:DI (neg:SI
693 (match_operand:SI 1 "reg_or_8bit_operand" "rI"))))]
697 (define_insn "negdi2"
698 [(set (match_operand:DI 0 "register_operand" "=r")
699 (neg:DI (match_operand:DI 1 "reg_or_8bit_operand" "rI")))]
703 (define_expand "subsi3"
704 [(set (match_operand:SI 0 "register_operand" "")
705 (minus:SI (match_operand:SI 1 "reg_or_0_operand" "")
706 (match_operand:SI 2 "reg_or_8bit_operand" "")))]
709 { emit_insn (gen_rtx_SET (VOIDmode, gen_lowpart (DImode, operands[0]),
710 gen_rtx_MINUS (DImode,
711 gen_lowpart (DImode, operands[1]),
712 gen_lowpart (DImode, operands[2]))));
717 [(set (match_operand:SI 0 "register_operand" "=r")
718 (minus:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
719 (match_operand:SI 2 "reg_or_8bit_operand" "rI")))]
724 [(set (match_operand:DI 0 "register_operand" "=r")
725 (sign_extend:DI (minus:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
726 (match_operand:SI 2 "reg_or_8bit_operand" "rI"))))]
730 (define_insn "subdi3"
731 [(set (match_operand:DI 0 "register_operand" "=r")
732 (minus:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
733 (match_operand:DI 2 "reg_or_8bit_operand" "rI")))]
738 [(set (match_operand:SI 0 "register_operand" "=r")
739 (minus:SI (mult:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
740 (match_operand:SI 2 "const48_operand" "I"))
741 (match_operand:SI 3 "reg_or_8bit_operand" "rI")))]
746 [(set (match_operand:DI 0 "register_operand" "=r")
748 (minus:SI (mult:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
749 (match_operand:SI 2 "const48_operand" "I"))
750 (match_operand:SI 3 "reg_or_8bit_operand" "rI"))))]
755 [(set (match_operand:DI 0 "register_operand" "=r")
756 (minus:DI (mult:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
757 (match_operand:DI 2 "const48_operand" "I"))
758 (match_operand:DI 3 "reg_or_8bit_operand" "rI")))]
762 (define_insn "mulsi3"
763 [(set (match_operand:SI 0 "register_operand" "=r")
764 (mult:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ")
765 (match_operand:SI 2 "reg_or_0_operand" "rJ")))]
768 [(set_attr "type" "imul")
769 (set_attr "opsize" "si")])
772 [(set (match_operand:DI 0 "register_operand" "=r")
773 (sign_extend:DI (mult:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ")
774 (match_operand:SI 2 "reg_or_0_operand" "rJ"))))]
777 [(set_attr "type" "imul")
778 (set_attr "opsize" "si")])
780 (define_insn "muldi3"
781 [(set (match_operand:DI 0 "register_operand" "=r")
782 (mult:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ")
783 (match_operand:DI 2 "reg_or_0_operand" "rJ")))]
786 [(set_attr "type" "imul")])
788 (define_insn "umuldi3_highpart"
789 [(set (match_operand:DI 0 "register_operand" "=r")
792 (mult:TI (zero_extend:TI (match_operand:DI 1 "register_operand" "r"))
793 (zero_extend:TI (match_operand:DI 2 "register_operand" "r")))
797 [(set_attr "type" "imul")
798 (set_attr "opsize" "udi")])
801 [(set (match_operand:DI 0 "register_operand" "=r")
804 (mult:TI (zero_extend:TI (match_operand:DI 1 "register_operand" "r"))
805 (match_operand:TI 2 "cint8_operand" "I"))
809 [(set_attr "type" "imul")
810 (set_attr "opsize" "udi")])
812 ;; The divide and remainder operations always take their inputs from
813 ;; r24 and r25, put their output in r27, and clobber r23 and r28.
815 ;; ??? Force sign-extension here because some versions of OSF/1 don't
816 ;; do the right thing if the inputs are not properly sign-extended.
817 ;; But Linux, for instance, does not have this problem. Is it worth
818 ;; the complication here to eliminate the sign extension?
820 (define_expand "divsi3"
822 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))
824 (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "")))
825 (parallel [(set (reg:DI 27)
826 (sign_extend:DI (div:SI (reg:DI 24) (reg:DI 25))))
827 (clobber (reg:DI 23))
828 (clobber (reg:DI 28))])
829 (set (match_operand:SI 0 "general_operand" "")
830 (subreg:SI (reg:DI 27) 0))]
834 (define_expand "udivsi3"
836 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))
838 (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "")))
839 (parallel [(set (reg:DI 27)
840 (sign_extend:DI (udiv:SI (reg:DI 24) (reg:DI 25))))
841 (clobber (reg:DI 23))
842 (clobber (reg:DI 28))])
843 (set (match_operand:SI 0 "general_operand" "")
844 (subreg:SI (reg:DI 27) 0))]
848 (define_expand "modsi3"
850 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))
852 (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "")))
853 (parallel [(set (reg:DI 27)
854 (sign_extend:DI (mod:SI (reg:DI 24) (reg:DI 25))))
855 (clobber (reg:DI 23))
856 (clobber (reg:DI 28))])
857 (set (match_operand:SI 0 "general_operand" "")
858 (subreg:SI (reg:DI 27) 0))]
862 (define_expand "umodsi3"
864 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))
866 (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "")))
867 (parallel [(set (reg:DI 27)
868 (sign_extend:DI (umod:SI (reg:DI 24) (reg:DI 25))))
869 (clobber (reg:DI 23))
870 (clobber (reg:DI 28))])
871 (set (match_operand:SI 0 "general_operand" "")
872 (subreg:SI (reg:DI 27) 0))]
876 (define_expand "divdi3"
877 [(set (reg:DI 24) (match_operand:DI 1 "input_operand" ""))
878 (set (reg:DI 25) (match_operand:DI 2 "input_operand" ""))
879 (parallel [(set (reg:DI 27)
882 (clobber (reg:DI 23))
883 (clobber (reg:DI 28))])
884 (set (match_operand:DI 0 "general_operand" "")
889 (define_expand "udivdi3"
890 [(set (reg:DI 24) (match_operand:DI 1 "input_operand" ""))
891 (set (reg:DI 25) (match_operand:DI 2 "input_operand" ""))
892 (parallel [(set (reg:DI 27)
895 (clobber (reg:DI 23))
896 (clobber (reg:DI 28))])
897 (set (match_operand:DI 0 "general_operand" "")
902 (define_expand "moddi3"
903 [(set (reg:DI 24) (match_operand:DI 1 "input_operand" ""))
904 (set (reg:DI 25) (match_operand:DI 2 "input_operand" ""))
905 (parallel [(set (reg:DI 27)
908 (clobber (reg:DI 23))
909 (clobber (reg:DI 28))])
910 (set (match_operand:DI 0 "general_operand" "")
915 (define_expand "umoddi3"
916 [(set (reg:DI 24) (match_operand:DI 1 "input_operand" ""))
917 (set (reg:DI 25) (match_operand:DI 2 "input_operand" ""))
918 (parallel [(set (reg:DI 27)
921 (clobber (reg:DI 23))
922 (clobber (reg:DI 28))])
923 (set (match_operand:DI 0 "general_operand" "")
928 ;; Lengths of 8 for ldq $t12,__divq($gp); jsr $t9,($t12),__divq as
929 ;; expanded by the assembler.
932 (sign_extend:DI (match_operator:SI 1 "divmod_operator"
933 [(reg:DI 24) (reg:DI 25)])))
934 (clobber (reg:DI 23))
935 (clobber (reg:DI 28))]
938 [(set_attr "type" "jsr")
939 (set_attr "length" "8")])
943 (match_operator:DI 1 "divmod_operator"
944 [(reg:DI 24) (reg:DI 25)]))
945 (clobber (reg:DI 23))
946 (clobber (reg:DI 28))]
949 [(set_attr "type" "jsr")
950 (set_attr "length" "8")])
952 ;; Next are the basic logical operations. These only exist in DImode.
954 (define_insn "anddi3"
955 [(set (match_operand:DI 0 "register_operand" "=r,r,r")
956 (and:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ,rJ")
957 (match_operand:DI 2 "and_operand" "rI,N,MH")))]
963 [(set_attr "type" "ilog,ilog,shift")])
965 ;; There are times when we can split an AND into two AND insns. This occurs
966 ;; when we can first clear any bytes and then clear anything else. For
967 ;; example "I & 0xffff07" is "(I & 0xffffff) & 0xffffffffffffff07".
968 ;; Only do this when running on 64-bit host since the computations are
969 ;; too messy otherwise.
972 [(set (match_operand:DI 0 "register_operand" "")
973 (and:DI (match_operand:DI 1 "register_operand" "")
974 (match_operand:DI 2 "const_int_operand" "")))]
975 "HOST_BITS_PER_WIDE_INT == 64 && ! and_operand (operands[2], DImode)"
976 [(set (match_dup 0) (and:DI (match_dup 1) (match_dup 3)))
977 (set (match_dup 0) (and:DI (match_dup 0) (match_dup 4)))]
980 unsigned HOST_WIDE_INT mask1 = INTVAL (operands[2]);
981 unsigned HOST_WIDE_INT mask2 = mask1;
984 /* For each byte that isn't all zeros, make it all ones. */
985 for (i = 0; i < 64; i += 8)
986 if ((mask1 & ((HOST_WIDE_INT) 0xff << i)) != 0)
987 mask1 |= (HOST_WIDE_INT) 0xff << i;
989 /* Now turn on any bits we've just turned off. */
992 operands[3] = GEN_INT (mask1);
993 operands[4] = GEN_INT (mask2);
996 (define_insn "zero_extendqihi2"
997 [(set (match_operand:HI 0 "register_operand" "=r")
998 (zero_extend:HI (match_operand:QI 1 "register_operand" "r")))]
1001 [(set_attr "type" "ilog")])
1004 [(set (match_operand:SI 0 "register_operand" "=r,r")
1005 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "r,m")))]
1010 [(set_attr "type" "ilog,ild")])
1013 [(set (match_operand:SI 0 "register_operand" "=r")
1014 (zero_extend:SI (match_operand:QI 1 "register_operand" "r")))]
1017 [(set_attr "type" "ilog")])
1019 (define_expand "zero_extendqisi2"
1020 [(set (match_operand:SI 0 "register_operand" "")
1021 (zero_extend:SI (match_operand:QI 1 "register_operand" "")))]
1026 [(set (match_operand:DI 0 "register_operand" "=r,r")
1027 (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "r,m")))]
1032 [(set_attr "type" "ilog,ild")])
1035 [(set (match_operand:DI 0 "register_operand" "=r")
1036 (zero_extend:DI (match_operand:QI 1 "register_operand" "r")))]
1039 [(set_attr "type" "ilog")])
1041 (define_expand "zero_extendqidi2"
1042 [(set (match_operand:DI 0 "register_operand" "")
1043 (zero_extend:DI (match_operand:QI 1 "register_operand" "")))]
1048 [(set (match_operand:SI 0 "register_operand" "=r,r")
1049 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "r,m")))]
1054 [(set_attr "type" "shift,ild")])
1057 [(set (match_operand:SI 0 "register_operand" "=r")
1058 (zero_extend:SI (match_operand:HI 1 "register_operand" "r")))]
1061 [(set_attr "type" "shift")])
1063 (define_expand "zero_extendhisi2"
1064 [(set (match_operand:SI 0 "register_operand" "")
1065 (zero_extend:SI (match_operand:HI 1 "register_operand" "")))]
1070 [(set (match_operand:DI 0 "register_operand" "=r,r")
1071 (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "r,m")))]
1076 [(set_attr "type" "shift,ild")])
1079 [(set (match_operand:DI 0 "register_operand" "=r")
1080 (zero_extend:DI (match_operand:HI 1 "register_operand" "r")))]
1083 [(set_attr "type" "shift")])
1085 (define_expand "zero_extendhidi2"
1086 [(set (match_operand:DI 0 "register_operand" "")
1087 (zero_extend:DI (match_operand:HI 1 "register_operand" "")))]
1091 (define_insn "zero_extendsidi2"
1092 [(set (match_operand:DI 0 "register_operand" "=r")
1093 (zero_extend:DI (match_operand:SI 1 "register_operand" "r")))]
1096 [(set_attr "type" "shift")])
1099 [(set (match_operand:DI 0 "register_operand" "=r")
1100 (and:DI (not:DI (match_operand:DI 1 "reg_or_8bit_operand" "rI"))
1101 (match_operand:DI 2 "reg_or_0_operand" "rJ")))]
1104 [(set_attr "type" "ilog")])
1106 (define_insn "iordi3"
1107 [(set (match_operand:DI 0 "register_operand" "=r,r")
1108 (ior:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ")
1109 (match_operand:DI 2 "or_operand" "rI,N")))]
1114 [(set_attr "type" "ilog")])
1116 (define_insn "one_cmpldi2"
1117 [(set (match_operand:DI 0 "register_operand" "=r")
1118 (not:DI (match_operand:DI 1 "reg_or_8bit_operand" "rI")))]
1121 [(set_attr "type" "ilog")])
1124 [(set (match_operand:DI 0 "register_operand" "=r")
1125 (ior:DI (not:DI (match_operand:DI 1 "reg_or_8bit_operand" "rI"))
1126 (match_operand:DI 2 "reg_or_0_operand" "rJ")))]
1129 [(set_attr "type" "ilog")])
1131 (define_insn "xordi3"
1132 [(set (match_operand:DI 0 "register_operand" "=r,r")
1133 (xor:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ")
1134 (match_operand:DI 2 "or_operand" "rI,N")))]
1139 [(set_attr "type" "ilog")])
1142 [(set (match_operand:DI 0 "register_operand" "=r")
1143 (not:DI (xor:DI (match_operand:DI 1 "register_operand" "%rJ")
1144 (match_operand:DI 2 "register_operand" "rI"))))]
1147 [(set_attr "type" "ilog")])
1149 ;; Handle the FFS insn if we support CIX.
1151 (define_expand "ffsdi2"
1153 (unspec [(match_operand:DI 1 "register_operand" "")] 1))
1155 (plus:DI (match_dup 2) (const_int 1)))
1156 (set (match_operand:DI 0 "register_operand" "")
1157 (if_then_else:DI (eq (match_dup 1) (const_int 0))
1158 (const_int 0) (match_dup 3)))]
1162 operands[2] = gen_reg_rtx (DImode);
1163 operands[3] = gen_reg_rtx (DImode);
1167 [(set (match_operand:DI 0 "register_operand" "=r")
1168 (unspec [(match_operand:DI 1 "register_operand" "r")] 1))]
1171 ; ev6 calls all mvi and cttz/ctlz/popc class imisc, so just
1172 ; reuse the existing type name.
1173 [(set_attr "type" "mvi")])
1175 ;; Next come the shifts and the various extract and insert operations.
1177 (define_insn "ashldi3"
1178 [(set (match_operand:DI 0 "register_operand" "=r,r")
1179 (ashift:DI (match_operand:DI 1 "reg_or_0_operand" "rJ,rJ")
1180 (match_operand:DI 2 "reg_or_6bit_operand" "P,rI")))]
1184 switch (which_alternative)
1187 if (operands[2] == const1_rtx)
1188 return \"addq %r1,%r1,%0\";
1190 return \"s%P2addq %r1,0,%0\";
1192 return \"sll %r1,%2,%0\";
1197 [(set_attr "type" "iadd,shift")])
1199 ;; ??? The following pattern is made by combine, but earlier phases
1200 ;; (specifically flow) can't handle it. This occurs in jump.c. Deal
1201 ;; with this in a better way at some point.
1203 ;; [(set (match_operand:DI 0 "register_operand" "=r")
1205 ;; (subreg:SI (ashift:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1206 ;; (match_operand:DI 2 "const_int_operand" "P"))
1208 ;; "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 3"
1211 ;; if (operands[2] == const1_rtx)
1212 ;; return \"addl %r1,%r1,%0\";
1214 ;; return \"s%P2addl %r1,0,%0\";
1216 ;; [(set_attr "type" "iadd")])
1218 (define_insn "lshrdi3"
1219 [(set (match_operand:DI 0 "register_operand" "=r")
1220 (lshiftrt:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1221 (match_operand:DI 2 "reg_or_6bit_operand" "rI")))]
1224 [(set_attr "type" "shift")])
1226 (define_insn "ashrdi3"
1227 [(set (match_operand:DI 0 "register_operand" "=r")
1228 (ashiftrt:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1229 (match_operand:DI 2 "reg_or_6bit_operand" "rI")))]
1232 [(set_attr "type" "shift")])
1234 (define_expand "extendqihi2"
1236 (ashift:DI (match_operand:QI 1 "some_operand" "")
1238 (set (match_operand:HI 0 "register_operand" "")
1239 (ashiftrt:DI (match_dup 2)
1246 emit_insn (gen_extendqihi2x (operands[0],
1247 force_reg (QImode, operands[1])));
1251 /* If we have an unaligned MEM, extend to DImode (which we do
1252 specially) and then copy to the result. */
1253 if (unaligned_memory_operand (operands[1], HImode))
1255 rtx temp = gen_reg_rtx (DImode);
1257 emit_insn (gen_extendqidi2 (temp, operands[1]));
1258 emit_move_insn (operands[0], gen_lowpart (HImode, temp));
1262 operands[0] = gen_lowpart (DImode, operands[0]);
1263 operands[1] = gen_lowpart (DImode, force_reg (QImode, operands[1]));
1264 operands[2] = gen_reg_rtx (DImode);
1267 (define_insn "extendqidi2x"
1268 [(set (match_operand:DI 0 "register_operand" "=r")
1269 (sign_extend:DI (match_operand:QI 1 "register_operand" "r")))]
1272 [(set_attr "type" "shift")])
1274 (define_insn "extendhidi2x"
1275 [(set (match_operand:DI 0 "register_operand" "=r")
1276 (sign_extend:DI (match_operand:HI 1 "register_operand" "r")))]
1279 [(set_attr "type" "shift")])
1281 (define_insn "extendqisi2x"
1282 [(set (match_operand:SI 0 "register_operand" "=r")
1283 (sign_extend:SI (match_operand:QI 1 "register_operand" "r")))]
1286 [(set_attr "type" "shift")])
1288 (define_insn "extendhisi2x"
1289 [(set (match_operand:SI 0 "register_operand" "=r")
1290 (sign_extend:SI (match_operand:HI 1 "register_operand" "r")))]
1293 [(set_attr "type" "shift")])
1295 (define_insn "extendqihi2x"
1296 [(set (match_operand:HI 0 "register_operand" "=r")
1297 (sign_extend:HI (match_operand:QI 1 "register_operand" "r")))]
1300 [(set_attr "type" "shift")])
1302 (define_expand "extendqisi2"
1304 (ashift:DI (match_operand:QI 1 "some_operand" "")
1306 (set (match_operand:SI 0 "register_operand" "")
1307 (ashiftrt:DI (match_dup 2)
1314 emit_insn (gen_extendqisi2x (operands[0],
1315 force_reg (QImode, operands[1])));
1319 /* If we have an unaligned MEM, extend to a DImode form of
1320 the result (which we do specially). */
1321 if (unaligned_memory_operand (operands[1], QImode))
1323 rtx temp = gen_reg_rtx (DImode);
1325 emit_insn (gen_extendqidi2 (temp, operands[1]));
1326 emit_move_insn (operands[0], gen_lowpart (SImode, temp));
1330 operands[0] = gen_lowpart (DImode, operands[0]);
1331 operands[1] = gen_lowpart (DImode, force_reg (QImode, operands[1]));
1332 operands[2] = gen_reg_rtx (DImode);
1335 (define_expand "extendqidi2"
1337 (ashift:DI (match_operand:QI 1 "some_operand" "")
1339 (set (match_operand:DI 0 "register_operand" "")
1340 (ashiftrt:DI (match_dup 2)
1347 emit_insn (gen_extendqidi2x (operands[0],
1348 force_reg (QImode, operands[1])));
1352 if (unaligned_memory_operand (operands[1], QImode))
1355 = gen_unaligned_extendqidi (operands[0],
1356 get_unaligned_address (operands[1], 1));
1358 alpha_set_memflags (seq, operands[1]);
1363 operands[1] = gen_lowpart (DImode, force_reg (QImode, operands[1]));
1364 operands[2] = gen_reg_rtx (DImode);
1367 (define_expand "extendhisi2"
1369 (ashift:DI (match_operand:HI 1 "some_operand" "")
1371 (set (match_operand:SI 0 "register_operand" "")
1372 (ashiftrt:DI (match_dup 2)
1379 emit_insn (gen_extendhisi2x (operands[0],
1380 force_reg (HImode, operands[1])));
1384 /* If we have an unaligned MEM, extend to a DImode form of
1385 the result (which we do specially). */
1386 if (unaligned_memory_operand (operands[1], HImode))
1388 rtx temp = gen_reg_rtx (DImode);
1390 emit_insn (gen_extendhidi2 (temp, operands[1]));
1391 emit_move_insn (operands[0], gen_lowpart (SImode, temp));
1395 operands[0] = gen_lowpart (DImode, operands[0]);
1396 operands[1] = gen_lowpart (DImode, force_reg (HImode, operands[1]));
1397 operands[2] = gen_reg_rtx (DImode);
1400 (define_expand "extendhidi2"
1402 (ashift:DI (match_operand:HI 1 "some_operand" "")
1404 (set (match_operand:DI 0 "register_operand" "")
1405 (ashiftrt:DI (match_dup 2)
1412 emit_insn (gen_extendhidi2x (operands[0],
1413 force_reg (HImode, operands[1])));
1417 if (unaligned_memory_operand (operands[1], HImode))
1420 = gen_unaligned_extendhidi (operands[0],
1421 get_unaligned_address (operands[1], 2));
1423 alpha_set_memflags (seq, operands[1]);
1428 operands[1] = gen_lowpart (DImode, force_reg (HImode, operands[1]));
1429 operands[2] = gen_reg_rtx (DImode);
1432 ;; Here's how we sign extend an unaligned byte and halfword. Doing this
1433 ;; as a pattern saves one instruction. The code is similar to that for
1434 ;; the unaligned loads (see below).
1436 ;; Operand 1 is the address + 1 (+2 for HI), operand 0 is the result.
1437 (define_expand "unaligned_extendqidi"
1438 [(set (match_dup 2) (match_operand:DI 1 "address_operand" ""))
1440 (mem:DI (and:DI (plus:DI (match_dup 2) (const_int -1))
1443 (ashift:DI (match_dup 3)
1444 (minus:DI (const_int 56)
1446 (and:DI (plus:DI (match_dup 2) (const_int -1))
1449 (set (subreg:DI (match_operand:QI 0 "register_operand" "") 0)
1450 (ashiftrt:DI (match_dup 4) (const_int 56)))]
1453 { operands[2] = gen_reg_rtx (DImode);
1454 operands[3] = gen_reg_rtx (DImode);
1455 operands[4] = gen_reg_rtx (DImode);
1458 (define_expand "unaligned_extendhidi"
1459 [(set (match_dup 2) (match_operand:DI 1 "address_operand" ""))
1461 (mem:DI (and:DI (plus:DI (match_dup 2) (const_int -2))
1464 (ashift:DI (match_dup 3)
1465 (minus:DI (const_int 56)
1467 (and:DI (plus:DI (match_dup 2) (const_int -1))
1470 (set (subreg:DI (match_operand:QI 0 "register_operand" "") 0)
1471 (ashiftrt:DI (match_dup 4) (const_int 48)))]
1474 { operands[2] = gen_reg_rtx (DImode);
1475 operands[3] = gen_reg_rtx (DImode);
1476 operands[4] = gen_reg_rtx (DImode);
1480 [(set (match_operand:DI 0 "register_operand" "=r")
1481 (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1482 (match_operand:DI 2 "mode_width_operand" "n")
1483 (match_operand:DI 3 "mul8_operand" "I")))]
1485 "ext%M2l %r1,%s3,%0"
1486 [(set_attr "type" "shift")])
1488 (define_insn "extxl"
1489 [(set (match_operand:DI 0 "register_operand" "=r")
1490 (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1491 (match_operand:DI 2 "mode_width_operand" "n")
1492 (ashift:DI (match_operand:DI 3 "reg_or_8bit_operand" "rI")
1496 [(set_attr "type" "shift")])
1498 (define_insn "extqh"
1499 [(set (match_operand:DI 0 "register_operand" "=r")
1501 (match_operand:DI 1 "reg_or_0_operand" "rJ")
1502 (minus:DI (const_int 56)
1505 (plus:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
1511 [(set_attr "type" "shift")])
1513 (define_insn "extlh"
1514 [(set (match_operand:DI 0 "register_operand" "=r")
1516 (and:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1517 (const_int 2147483647))
1518 (minus:DI (const_int 56)
1521 (plus:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
1527 [(set_attr "type" "shift")])
1529 (define_insn "extwh"
1530 [(set (match_operand:DI 0 "register_operand" "=r")
1532 (and:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1534 (minus:DI (const_int 56)
1537 (plus:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
1543 [(set_attr "type" "shift")])
1545 ;; This converts an extXl into an extXh with an appropriate adjustment
1546 ;; to the address calculation.
1549 ;; [(set (match_operand:DI 0 "register_operand" "")
1550 ;; (ashift:DI (zero_extract:DI (match_operand:DI 1 "register_operand" "")
1551 ;; (match_operand:DI 2 "mode_width_operand" "")
1552 ;; (ashift:DI (match_operand:DI 3 "" "")
1554 ;; (match_operand:DI 4 "const_int_operand" "")))
1555 ;; (clobber (match_operand:DI 5 "register_operand" ""))]
1556 ;; "INTVAL (operands[4]) == 64 - INTVAL (operands[2])"
1557 ;; [(set (match_dup 5) (match_dup 6))
1558 ;; (set (match_dup 0)
1559 ;; (ashift:DI (zero_extract:DI (match_dup 1) (match_dup 2)
1560 ;; (ashift:DI (plus:DI (match_dup 5)
1566 ;; operands[6] = plus_constant (operands[3],
1567 ;; INTVAL (operands[2]) / BITS_PER_UNIT);
1568 ;; operands[7] = GEN_INT (- INTVAL (operands[2]) / BITS_PER_UNIT);
1572 [(set (match_operand:DI 0 "register_operand" "=r")
1573 (ashift:DI (zero_extend:DI (match_operand:QI 1 "register_operand" "r"))
1574 (match_operand:DI 2 "mul8_operand" "I")))]
1577 [(set_attr "type" "shift")])
1580 [(set (match_operand:DI 0 "register_operand" "=r")
1581 (ashift:DI (zero_extend:DI (match_operand:HI 1 "register_operand" "r"))
1582 (match_operand:DI 2 "mul8_operand" "I")))]
1585 [(set_attr "type" "shift")])
1588 [(set (match_operand:DI 0 "register_operand" "=r")
1589 (ashift:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
1590 (match_operand:DI 2 "mul8_operand" "I")))]
1593 [(set_attr "type" "shift")])
1595 (define_insn "insbl"
1596 [(set (match_operand:DI 0 "register_operand" "=r")
1597 (ashift:DI (zero_extend:DI (match_operand:QI 1 "register_operand" "r"))
1598 (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
1602 [(set_attr "type" "shift")])
1604 (define_insn "inswl"
1605 [(set (match_operand:DI 0 "register_operand" "=r")
1606 (ashift:DI (zero_extend:DI (match_operand:HI 1 "register_operand" "r"))
1607 (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
1611 [(set_attr "type" "shift")])
1613 (define_insn "insll"
1614 [(set (match_operand:DI 0 "register_operand" "=r")
1615 (ashift:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
1616 (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
1620 [(set_attr "type" "shift")])
1622 (define_insn "insql"
1623 [(set (match_operand:DI 0 "register_operand" "=r")
1624 (ashift:DI (match_operand:DI 1 "register_operand" "r")
1625 (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
1629 [(set_attr "type" "shift")])
1631 ;; Combine has this sometimes habit of moving the and outside of the
1632 ;; shift, making life more interesting.
1635 [(set (match_operand:DI 0 "register_operand" "=r")
1636 (and:DI (ashift:DI (match_operand:DI 1 "register_operand" "r")
1637 (match_operand:DI 2 "mul8_operand" "I"))
1638 (match_operand:DI 3 "immediate_operand" "i")))]
1639 "HOST_BITS_PER_WIDE_INT == 64
1640 && GET_CODE (operands[3]) == CONST_INT
1641 && (((unsigned HOST_WIDE_INT) 0xff << INTVAL (operands[2])
1642 == INTVAL (operands[3]))
1643 || ((unsigned HOST_WIDE_INT) 0xffff << INTVAL (operands[2])
1644 == INTVAL (operands[3]))
1645 || ((unsigned HOST_WIDE_INT) 0xffffffff << INTVAL (operands[2])
1646 == INTVAL (operands[3])))"
1649 #if HOST_BITS_PER_WIDE_INT == 64
1650 if ((unsigned HOST_WIDE_INT) 0xff << INTVAL (operands[2])
1651 == INTVAL (operands[3]))
1652 return \"insbl %1,%s2,%0\";
1653 if ((unsigned HOST_WIDE_INT) 0xffff << INTVAL (operands[2])
1654 == INTVAL (operands[3]))
1655 return \"inswl %1,%s2,%0\";
1656 if ((unsigned HOST_WIDE_INT) 0xffffffff << INTVAL (operands[2])
1657 == INTVAL (operands[3]))
1658 return \"insll %1,%s2,%0\";
1662 [(set_attr "type" "shift")])
1664 ;; We do not include the insXh insns because they are complex to express
1665 ;; and it does not appear that we would ever want to generate them.
1667 ;; Since we need them for block moves, though, cop out and use unspec.
1669 (define_insn "insxh"
1670 [(set (match_operand:DI 0 "register_operand" "=r")
1671 (unspec [(match_operand:DI 1 "register_operand" "r")
1672 (match_operand:DI 2 "mode_width_operand" "n")
1673 (match_operand:DI 3 "reg_or_8bit_operand" "rI")] 2))]
1676 [(set_attr "type" "shift")])
1678 (define_insn "mskxl"
1679 [(set (match_operand:DI 0 "register_operand" "=r")
1680 (and:DI (not:DI (ashift:DI
1681 (match_operand:DI 2 "mode_mask_operand" "n")
1683 (match_operand:DI 3 "reg_or_8bit_operand" "rI")
1685 (match_operand:DI 1 "reg_or_0_operand" "rJ")))]
1688 [(set_attr "type" "shift")])
1690 ;; We do not include the mskXh insns because it does not appear we would
1691 ;; ever generate one.
1693 ;; Again, we do for block moves and we use unspec again.
1695 (define_insn "mskxh"
1696 [(set (match_operand:DI 0 "register_operand" "=r")
1697 (unspec [(match_operand:DI 1 "register_operand" "r")
1698 (match_operand:DI 2 "mode_width_operand" "n")
1699 (match_operand:DI 3 "reg_or_8bit_operand" "rI")] 3))]
1702 [(set_attr "type" "shift")])
1704 ;; Floating-point operations. All the double-precision insns can extend
1705 ;; from single, so indicate that. The exception are the ones that simply
1706 ;; play with the sign bits; it's not clear what to do there.
1708 (define_insn "abssf2"
1709 [(set (match_operand:SF 0 "register_operand" "=f")
1710 (abs:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")))]
1713 [(set_attr "type" "fcpys")])
1715 (define_insn "absdf2"
1716 [(set (match_operand:DF 0 "register_operand" "=f")
1717 (abs:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
1720 [(set_attr "type" "fcpys")])
1722 (define_insn "negsf2"
1723 [(set (match_operand:SF 0 "register_operand" "=f")
1724 (neg:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")))]
1727 [(set_attr "type" "fadd")])
1729 (define_insn "negdf2"
1730 [(set (match_operand:DF 0 "register_operand" "=f")
1731 (neg:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
1734 [(set_attr "type" "fadd")])
1737 [(set (match_operand:SF 0 "register_operand" "=&f")
1738 (plus:SF (match_operand:SF 1 "reg_or_fp0_operand" "%fG")
1739 (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
1740 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
1741 "add%,%)%& %R1,%R2,%0"
1742 [(set_attr "type" "fadd")
1743 (set_attr "trap" "yes")])
1745 (define_insn "addsf3"
1746 [(set (match_operand:SF 0 "register_operand" "=f")
1747 (plus:SF (match_operand:SF 1 "reg_or_fp0_operand" "%fG")
1748 (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
1750 "add%,%)%& %R1,%R2,%0"
1751 [(set_attr "type" "fadd")
1752 (set_attr "trap" "yes")])
1755 [(set (match_operand:DF 0 "register_operand" "=&f")
1756 (plus:DF (match_operand:DF 1 "reg_or_fp0_operand" "%fG")
1757 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
1758 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
1759 "add%-%)%& %R1,%R2,%0"
1760 [(set_attr "type" "fadd")
1761 (set_attr "trap" "yes")])
1763 (define_insn "adddf3"
1764 [(set (match_operand:DF 0 "register_operand" "=f")
1765 (plus:DF (match_operand:DF 1 "reg_or_fp0_operand" "%fG")
1766 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
1768 "add%-%)%& %R1,%R2,%0"
1769 [(set_attr "type" "fadd")
1770 (set_attr "trap" "yes")])
1773 [(set (match_operand:DF 0 "register_operand" "=f")
1774 (plus:DF (float_extend:DF
1775 (match_operand:SF 1 "reg_or_fp0_operand" "fG"))
1776 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
1777 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
1778 "add%-%)%& %R1,%R2,%0"
1779 [(set_attr "type" "fadd")
1780 (set_attr "trap" "yes")])
1783 [(set (match_operand:DF 0 "register_operand" "=f")
1784 (plus:DF (float_extend:DF
1785 (match_operand:SF 1 "reg_or_fp0_operand" "%fG"))
1787 (match_operand:SF 2 "reg_or_fp0_operand" "fG"))))]
1788 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
1789 "add%-%)%& %R1,%R2,%0"
1790 [(set_attr "type" "fadd")
1791 (set_attr "trap" "yes")])
1793 ;; Define conversion operators between DFmode and SImode, using the cvtql
1794 ;; instruction. To allow combine et al to do useful things, we keep the
1795 ;; operation as a unit until after reload, at which point we split the
1799 [(set (match_operand:SI 0 "register_operand" "")
1800 (fix:SI (match_operand:DF 1 "reg_or_fp0_operand" "")))
1801 (clobber (match_scratch:DI 2 ""))]
1802 "TARGET_FP && reload_completed"
1803 [(set (match_dup 2) (fix:DI (match_dup 1)))
1804 (set (match_dup 0) (unspec:SI [(match_dup 2)] 5))]
1807 ;; Due to issues with CLASS_CANNOT_CHANGE_SIZE, we cannot use a subreg here.
1809 [(set (match_operand:SI 0 "register_operand" "")
1810 (fix:SI (match_operand:DF 1 "reg_or_fp0_operand" "")))]
1811 "TARGET_FP && reload_completed"
1812 [(set (match_dup 2) (fix:DI (match_dup 1)))
1813 (set (match_dup 0) (unspec:SI [(match_dup 2)] 5))]
1814 "operands[2] = gen_rtx_REG (DImode, REGNO (operands[0]));")
1817 [(set (match_operand:SI 0 "register_operand" "=f")
1818 (unspec:SI [(match_operand:DI 1 "reg_or_fp0_operand" "fG")] 5))]
1821 [(set_attr "type" "fadd")
1822 (set_attr "trap" "yes")])
1824 (define_insn "fix_truncdfsi2_tp"
1825 [(set (match_operand:SI 0 "register_operand" "=&f")
1826 (fix:SI (match_operand:DF 1 "reg_or_fp0_operand" "fG")))
1827 (clobber (match_scratch:DI 2 "=&f"))]
1828 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
1830 [(set_attr "type" "fadd")
1831 (set_attr "trap" "yes")])
1834 [(set (match_operand:SI 0 "register_operand" "=f")
1835 (fix:SI (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
1836 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
1838 [(set_attr "type" "fadd")
1839 (set_attr "trap" "yes")])
1841 (define_expand "fix_truncdfsi2"
1842 [(set (match_operand:SI 0 "register_operand" "=f")
1843 (fix:SI (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
1845 "{ if (alpha_tp == ALPHA_TP_INSN)
1846 { emit_insn(gen_fix_truncdfsi2_tp(operands[0], operands[1])); DONE; }
1850 [(set (match_operand:DI 0 "register_operand" "=&f")
1851 (fix:DI (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
1852 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
1854 [(set_attr "type" "fadd")
1855 (set_attr "trap" "yes")])
1857 (define_insn "fix_truncdfdi2"
1858 [(set (match_operand:DI 0 "register_operand" "=f")
1859 (fix:DI (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
1862 [(set_attr "type" "fadd")
1863 (set_attr "trap" "yes")])
1865 ;; Likewise between SFmode and SImode.
1868 [(set (match_operand:SI 0 "register_operand" "")
1869 (fix:SI (float_extend:DF
1870 (match_operand:SF 1 "reg_or_fp0_operand" ""))))
1871 (clobber (match_scratch:DI 2 ""))]
1872 "TARGET_FP && reload_completed"
1873 [(set (match_dup 2) (fix:DI (float_extend:DF (match_dup 1))))
1874 (set (match_dup 0) (unspec:SI [(match_dup 2)] 5))]
1877 ;; Due to issues with CLASS_CANNOT_CHANGE_SIZE, we cannot use a subreg here.
1879 [(set (match_operand:SI 0 "register_operand" "")
1880 (fix:SI (float_extend:DF
1881 (match_operand:SF 1 "reg_or_fp0_operand" ""))))]
1882 "TARGET_FP && reload_completed"
1883 [(set (match_dup 2) (fix:DI (float_extend:DF (match_dup 1))))
1884 (set (match_dup 0) (unspec:SI [(match_dup 2)] 5))]
1885 "operands[2] = gen_rtx_REG (DImode, REGNO (operands[0]));")
1887 (define_insn "fix_truncsfsi2_tp"
1888 [(set (match_operand:SI 0 "register_operand" "=&f")
1889 (fix:SI (float_extend:DF
1890 (match_operand:SF 1 "reg_or_fp0_operand" "fG"))))
1891 (clobber (match_scratch:DI 2 "=&f"))]
1892 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
1894 [(set_attr "type" "fadd")
1895 (set_attr "trap" "yes")])
1898 [(set (match_operand:SI 0 "register_operand" "=f")
1899 (fix:SI (float_extend:DF
1900 (match_operand:SF 1 "reg_or_fp0_operand" "fG"))))]
1901 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
1903 [(set_attr "type" "fadd")
1904 (set_attr "trap" "yes")])
1906 (define_expand "fix_truncsfsi2"
1907 [(set (match_operand:SI 0 "register_operand" "=f")
1908 (fix:SI (float_extend:DF
1909 (match_operand:SF 1 "reg_or_fp0_operand" "fG"))))]
1911 "{ if (alpha_tp == ALPHA_TP_INSN)
1912 { emit_insn(gen_fix_truncsfsi2_tp(operands[0], operands[1])); DONE; }
1916 [(set (match_operand:DI 0 "register_operand" "=&f")
1917 (fix:DI (float_extend:DF
1918 (match_operand:SF 1 "reg_or_fp0_operand" "fG"))))]
1919 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
1921 [(set_attr "type" "fadd")
1922 (set_attr "trap" "yes")])
1924 (define_insn "fix_truncsfdi2"
1925 [(set (match_operand:DI 0 "register_operand" "=f")
1926 (fix:DI (float_extend:DF
1927 (match_operand:SF 1 "reg_or_fp0_operand" "fG"))))]
1930 [(set_attr "type" "fadd")
1931 (set_attr "trap" "yes")])
1934 [(set (match_operand:SF 0 "register_operand" "=&f")
1935 (float:SF (match_operand:DI 1 "register_operand" "f")))]
1936 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
1938 [(set_attr "type" "fadd")
1939 (set_attr "trap" "yes")])
1941 (define_insn "floatdisf2"
1942 [(set (match_operand:SF 0 "register_operand" "=f")
1943 (float:SF (match_operand:DI 1 "register_operand" "f")))]
1946 [(set_attr "type" "fadd")
1947 (set_attr "trap" "yes")])
1950 [(set (match_operand:DF 0 "register_operand" "=&f")
1951 (float:DF (match_operand:DI 1 "register_operand" "f")))]
1952 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
1954 [(set_attr "type" "fadd")
1955 (set_attr "trap" "yes")])
1957 (define_insn "floatdidf2"
1958 [(set (match_operand:DF 0 "register_operand" "=f")
1959 (float:DF (match_operand:DI 1 "register_operand" "f")))]
1962 [(set_attr "type" "fadd")
1963 (set_attr "trap" "yes")])
1965 (define_expand "extendsfdf2"
1966 [(use (match_operand:DF 0 "register_operand" ""))
1967 (use (match_operand:SF 1 "nonimmediate_operand" ""))]
1971 if (alpha_tp == ALPHA_TP_INSN)
1972 emit_insn (gen_extendsfdf2_tp (operands[0],
1973 force_reg (SFmode, operands[1])));
1975 emit_insn (gen_extendsfdf2_no_tp (operands[0], operands[1]));
1980 (define_insn "extendsfdf2_tp"
1981 [(set (match_operand:DF 0 "register_operand" "=&f")
1982 (float_extend:DF (match_operand:SF 1 "register_operand" "f")))]
1983 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
1985 [(set_attr "type" "fadd")
1986 (set_attr "trap" "yes")])
1988 (define_insn "extendsfdf2_no_tp"
1989 [(set (match_operand:DF 0 "register_operand" "=f,f,m")
1990 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "f,m,f")))]
1991 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
1996 [(set_attr "type" "fcpys,fld,fst")
1997 (set_attr "trap" "yes")])
2000 [(set (match_operand:SF 0 "register_operand" "=&f")
2001 (float_truncate:SF (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
2002 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
2003 "cvt%-%,%)%& %R1,%0"
2004 [(set_attr "type" "fadd")
2005 (set_attr "trap" "yes")])
2007 (define_insn "truncdfsf2"
2008 [(set (match_operand:SF 0 "register_operand" "=f")
2009 (float_truncate:SF (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
2011 "cvt%-%,%)%& %R1,%0"
2012 [(set_attr "type" "fadd")
2013 (set_attr "trap" "yes")])
2016 [(set (match_operand:SF 0 "register_operand" "=&f")
2017 (div:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")
2018 (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2019 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
2020 "div%,%)%& %R1,%R2,%0"
2021 [(set_attr "type" "fdiv")
2022 (set_attr "opsize" "si")
2023 (set_attr "trap" "yes")])
2025 (define_insn "divsf3"
2026 [(set (match_operand:SF 0 "register_operand" "=f")
2027 (div:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")
2028 (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2030 "div%,%)%& %R1,%R2,%0"
2031 [(set_attr "type" "fdiv")
2032 (set_attr "opsize" "si")
2033 (set_attr "trap" "yes")])
2036 [(set (match_operand:DF 0 "register_operand" "=&f")
2037 (div:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")
2038 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2039 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
2040 "div%-%)%& %R1,%R2,%0"
2041 [(set_attr "type" "fdiv")
2042 (set_attr "trap" "yes")])
2044 (define_insn "divdf3"
2045 [(set (match_operand:DF 0 "register_operand" "=f")
2046 (div:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")
2047 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2049 "div%-%)%& %R1,%R2,%0"
2050 [(set_attr "type" "fdiv")
2051 (set_attr "trap" "yes")])
2054 [(set (match_operand:DF 0 "register_operand" "=f")
2055 (div:DF (float_extend:DF (match_operand:SF 1 "reg_or_fp0_operand" "fG"))
2056 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2057 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2058 "div%-%)%& %R1,%R2,%0"
2059 [(set_attr "type" "fdiv")
2060 (set_attr "trap" "yes")])
2063 [(set (match_operand:DF 0 "register_operand" "=f")
2064 (div:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")
2066 (match_operand:SF 2 "reg_or_fp0_operand" "fG"))))]
2067 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2068 "div%-%)%& %R1,%R2,%0"
2069 [(set_attr "type" "fdiv")
2070 (set_attr "trap" "yes")])
2073 [(set (match_operand:DF 0 "register_operand" "=f")
2074 (div:DF (float_extend:DF (match_operand:SF 1 "reg_or_fp0_operand" "fG"))
2075 (float_extend:DF (match_operand:SF 2 "reg_or_fp0_operand" "fG"))))]
2076 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2077 "div%-%)%& %R1,%R2,%0"
2078 [(set_attr "type" "fdiv")
2079 (set_attr "trap" "yes")])
2082 [(set (match_operand:SF 0 "register_operand" "=&f")
2083 (mult:SF (match_operand:SF 1 "reg_or_fp0_operand" "%fG")
2084 (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2085 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
2086 "mul%,%)%& %R1,%R2,%0"
2087 [(set_attr "type" "fmul")
2088 (set_attr "trap" "yes")])
2090 (define_insn "mulsf3"
2091 [(set (match_operand:SF 0 "register_operand" "=f")
2092 (mult:SF (match_operand:SF 1 "reg_or_fp0_operand" "%fG")
2093 (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2095 "mul%,%)%& %R1,%R2,%0"
2096 [(set_attr "type" "fmul")
2097 (set_attr "trap" "yes")])
2100 [(set (match_operand:DF 0 "register_operand" "=&f")
2101 (mult:DF (match_operand:DF 1 "reg_or_fp0_operand" "%fG")
2102 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2103 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
2104 "mul%-%)%& %R1,%R2,%0"
2105 [(set_attr "type" "fmul")
2106 (set_attr "trap" "yes")])
2108 (define_insn "muldf3"
2109 [(set (match_operand:DF 0 "register_operand" "=f")
2110 (mult:DF (match_operand:DF 1 "reg_or_fp0_operand" "%fG")
2111 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2113 "mul%-%)%& %R1,%R2,%0"
2114 [(set_attr "type" "fmul")
2115 (set_attr "trap" "yes")])
2118 [(set (match_operand:DF 0 "register_operand" "=f")
2119 (mult:DF (float_extend:DF
2120 (match_operand:SF 1 "reg_or_fp0_operand" "fG"))
2121 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2122 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2123 "mul%-%)%& %R1,%R2,%0"
2124 [(set_attr "type" "fmul")
2125 (set_attr "trap" "yes")])
2128 [(set (match_operand:DF 0 "register_operand" "=f")
2129 (mult:DF (float_extend:DF
2130 (match_operand:SF 1 "reg_or_fp0_operand" "%fG"))
2132 (match_operand:SF 2 "reg_or_fp0_operand" "fG"))))]
2133 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2134 "mul%-%)%& %R1,%R2,%0"
2135 [(set_attr "type" "fmul")
2136 (set_attr "trap" "yes")])
2139 [(set (match_operand:SF 0 "register_operand" "=&f")
2140 (minus:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")
2141 (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2142 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
2143 "sub%,%)%& %R1,%R2,%0"
2144 [(set_attr "type" "fadd")
2145 (set_attr "trap" "yes")])
2147 (define_insn "subsf3"
2148 [(set (match_operand:SF 0 "register_operand" "=f")
2149 (minus:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")
2150 (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2152 "sub%,%)%& %R1,%R2,%0"
2153 [(set_attr "type" "fadd")
2154 (set_attr "trap" "yes")])
2157 [(set (match_operand:DF 0 "register_operand" "=&f")
2158 (minus:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")
2159 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2160 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
2161 "sub%-%)%& %R1,%R2,%0"
2162 [(set_attr "type" "fadd")
2163 (set_attr "trap" "yes")])
2165 (define_insn "subdf3"
2166 [(set (match_operand:DF 0 "register_operand" "=f")
2167 (minus:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")
2168 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2170 "sub%-%)%& %R1,%R2,%0"
2171 [(set_attr "type" "fadd")
2172 (set_attr "trap" "yes")])
2175 [(set (match_operand:DF 0 "register_operand" "=f")
2176 (minus:DF (float_extend:DF
2177 (match_operand:SF 1 "reg_or_fp0_operand" "fG"))
2178 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2179 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2180 "sub%-%)%& %R1,%R2,%0"
2181 [(set_attr "type" "fadd")
2182 (set_attr "trap" "yes")])
2185 [(set (match_operand:DF 0 "register_operand" "=f")
2186 (minus:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")
2188 (match_operand:SF 2 "reg_or_fp0_operand" "fG"))))]
2189 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2190 "sub%-%)%& %R1,%R2,%0"
2191 [(set_attr "type" "fadd")
2192 (set_attr "trap" "yes")])
2195 [(set (match_operand:DF 0 "register_operand" "=f")
2196 (minus:DF (float_extend:DF
2197 (match_operand:SF 1 "reg_or_fp0_operand" "fG"))
2199 (match_operand:SF 2 "reg_or_fp0_operand" "fG"))))]
2200 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2201 "sub%-%)%& %R1,%R2,%0"
2202 [(set_attr "type" "fadd")
2203 (set_attr "trap" "yes")])
2206 [(set (match_operand:SF 0 "register_operand" "=&f")
2207 (sqrt:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")))]
2208 "TARGET_FP && TARGET_CIX && alpha_tp == ALPHA_TP_INSN"
2210 [(set_attr "type" "fsqrt")
2211 (set_attr "opsize" "si")
2212 (set_attr "trap" "yes")])
2214 (define_insn "sqrtsf2"
2215 [(set (match_operand:SF 0 "register_operand" "=f")
2216 (sqrt:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")))]
2217 "TARGET_FP && TARGET_CIX"
2219 [(set_attr "type" "fsqrt")
2220 (set_attr "opsize" "si")
2221 (set_attr "trap" "yes")])
2224 [(set (match_operand:DF 0 "register_operand" "=&f")
2225 (sqrt:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
2226 "TARGET_FP && TARGET_CIX && alpha_tp == ALPHA_TP_INSN"
2228 [(set_attr "type" "fsqrt")
2229 (set_attr "trap" "yes")])
2231 (define_insn "sqrtdf2"
2232 [(set (match_operand:DF 0 "register_operand" "=f")
2233 (sqrt:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
2234 "TARGET_FP && TARGET_CIX"
2236 [(set_attr "type" "fsqrt")
2237 (set_attr "trap" "yes")])
2239 ;; Next are all the integer comparisons, and conditional moves and branches
2240 ;; and some of the related define_expand's and define_split's.
2243 [(set (match_operand:DI 0 "register_operand" "=r")
2244 (match_operator:DI 1 "alpha_comparison_operator"
2245 [(match_operand:DI 2 "reg_or_0_operand" "rJ")
2246 (match_operand:DI 3 "reg_or_8bit_operand" "rI")]))]
2249 [(set_attr "type" "icmp")])
2252 [(set (match_operand:DI 0 "register_operand" "=r")
2253 (match_operator:DI 1 "alpha_swapped_comparison_operator"
2254 [(match_operand:DI 2 "reg_or_8bit_operand" "rI")
2255 (match_operand:DI 3 "reg_or_0_operand" "rJ")]))]
2258 [(set_attr "type" "icmp")])
2260 ;; This pattern exists so conditional moves of SImode values are handled.
2261 ;; Comparisons are still done in DImode though.
2264 [(set (match_operand:SI 0 "register_operand" "=r,r,r,r")
2266 (match_operator 2 "signed_comparison_operator"
2267 [(match_operand:DI 3 "reg_or_0_operand" "rJ,rJ,J,J")
2268 (match_operand:DI 4 "reg_or_0_operand" "J,J,rJ,rJ")])
2269 (match_operand:SI 1 "reg_or_8bit_operand" "rI,0,rI,0")
2270 (match_operand:SI 5 "reg_or_8bit_operand" "0,rI,0,rI")))]
2271 "operands[3] == const0_rtx || operands[4] == const0_rtx"
2277 [(set_attr "type" "icmov")])
2280 [(set (match_operand:DI 0 "register_operand" "=r,r,r,r")
2282 (match_operator 2 "signed_comparison_operator"
2283 [(match_operand:DI 3 "reg_or_0_operand" "rJ,rJ,J,J")
2284 (match_operand:DI 4 "reg_or_0_operand" "J,J,rJ,rJ")])
2285 (match_operand:DI 1 "reg_or_8bit_operand" "rI,0,rI,0")
2286 (match_operand:DI 5 "reg_or_8bit_operand" "0,rI,0,rI")))]
2287 "operands[3] == const0_rtx || operands[4] == const0_rtx"
2293 [(set_attr "type" "icmov")])
2296 [(set (match_operand:DI 0 "register_operand" "=r,r")
2298 (eq (zero_extract:DI (match_operand:DI 2 "reg_or_0_operand" "rJ,rJ")
2302 (match_operand:DI 1 "reg_or_8bit_operand" "rI,0")
2303 (match_operand:DI 3 "reg_or_8bit_operand" "0,rI")))]
2308 [(set_attr "type" "icmov")])
2311 [(set (match_operand:DI 0 "register_operand" "=r,r")
2313 (ne (zero_extract:DI (match_operand:DI 2 "reg_or_0_operand" "rJ,rJ")
2317 (match_operand:DI 1 "reg_or_8bit_operand" "rI,0")
2318 (match_operand:DI 3 "reg_or_8bit_operand" "0,rI")))]
2323 [(set_attr "type" "icmov")])
2325 ;; This form is added since combine thinks that an IF_THEN_ELSE with both
2326 ;; arms constant is a single insn, so it won't try to form it if combine
2327 ;; knows they are really two insns. This occurs in divides by powers
2331 [(set (match_operand:DI 0 "register_operand" "=r")
2333 (match_operator 2 "signed_comparison_operator"
2334 [(match_operand:DI 3 "reg_or_0_operand" "rJ")
2336 (plus:DI (match_dup 0)
2337 (match_operand:DI 1 "reg_or_8bit_operand" "rI"))
2339 (clobber (match_scratch:DI 4 "=&r"))]
2341 "addq %0,%1,%4\;cmov%C2 %r3,%4,%0"
2342 [(set_attr "type" "icmov")
2343 (set_attr "length" "8")])
2346 [(set (match_operand:DI 0 "register_operand" "")
2348 (match_operator 2 "signed_comparison_operator"
2349 [(match_operand:DI 3 "reg_or_0_operand" "")
2351 (plus:DI (match_dup 0)
2352 (match_operand:DI 1 "reg_or_8bit_operand" ""))
2354 (clobber (match_operand:DI 4 "register_operand" ""))]
2356 [(set (match_dup 4) (plus:DI (match_dup 0) (match_dup 1)))
2357 (set (match_dup 0) (if_then_else:DI (match_op_dup 2
2360 (match_dup 4) (match_dup 0)))]
2365 [(set (match_operand:DI 0 "register_operand" "")
2367 (match_operator 1 "comparison_operator"
2368 [(zero_extract:DI (match_operand:DI 2 "register_operand" "")
2370 (match_operand:DI 3 "const_int_operand" ""))
2372 (match_operand:DI 4 "reg_or_8bit_operand" "")
2373 (match_operand:DI 5 "reg_or_8bit_operand" "")))
2374 (clobber (match_operand:DI 6 "register_operand" ""))])]
2375 "INTVAL (operands[3]) != 0"
2377 (lshiftrt:DI (match_dup 2) (match_dup 3)))
2379 (if_then_else:DI (match_op_dup 1
2380 [(zero_extract:DI (match_dup 6)
2388 ;; For ABS, we have two choices, depending on whether the input and output
2389 ;; registers are the same or not.
2390 (define_expand "absdi2"
2391 [(set (match_operand:DI 0 "register_operand" "")
2392 (abs:DI (match_operand:DI 1 "register_operand" "")))]
2395 { if (rtx_equal_p (operands[0], operands[1]))
2396 emit_insn (gen_absdi2_same (operands[0], gen_reg_rtx (DImode)));
2398 emit_insn (gen_absdi2_diff (operands[0], operands[1]));
2403 (define_expand "absdi2_same"
2404 [(set (match_operand:DI 1 "register_operand" "")
2405 (neg:DI (match_operand:DI 0 "register_operand" "")))
2407 (if_then_else:DI (ge (match_dup 0) (const_int 0))
2413 (define_expand "absdi2_diff"
2414 [(set (match_operand:DI 0 "register_operand" "")
2415 (neg:DI (match_operand:DI 1 "register_operand" "")))
2417 (if_then_else:DI (lt (match_dup 1) (const_int 0))
2424 [(set (match_operand:DI 0 "register_operand" "")
2425 (abs:DI (match_dup 0)))
2426 (clobber (match_operand:DI 2 "register_operand" ""))]
2428 [(set (match_dup 1) (neg:DI (match_dup 0)))
2429 (set (match_dup 0) (if_then_else:DI (ge (match_dup 0) (const_int 0))
2430 (match_dup 0) (match_dup 1)))]
2434 [(set (match_operand:DI 0 "register_operand" "")
2435 (abs:DI (match_operand:DI 1 "register_operand" "")))]
2436 "! rtx_equal_p (operands[0], operands[1])"
2437 [(set (match_dup 0) (neg:DI (match_dup 1)))
2438 (set (match_dup 0) (if_then_else:DI (lt (match_dup 1) (const_int 0))
2439 (match_dup 0) (match_dup 1)))]
2443 [(set (match_operand:DI 0 "register_operand" "")
2444 (neg:DI (abs:DI (match_dup 0))))
2445 (clobber (match_operand:DI 2 "register_operand" ""))]
2447 [(set (match_dup 1) (neg:DI (match_dup 0)))
2448 (set (match_dup 0) (if_then_else:DI (le (match_dup 0) (const_int 0))
2449 (match_dup 0) (match_dup 1)))]
2453 [(set (match_operand:DI 0 "register_operand" "")
2454 (neg:DI (abs:DI (match_operand:DI 1 "register_operand" ""))))]
2455 "! rtx_equal_p (operands[0], operands[1])"
2456 [(set (match_dup 0) (neg:DI (match_dup 1)))
2457 (set (match_dup 0) (if_then_else:DI (gt (match_dup 1) (const_int 0))
2458 (match_dup 0) (match_dup 1)))]
2461 (define_insn "sminqi3"
2462 [(set (match_operand:QI 0 "register_operand" "=r")
2463 (smin:SI (match_operand:QI 1 "reg_or_0_operand" "%rJ")
2464 (match_operand:QI 2 "reg_or_8bit_operand" "rI")))]
2467 [(set_attr "type" "mvi")])
2469 (define_insn "uminqi3"
2470 [(set (match_operand:QI 0 "register_operand" "=r")
2471 (umin:SI (match_operand:QI 1 "reg_or_0_operand" "%rJ")
2472 (match_operand:QI 2 "reg_or_8bit_operand" "rI")))]
2475 [(set_attr "type" "mvi")])
2477 (define_insn "smaxqi3"
2478 [(set (match_operand:QI 0 "register_operand" "=r")
2479 (smax:SI (match_operand:QI 1 "reg_or_0_operand" "%rJ")
2480 (match_operand:QI 2 "reg_or_8bit_operand" "rI")))]
2483 [(set_attr "type" "mvi")])
2485 (define_insn "umaxqi3"
2486 [(set (match_operand:QI 0 "register_operand" "=r")
2487 (umax:SI (match_operand:QI 1 "reg_or_0_operand" "%rJ")
2488 (match_operand:QI 2 "reg_or_8bit_operand" "rI")))]
2491 [(set_attr "type" "mvi")])
2493 (define_insn "sminhi3"
2494 [(set (match_operand:HI 0 "register_operand" "=r")
2495 (smin:SI (match_operand:HI 1 "reg_or_0_operand" "%rJ")
2496 (match_operand:HI 2 "reg_or_8bit_operand" "rI")))]
2499 [(set_attr "type" "mvi")])
2501 (define_insn "uminhi3"
2502 [(set (match_operand:HI 0 "register_operand" "=r")
2503 (umin:SI (match_operand:HI 1 "reg_or_0_operand" "%rJ")
2504 (match_operand:HI 2 "reg_or_8bit_operand" "rI")))]
2507 [(set_attr "type" "mvi")])
2509 (define_insn "smaxhi3"
2510 [(set (match_operand:HI 0 "register_operand" "=r")
2511 (smax:SI (match_operand:HI 1 "reg_or_0_operand" "%rJ")
2512 (match_operand:HI 2 "reg_or_8bit_operand" "rI")))]
2515 [(set_attr "type" "mvi")])
2517 (define_insn "umaxhi3"
2518 [(set (match_operand:HI 0 "register_operand" "=r")
2519 (umax:SI (match_operand:HI 1 "reg_or_0_operand" "%rJ")
2520 (match_operand:HI 2 "reg_or_8bit_operand" "rI")))]
2523 [(set_attr "type" "shift")])
2525 (define_expand "smaxdi3"
2527 (le:DI (match_operand:DI 1 "reg_or_0_operand" "")
2528 (match_operand:DI 2 "reg_or_8bit_operand" "")))
2529 (set (match_operand:DI 0 "register_operand" "")
2530 (if_then_else:DI (eq (match_dup 3) (const_int 0))
2531 (match_dup 1) (match_dup 2)))]
2534 { operands[3] = gen_reg_rtx (DImode);
2538 [(set (match_operand:DI 0 "register_operand" "")
2539 (smax:DI (match_operand:DI 1 "reg_or_0_operand" "")
2540 (match_operand:DI 2 "reg_or_8bit_operand" "")))
2541 (clobber (match_operand:DI 3 "register_operand" ""))]
2542 "operands[2] != const0_rtx"
2543 [(set (match_dup 3) (le:DI (match_dup 1) (match_dup 2)))
2544 (set (match_dup 0) (if_then_else:DI (eq (match_dup 3) (const_int 0))
2545 (match_dup 1) (match_dup 2)))]
2549 [(set (match_operand:DI 0 "register_operand" "=r")
2550 (smax:DI (match_operand:DI 1 "register_operand" "0")
2554 [(set_attr "type" "icmov")])
2556 (define_expand "smindi3"
2558 (lt:DI (match_operand:DI 1 "reg_or_0_operand" "")
2559 (match_operand:DI 2 "reg_or_8bit_operand" "")))
2560 (set (match_operand:DI 0 "register_operand" "")
2561 (if_then_else:DI (ne (match_dup 3) (const_int 0))
2562 (match_dup 1) (match_dup 2)))]
2565 { operands[3] = gen_reg_rtx (DImode);
2569 [(set (match_operand:DI 0 "register_operand" "")
2570 (smin:DI (match_operand:DI 1 "reg_or_0_operand" "")
2571 (match_operand:DI 2 "reg_or_8bit_operand" "")))
2572 (clobber (match_operand:DI 3 "register_operand" ""))]
2573 "operands[2] != const0_rtx"
2574 [(set (match_dup 3) (lt:DI (match_dup 1) (match_dup 2)))
2575 (set (match_dup 0) (if_then_else:DI (ne (match_dup 3) (const_int 0))
2576 (match_dup 1) (match_dup 2)))]
2580 [(set (match_operand:DI 0 "register_operand" "=r")
2581 (smin:DI (match_operand:DI 1 "register_operand" "0")
2585 [(set_attr "type" "icmov")])
2587 (define_expand "umaxdi3"
2589 (leu:DI (match_operand:DI 1 "reg_or_0_operand" "")
2590 (match_operand:DI 2 "reg_or_8bit_operand" "")))
2591 (set (match_operand:DI 0 "register_operand" "")
2592 (if_then_else:DI (eq (match_dup 3) (const_int 0))
2593 (match_dup 1) (match_dup 2)))]
2596 { operands[3] = gen_reg_rtx (DImode);
2600 [(set (match_operand:DI 0 "register_operand" "")
2601 (umax:DI (match_operand:DI 1 "reg_or_0_operand" "")
2602 (match_operand:DI 2 "reg_or_8bit_operand" "")))
2603 (clobber (match_operand:DI 3 "register_operand" ""))]
2604 "operands[2] != const0_rtx"
2605 [(set (match_dup 3) (leu:DI (match_dup 1) (match_dup 2)))
2606 (set (match_dup 0) (if_then_else:DI (eq (match_dup 3) (const_int 0))
2607 (match_dup 1) (match_dup 2)))]
2610 (define_expand "umindi3"
2612 (ltu:DI (match_operand:DI 1 "reg_or_0_operand" "")
2613 (match_operand:DI 2 "reg_or_8bit_operand" "")))
2614 (set (match_operand:DI 0 "register_operand" "")
2615 (if_then_else:DI (ne (match_dup 3) (const_int 0))
2616 (match_dup 1) (match_dup 2)))]
2619 { operands[3] = gen_reg_rtx (DImode);
2623 [(set (match_operand:DI 0 "register_operand" "")
2624 (umin:DI (match_operand:DI 1 "reg_or_0_operand" "")
2625 (match_operand:DI 2 "reg_or_8bit_operand" "")))
2626 (clobber (match_operand:DI 3 "register_operand" ""))]
2627 "operands[2] != const0_rtx"
2628 [(set (match_dup 3) (ltu:DI (match_dup 1) (match_dup 2)))
2629 (set (match_dup 0) (if_then_else:DI (ne (match_dup 3) (const_int 0))
2630 (match_dup 1) (match_dup 2)))]
2636 (match_operator 1 "signed_comparison_operator"
2637 [(match_operand:DI 2 "reg_or_0_operand" "rJ")
2639 (label_ref (match_operand 0 "" ""))
2643 [(set_attr "type" "ibr")])
2648 (match_operator 1 "signed_comparison_operator"
2650 (match_operand:DI 2 "register_operand" "r")])
2651 (label_ref (match_operand 0 "" ""))
2655 [(set_attr "type" "ibr")])
2660 (ne (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
2664 (label_ref (match_operand 0 "" ""))
2668 [(set_attr "type" "ibr")])
2673 (eq (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
2677 (label_ref (match_operand 0 "" ""))
2681 [(set_attr "type" "ibr")])
2687 (match_operator 1 "comparison_operator"
2688 [(zero_extract:DI (match_operand:DI 2 "register_operand" "")
2690 (match_operand:DI 3 "const_int_operand" ""))
2692 (label_ref (match_operand 0 "" ""))
2694 (clobber (match_operand:DI 4 "register_operand" ""))])]
2695 "INTVAL (operands[3]) != 0"
2697 (lshiftrt:DI (match_dup 2) (match_dup 3)))
2699 (if_then_else (match_op_dup 1
2700 [(zero_extract:DI (match_dup 4)
2704 (label_ref (match_dup 0))
2708 ;; The following are the corresponding floating-point insns. Recall
2709 ;; we need to have variants that expand the arguments from SF mode
2713 [(set (match_operand:DF 0 "register_operand" "=&f")
2714 (match_operator:DF 1 "alpha_comparison_operator"
2715 [(match_operand:DF 2 "reg_or_fp0_operand" "fG")
2716 (match_operand:DF 3 "reg_or_fp0_operand" "fG")]))]
2717 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
2718 "cmp%-%C1%' %R2,%R3,%0"
2719 [(set_attr "type" "fadd")
2720 (set_attr "trap" "yes")])
2723 [(set (match_operand:DF 0 "register_operand" "=f")
2724 (match_operator:DF 1 "alpha_comparison_operator"
2725 [(match_operand:DF 2 "reg_or_fp0_operand" "fG")
2726 (match_operand:DF 3 "reg_or_fp0_operand" "fG")]))]
2727 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2728 "cmp%-%C1%' %R2,%R3,%0"
2729 [(set_attr "type" "fadd")
2730 (set_attr "trap" "yes")])
2733 [(set (match_operand:DF 0 "register_operand" "=f")
2734 (match_operator:DF 1 "alpha_comparison_operator"
2736 (match_operand:SF 2 "reg_or_fp0_operand" "fG"))
2737 (match_operand:DF 3 "reg_or_fp0_operand" "fG")]))]
2738 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2739 "cmp%-%C1%' %R2,%R3,%0"
2740 [(set_attr "type" "fadd")
2741 (set_attr "trap" "yes")])
2744 [(set (match_operand:DF 0 "register_operand" "=f")
2745 (match_operator:DF 1 "alpha_comparison_operator"
2746 [(match_operand:DF 2 "reg_or_fp0_operand" "fG")
2748 (match_operand:SF 3 "reg_or_fp0_operand" "fG"))]))]
2749 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2750 "cmp%-%C1%' %R2,%R3,%0"
2751 [(set_attr "type" "fadd")
2752 (set_attr "trap" "yes")])
2755 [(set (match_operand:DF 0 "register_operand" "=f")
2756 (match_operator:DF 1 "alpha_comparison_operator"
2758 (match_operand:SF 2 "reg_or_fp0_operand" "fG"))
2760 (match_operand:SF 3 "reg_or_fp0_operand" "fG"))]))]
2761 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2762 "cmp%-%C1%' %R2,%R3,%0"
2763 [(set_attr "type" "fadd")
2764 (set_attr "trap" "yes")])
2767 [(set (match_operand:DF 0 "register_operand" "=&f,f")
2769 (match_operator 3 "signed_comparison_operator"
2770 [(match_operand:DF 4 "reg_or_fp0_operand" "fG,fG")
2771 (match_operand:DF 2 "fp0_operand" "G,G")])
2772 (match_operand:DF 1 "reg_or_fp0_operand" "fG,0")
2773 (match_operand:DF 5 "reg_or_fp0_operand" "0,fG")))]
2774 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
2777 fcmov%D3 %R4,%R5,%0"
2778 [(set_attr "type" "fcmov")])
2781 [(set (match_operand:DF 0 "register_operand" "=f,f")
2783 (match_operator 3 "signed_comparison_operator"
2784 [(match_operand:DF 4 "reg_or_fp0_operand" "fG,fG")
2785 (match_operand:DF 2 "fp0_operand" "G,G")])
2786 (match_operand:DF 1 "reg_or_fp0_operand" "fG,0")
2787 (match_operand:DF 5 "reg_or_fp0_operand" "0,fG")))]
2788 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2791 fcmov%D3 %R4,%R5,%0"
2792 [(set_attr "type" "fcmov")])
2795 [(set (match_operand:SF 0 "register_operand" "=&f,f")
2797 (match_operator 3 "signed_comparison_operator"
2798 [(match_operand:DF 4 "reg_or_fp0_operand" "fG,fG")
2799 (match_operand:DF 2 "fp0_operand" "G,G")])
2800 (match_operand:SF 1 "reg_or_fp0_operand" "fG,0")
2801 (match_operand:SF 5 "reg_or_fp0_operand" "0,fG")))]
2802 "TARGET_FP && alpha_tp == ALPHA_TP_INSN"
2805 fcmov%D3 %R4,%R5,%0"
2806 [(set_attr "type" "fcmov")])
2809 [(set (match_operand:SF 0 "register_operand" "=f,f")
2811 (match_operator 3 "signed_comparison_operator"
2812 [(match_operand:DF 4 "reg_or_fp0_operand" "fG,fG")
2813 (match_operand:DF 2 "fp0_operand" "G,G")])
2814 (match_operand:SF 1 "reg_or_fp0_operand" "fG,0")
2815 (match_operand:SF 5 "reg_or_fp0_operand" "0,fG")))]
2816 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2819 fcmov%D3 %R4,%R5,%0"
2820 [(set_attr "type" "fcmov")])
2823 [(set (match_operand:DF 0 "register_operand" "=f,f")
2825 (match_operator 3 "signed_comparison_operator"
2826 [(match_operand:DF 4 "reg_or_fp0_operand" "fG,fG")
2827 (match_operand:DF 2 "fp0_operand" "G,G")])
2828 (float_extend:DF (match_operand:SF 1 "reg_or_fp0_operand" "fG,0"))
2829 (match_operand:DF 5 "reg_or_fp0_operand" "0,fG")))]
2830 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2833 fcmov%D3 %R4,%R5,%0"
2834 [(set_attr "type" "fcmov")])
2837 [(set (match_operand:DF 0 "register_operand" "=f,f")
2839 (match_operator 3 "signed_comparison_operator"
2841 (match_operand:SF 4 "reg_or_fp0_operand" "fG,fG"))
2842 (match_operand:DF 2 "fp0_operand" "G,G")])
2843 (match_operand:DF 1 "reg_or_fp0_operand" "fG,0")
2844 (match_operand:DF 5 "reg_or_fp0_operand" "0,fG")))]
2845 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2848 fcmov%D3 %R4,%R5,%0"
2849 [(set_attr "type" "fcmov")])
2852 [(set (match_operand:SF 0 "register_operand" "=f,f")
2854 (match_operator 3 "signed_comparison_operator"
2856 (match_operand:SF 4 "reg_or_fp0_operand" "fG,fG"))
2857 (match_operand:DF 2 "fp0_operand" "G,G")])
2858 (match_operand:SF 1 "reg_or_fp0_operand" "fG,0")
2859 (match_operand:SF 5 "reg_or_fp0_operand" "0,fG")))]
2860 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2863 fcmov%D3 %R4,%R5,%0"
2864 [(set_attr "type" "fcmov")])
2867 [(set (match_operand:DF 0 "register_operand" "=f,f")
2869 (match_operator 3 "signed_comparison_operator"
2871 (match_operand:SF 4 "reg_or_fp0_operand" "fG,fG"))
2872 (match_operand:DF 2 "fp0_operand" "G,G")])
2873 (float_extend:DF (match_operand:SF 1 "reg_or_fp0_operand" "fG,0"))
2874 (match_operand:DF 5 "reg_or_fp0_operand" "0,fG")))]
2875 "TARGET_FP && alpha_tp != ALPHA_TP_INSN"
2878 fcmov%D3 %R4,%R5,%0"
2879 [(set_attr "type" "fcmov")])
2881 (define_expand "maxdf3"
2883 (le:DF (match_operand:DF 1 "reg_or_fp0_operand" "")
2884 (match_operand:DF 2 "reg_or_fp0_operand" "")))
2885 (set (match_operand:DF 0 "register_operand" "")
2886 (if_then_else:DF (eq (match_dup 3) (match_dup 4))
2887 (match_dup 1) (match_dup 2)))]
2890 { operands[3] = gen_reg_rtx (DFmode);
2891 operands[4] = CONST0_RTX (DFmode);
2894 (define_expand "mindf3"
2896 (lt:DF (match_operand:DF 1 "reg_or_fp0_operand" "")
2897 (match_operand:DF 2 "reg_or_fp0_operand" "")))
2898 (set (match_operand:DF 0 "register_operand" "")
2899 (if_then_else:DF (ne (match_dup 3) (match_dup 4))
2900 (match_dup 1) (match_dup 2)))]
2903 { operands[3] = gen_reg_rtx (DFmode);
2904 operands[4] = CONST0_RTX (DFmode);
2907 (define_expand "maxsf3"
2909 (le:DF (float_extend:DF (match_operand:SF 1 "reg_or_fp0_operand" ""))
2910 (float_extend:DF (match_operand:SF 2 "reg_or_fp0_operand" ""))))
2911 (set (match_operand:SF 0 "register_operand" "")
2912 (if_then_else:SF (eq (match_dup 3) (match_dup 4))
2913 (match_dup 1) (match_dup 2)))]
2916 { operands[3] = gen_reg_rtx (DFmode);
2917 operands[4] = CONST0_RTX (DFmode);
2920 (define_expand "minsf3"
2922 (lt:DF (float_extend:DF (match_operand:SF 1 "reg_or_fp0_operand" ""))
2923 (float_extend:DF (match_operand:SF 2 "reg_or_fp0_operand" ""))))
2924 (set (match_operand:SF 0 "register_operand" "")
2925 (if_then_else:SF (ne (match_dup 3) (match_dup 4))
2926 (match_dup 1) (match_dup 2)))]
2929 { operands[3] = gen_reg_rtx (DFmode);
2930 operands[4] = CONST0_RTX (DFmode);
2936 (match_operator 1 "signed_comparison_operator"
2937 [(match_operand:DF 2 "reg_or_fp0_operand" "fG")
2938 (match_operand:DF 3 "fp0_operand" "G")])
2939 (label_ref (match_operand 0 "" ""))
2943 [(set_attr "type" "fbr")])
2948 (match_operator 1 "signed_comparison_operator"
2950 (match_operand:SF 2 "reg_or_fp0_operand" "fG"))
2951 (match_operand:DF 3 "fp0_operand" "G")])
2952 (label_ref (match_operand 0 "" ""))
2956 [(set_attr "type" "fbr")])
2958 ;; These are the main define_expand's used to make conditional branches
2961 (define_expand "cmpdf"
2962 [(set (cc0) (compare (match_operand:DF 0 "reg_or_fp0_operand" "")
2963 (match_operand:DF 1 "reg_or_fp0_operand" "")))]
2967 alpha_compare_op0 = operands[0];
2968 alpha_compare_op1 = operands[1];
2969 alpha_compare_fp_p = 1;
2973 (define_expand "cmpdi"
2974 [(set (cc0) (compare (match_operand:DI 0 "reg_or_0_operand" "")
2975 (match_operand:DI 1 "reg_or_8bit_operand" "")))]
2979 alpha_compare_op0 = operands[0];
2980 alpha_compare_op1 = operands[1];
2981 alpha_compare_fp_p = 0;
2985 (define_expand "beq"
2987 (if_then_else (match_dup 1)
2988 (label_ref (match_operand 0 "" ""))
2991 "{ operands[1] = alpha_emit_conditional_branch (EQ); }")
2993 (define_expand "bne"
2995 (if_then_else (match_dup 1)
2996 (label_ref (match_operand 0 "" ""))
2999 "{ operands[1] = alpha_emit_conditional_branch (NE); }")
3001 (define_expand "blt"
3003 (if_then_else (match_dup 1)
3004 (label_ref (match_operand 0 "" ""))
3007 "{ operands[1] = alpha_emit_conditional_branch (LT); }")
3009 (define_expand "ble"
3011 (if_then_else (match_dup 1)
3012 (label_ref (match_operand 0 "" ""))
3015 "{ operands[1] = alpha_emit_conditional_branch (LE); }")
3017 (define_expand "bgt"
3019 (if_then_else (match_dup 1)
3020 (label_ref (match_operand 0 "" ""))
3023 "{ operands[1] = alpha_emit_conditional_branch (GT); }")
3025 (define_expand "bge"
3027 (if_then_else (match_dup 1)
3028 (label_ref (match_operand 0 "" ""))
3031 "{ operands[1] = alpha_emit_conditional_branch (GE); }")
3033 (define_expand "bltu"
3035 (if_then_else (match_dup 1)
3036 (label_ref (match_operand 0 "" ""))
3039 "{ operands[1] = alpha_emit_conditional_branch (LTU); }")
3041 (define_expand "bleu"
3043 (if_then_else (match_dup 1)
3044 (label_ref (match_operand 0 "" ""))
3047 "{ operands[1] = alpha_emit_conditional_branch (LEU); }")
3049 (define_expand "bgtu"
3051 (if_then_else (match_dup 1)
3052 (label_ref (match_operand 0 "" ""))
3055 "{ operands[1] = alpha_emit_conditional_branch (GTU); }")
3057 (define_expand "bgeu"
3059 (if_then_else (match_dup 1)
3060 (label_ref (match_operand 0 "" ""))
3063 "{ operands[1] = alpha_emit_conditional_branch (GEU); }")
3065 (define_expand "seq"
3066 [(set (match_operand:DI 0 "register_operand" "")
3071 if (alpha_compare_fp_p)
3074 operands[1] = gen_rtx_EQ (DImode, alpha_compare_op0, alpha_compare_op1);
3077 (define_expand "sne"
3078 [(set (match_operand:DI 0 "register_operand" "")
3080 (set (match_dup 0) (xor:DI (match_dup 0) (const_int 1)))]
3084 if (alpha_compare_fp_p)
3087 operands[1] = gen_rtx_EQ (DImode, alpha_compare_op0, alpha_compare_op1);
3090 (define_expand "slt"
3091 [(set (match_operand:DI 0 "register_operand" "")
3096 if (alpha_compare_fp_p)
3099 operands[1] = gen_rtx_LT (DImode, alpha_compare_op0, alpha_compare_op1);
3102 (define_expand "sle"
3103 [(set (match_operand:DI 0 "register_operand" "")
3108 if (alpha_compare_fp_p)
3111 operands[1] = gen_rtx_LE (DImode, alpha_compare_op0, alpha_compare_op1);
3114 (define_expand "sgt"
3115 [(set (match_operand:DI 0 "register_operand" "")
3120 if (alpha_compare_fp_p)
3123 operands[1] = gen_rtx_LT (DImode, force_reg (DImode, alpha_compare_op1),
3127 (define_expand "sge"
3128 [(set (match_operand:DI 0 "register_operand" "")
3133 if (alpha_compare_fp_p)
3136 operands[1] = gen_rtx_LE (DImode, force_reg (DImode, alpha_compare_op1),
3140 (define_expand "sltu"
3141 [(set (match_operand:DI 0 "register_operand" "")
3146 if (alpha_compare_fp_p)
3149 operands[1] = gen_rtx_LTU (DImode, alpha_compare_op0, alpha_compare_op1);
3152 (define_expand "sleu"
3153 [(set (match_operand:DI 0 "register_operand" "")
3158 if (alpha_compare_fp_p)
3161 operands[1] = gen_rtx_LEU (DImode, alpha_compare_op0, alpha_compare_op1);
3164 (define_expand "sgtu"
3165 [(set (match_operand:DI 0 "register_operand" "")
3170 if (alpha_compare_fp_p)
3173 operands[1] = gen_rtx_LTU (DImode, force_reg (DImode, alpha_compare_op1),
3177 (define_expand "sgeu"
3178 [(set (match_operand:DI 0 "register_operand" "")
3183 if (alpha_compare_fp_p)
3186 operands[1] = gen_rtx_LEU (DImode, force_reg (DImode, alpha_compare_op1),
3190 ;; These are the main define_expand's used to make conditional moves.
3192 (define_expand "movsicc"
3193 [(set (match_operand:SI 0 "register_operand" "")
3194 (if_then_else:DI (match_operand 1 "comparison_operator" "")
3195 (match_operand:SI 2 "reg_or_8bit_operand" "")
3196 (match_operand:SI 3 "reg_or_8bit_operand" "")))]
3200 if ((operands[1] = alpha_emit_conditional_move (operands[1], SImode)) == 0)
3204 (define_expand "movdicc"
3205 [(set (match_operand:DI 0 "register_operand" "")
3206 (if_then_else:DI (match_operand 1 "comparison_operator" "")
3207 (match_operand:DI 2 "reg_or_8bit_operand" "")
3208 (match_operand:DI 3 "reg_or_8bit_operand" "")))]
3212 if ((operands[1] = alpha_emit_conditional_move (operands[1], DImode)) == 0)
3216 (define_expand "movsfcc"
3217 [(set (match_operand:SF 0 "register_operand" "")
3218 (if_then_else:SF (match_operand 1 "comparison_operator" "")
3219 (match_operand:SF 2 "reg_or_8bit_operand" "")
3220 (match_operand:SF 3 "reg_or_8bit_operand" "")))]
3224 if ((operands[1] = alpha_emit_conditional_move (operands[1], SFmode)) == 0)
3228 (define_expand "movdfcc"
3229 [(set (match_operand:DF 0 "register_operand" "")
3230 (if_then_else:DF (match_operand 1 "comparison_operator" "")
3231 (match_operand:DF 2 "reg_or_8bit_operand" "")
3232 (match_operand:DF 3 "reg_or_8bit_operand" "")))]
3236 if ((operands[1] = alpha_emit_conditional_move (operands[1], DFmode)) == 0)
3240 ;; These define_split definitions are used in cases when comparisons have
3241 ;; not be stated in the correct way and we need to reverse the second
3242 ;; comparison. For example, x >= 7 has to be done as x < 6 with the
3243 ;; comparison that tests the result being reversed. We have one define_split
3244 ;; for each use of a comparison. They do not match valid insns and need
3245 ;; not generate valid insns.
3247 ;; We can also handle equality comparisons (and inequality comparisons in
3248 ;; cases where the resulting add cannot overflow) by doing an add followed by
3249 ;; a comparison with zero. This is faster since the addition takes one
3250 ;; less cycle than a compare when feeding into a conditional move.
3251 ;; For this case, we also have an SImode pattern since we can merge the add
3252 ;; and sign extend and the order doesn't matter.
3254 ;; We do not do this for floating-point, since it isn't clear how the "wrong"
3255 ;; operation could have been generated.
3258 [(set (match_operand:DI 0 "register_operand" "")
3260 (match_operator 1 "comparison_operator"
3261 [(match_operand:DI 2 "reg_or_0_operand" "")
3262 (match_operand:DI 3 "reg_or_cint_operand" "")])
3263 (match_operand:DI 4 "reg_or_cint_operand" "")
3264 (match_operand:DI 5 "reg_or_cint_operand" "")))
3265 (clobber (match_operand:DI 6 "register_operand" ""))]
3266 "operands[3] != const0_rtx"
3267 [(set (match_dup 6) (match_dup 7))
3269 (if_then_else:DI (match_dup 8) (match_dup 4) (match_dup 5)))]
3271 { enum rtx_code code = GET_CODE (operands[1]);
3272 int unsignedp = (code == GEU || code == LEU || code == GTU || code == LTU);
3274 /* If we are comparing for equality with a constant and that constant
3275 appears in the arm when the register equals the constant, use the
3276 register since that is more likely to match (and to produce better code
3279 if (code == EQ && GET_CODE (operands[3]) == CONST_INT
3280 && rtx_equal_p (operands[4], operands[3]))
3281 operands[4] = operands[2];
3283 else if (code == NE && GET_CODE (operands[3]) == CONST_INT
3284 && rtx_equal_p (operands[5], operands[3]))
3285 operands[5] = operands[2];
3287 if (code == NE || code == EQ
3288 || (extended_count (operands[2], DImode, unsignedp) >= 1
3289 && extended_count (operands[3], DImode, unsignedp) >= 1))
3291 if (GET_CODE (operands[3]) == CONST_INT)
3292 operands[7] = gen_rtx_PLUS (DImode, operands[2],
3293 GEN_INT (- INTVAL (operands[3])));
3295 operands[7] = gen_rtx_MINUS (DImode, operands[2], operands[3]);
3297 operands[8] = gen_rtx_fmt_ee (code, VOIDmode, operands[6], const0_rtx);
3300 else if (code == EQ || code == LE || code == LT
3301 || code == LEU || code == LTU)
3303 operands[7] = gen_rtx_fmt_ee (code, DImode, operands[2], operands[3]);
3304 operands[8] = gen_rtx_NE (VOIDmode, operands[6], const0_rtx);
3308 operands[7] = gen_rtx_fmt_ee (reverse_condition (code), DImode,
3309 operands[2], operands[3]);
3310 operands[8] = gen_rtx_EQ (VOIDmode, operands[6], const0_rtx);
3315 [(set (match_operand:DI 0 "register_operand" "")
3317 (match_operator 1 "comparison_operator"
3318 [(match_operand:SI 2 "reg_or_0_operand" "")
3319 (match_operand:SI 3 "reg_or_cint_operand" "")])
3320 (match_operand:DI 4 "reg_or_8bit_operand" "")
3321 (match_operand:DI 5 "reg_or_8bit_operand" "")))
3322 (clobber (match_operand:DI 6 "register_operand" ""))]
3323 "operands[3] != const0_rtx
3324 && (GET_CODE (operands[1]) == EQ || GET_CODE (operands[1]) == NE)"
3325 [(set (match_dup 6) (match_dup 7))
3327 (if_then_else:DI (match_dup 8) (match_dup 4) (match_dup 5)))]
3329 { enum rtx_code code = GET_CODE (operands[1]);
3330 int unsignedp = (code == GEU || code == LEU || code == GTU || code == LTU);
3333 if ((code != NE && code != EQ
3334 && ! (extended_count (operands[2], DImode, unsignedp) >= 1
3335 && extended_count (operands[3], DImode, unsignedp) >= 1)))
3338 if (GET_CODE (operands[3]) == CONST_INT)
3339 tem = gen_rtx_PLUS (SImode, operands[2],
3340 GEN_INT (- INTVAL (operands[3])));
3342 tem = gen_rtx_MINUS (SImode, operands[2], operands[3]);
3344 operands[7] = gen_rtx_SIGN_EXTEND (DImode, tem);
3345 operands[8] = gen_rtx_fmt_ee (GET_CODE (operands[1]), VOIDmode,
3346 operands[6], const0_rtx);
3352 (match_operator 1 "comparison_operator"
3353 [(match_operand:DI 2 "reg_or_0_operand" "")
3354 (match_operand:DI 3 "reg_or_cint_operand" "")])
3355 (label_ref (match_operand 0 "" ""))
3357 (clobber (match_operand:DI 4 "register_operand" ""))]
3358 "operands[3] != const0_rtx"
3359 [(set (match_dup 4) (match_dup 5))
3360 (set (pc) (if_then_else (match_dup 6) (label_ref (match_dup 0)) (pc)))]
3362 { enum rtx_code code = GET_CODE (operands[1]);
3363 int unsignedp = (code == GEU || code == LEU || code == GTU || code == LTU);
3365 if (code == NE || code == EQ
3366 || (extended_count (operands[2], DImode, unsignedp) >= 1
3367 && extended_count (operands[3], DImode, unsignedp) >= 1))
3369 if (GET_CODE (operands[3]) == CONST_INT)
3370 operands[5] = gen_rtx_PLUS (DImode, operands[2],
3371 GEN_INT (- INTVAL (operands[3])));
3373 operands[5] = gen_rtx_MINUS (DImode, operands[2], operands[3]);
3375 operands[6] = gen_rtx_fmt_ee (code, VOIDmode, operands[4], const0_rtx);
3378 else if (code == EQ || code == LE || code == LT
3379 || code == LEU || code == LTU)
3381 operands[5] = gen_rtx_fmt_ee (code, DImode, operands[2], operands[3]);
3382 operands[6] = gen_rtx_NE (VOIDmode, operands[4], const0_rtx);
3386 operands[5] = gen_rtx_fmt_ee (reverse_condition (code), DImode,
3387 operands[2], operands[3]);
3388 operands[6] = gen_rtx_EQ (VOIDmode, operands[4], const0_rtx);
3395 (match_operator 1 "comparison_operator"
3396 [(match_operand:SI 2 "reg_or_0_operand" "")
3397 (match_operand:SI 3 "const_int_operand" "")])
3398 (label_ref (match_operand 0 "" ""))
3400 (clobber (match_operand:DI 4 "register_operand" ""))]
3401 "operands[3] != const0_rtx
3402 && (GET_CODE (operands[1]) == EQ || GET_CODE (operands[1]) == NE)"
3403 [(set (match_dup 4) (match_dup 5))
3404 (set (pc) (if_then_else (match_dup 6) (label_ref (match_dup 0)) (pc)))]
3408 if (GET_CODE (operands[3]) == CONST_INT)
3409 tem = gen_rtx_PLUS (SImode, operands[2],
3410 GEN_INT (- INTVAL (operands[3])));
3412 tem = gen_rtx_MINUS (SImode, operands[2], operands[3]);
3414 operands[5] = gen_rtx_SIGN_EXTEND (DImode, tem);
3415 operands[6] = gen_rtx_fmt_ee (GET_CODE (operands[1]), VOIDmode,
3416 operands[4], const0_rtx);
3419 ;; We can convert such things as "a > 0xffff" to "t = a & ~ 0xffff; t != 0".
3420 ;; This eliminates one, and sometimes two, insns when the AND can be done
3423 [(set (match_operand:DI 0 "register_operand" "")
3424 (match_operator 1 "comparison_operator"
3425 [(match_operand:DI 2 "register_operand" "")
3426 (match_operand:DI 3 "const_int_operand" "")]))
3427 (clobber (match_operand:DI 4 "register_operand" ""))]
3428 "exact_log2 (INTVAL (operands[3]) + 1) >= 0
3429 && (GET_CODE (operands[1]) == GTU
3430 || GET_CODE (operands[1]) == LEU
3431 || ((GET_CODE (operands[1]) == GT || GET_CODE (operands[1]) == LE)
3432 && extended_count (operands[2], DImode, 1) > 0))"
3433 [(set (match_dup 4) (and:DI (match_dup 2) (match_dup 5)))
3434 (set (match_dup 0) (match_dup 6))]
3437 operands[5] = GEN_INT (~ INTVAL (operands[3]));
3438 operands[6] = gen_rtx_fmt_ee (((GET_CODE (operands[1]) == GTU
3439 || GET_CODE (operands[1]) == GT)
3441 DImode, operands[4], const0_rtx);
3444 ;; Here are the CALL and unconditional branch insns. Calls on NT and OSF
3445 ;; work differently, so we have different patterns for each.
3447 (define_expand "call"
3448 [(use (match_operand:DI 0 "" ""))
3449 (use (match_operand 1 "" ""))
3450 (use (match_operand 2 "" ""))
3451 (use (match_operand 3 "" ""))]
3454 { if (TARGET_WINDOWS_NT)
3455 emit_call_insn (gen_call_nt (operands[0], operands[1]));
3456 else if (TARGET_OPEN_VMS)
3457 emit_call_insn (gen_call_vms (operands[0], operands[2]));
3459 emit_call_insn (gen_call_osf (operands[0], operands[1]));
3464 (define_expand "call_osf"
3465 [(parallel [(call (mem:DI (match_operand 0 "" ""))
3466 (match_operand 1 "" ""))
3467 (clobber (reg:DI 27))
3468 (clobber (reg:DI 26))])]
3471 { if (GET_CODE (operands[0]) != MEM)
3474 operands[0] = XEXP (operands[0], 0);
3476 if (GET_CODE (operands[0]) != SYMBOL_REF
3477 && ! (GET_CODE (operands[0]) == REG && REGNO (operands[0]) == 27))
3479 rtx tem = gen_rtx_REG (DImode, 27);
3480 emit_move_insn (tem, operands[0]);
3485 (define_expand "call_nt"
3486 [(parallel [(call (mem:DI (match_operand 0 "" ""))
3487 (match_operand 1 "" ""))
3488 (clobber (reg:DI 26))])]
3491 { if (GET_CODE (operands[0]) != MEM)
3494 operands[0] = XEXP (operands[0], 0);
3495 if (GET_CODE (operands[0]) != SYMBOL_REF && GET_CODE (operands[0]) != REG)
3496 operands[0] = force_reg (DImode, operands[0]);
3500 ;; call openvms/alpha
3501 ;; op 0: symbol ref for called function
3502 ;; op 1: next_arg_reg (argument information value for R25)
3504 (define_expand "call_vms"
3505 [(parallel [(call (mem:DI (match_operand 0 "" ""))
3506 (match_operand 1 "" ""))
3510 (clobber (reg:DI 27))])]
3513 { if (GET_CODE (operands[0]) != MEM)
3516 operands[0] = XEXP (operands[0], 0);
3518 /* Always load AI with argument information, then handle symbolic and
3519 indirect call differently. Load RA and set operands[2] to PV in
3522 emit_move_insn (gen_rtx_REG (DImode, 25), operands[1]);
3523 if (GET_CODE (operands[0]) == SYMBOL_REF)
3525 extern char *savealloc ();
3526 char *linksym, *symbol = XSTR (operands[0], 0);
3531 linksym = savealloc (strlen (symbol) + 6);
3533 alpha_need_linkage (symbol, 0);
3536 strcpy (linksym+1, symbol);
3537 strcat (linksym, \"..lk\");
3538 linkage = gen_rtx_SYMBOL_REF (Pmode, linksym);
3540 emit_move_insn (gen_rtx_REG (Pmode, 26), gen_rtx_MEM (Pmode, linkage));
3543 = validize_mem (gen_rtx_MEM (Pmode, plus_constant (linkage, 8)));
3547 emit_move_insn (gen_rtx_REG (Pmode, 26),
3548 gen_rtx_MEM (Pmode, plus_constant (operands[0], 8)));
3550 operands[2] = operands[0];
3555 (define_expand "call_value"
3556 [(use (match_operand 0 "" ""))
3557 (use (match_operand:DI 1 "" ""))
3558 (use (match_operand 2 "" ""))
3559 (use (match_operand 3 "" ""))
3560 (use (match_operand 4 "" ""))]
3563 { if (TARGET_WINDOWS_NT)
3564 emit_call_insn (gen_call_value_nt (operands[0], operands[1], operands[2]));
3565 else if (TARGET_OPEN_VMS)
3566 emit_call_insn (gen_call_value_vms (operands[0], operands[1],
3569 emit_call_insn (gen_call_value_osf (operands[0], operands[1],
3574 (define_expand "call_value_osf"
3575 [(parallel [(set (match_operand 0 "" "")
3576 (call (mem:DI (match_operand 1 "" ""))
3577 (match_operand 2 "" "")))
3578 (clobber (reg:DI 27))
3579 (clobber (reg:DI 26))])]
3582 { if (GET_CODE (operands[1]) != MEM)
3585 operands[1] = XEXP (operands[1], 0);
3587 if (GET_CODE (operands[1]) != SYMBOL_REF
3588 && ! (GET_CODE (operands[1]) == REG && REGNO (operands[1]) == 27))
3590 rtx tem = gen_rtx_REG (DImode, 27);
3591 emit_move_insn (tem, operands[1]);
3596 (define_expand "call_value_nt"
3597 [(parallel [(set (match_operand 0 "" "")
3598 (call (mem:DI (match_operand 1 "" ""))
3599 (match_operand 2 "" "")))
3600 (clobber (reg:DI 26))])]
3603 { if (GET_CODE (operands[1]) != MEM)
3606 operands[1] = XEXP (operands[1], 0);
3607 if (GET_CODE (operands[0]) != SYMBOL_REF && GET_CODE (operands[0]) != REG)
3608 operands[1] = force_reg (DImode, operands[1]);
3611 (define_expand "call_value_vms"
3612 [(parallel [(set (match_operand 0 "" "")
3613 (call (mem:DI (match_operand:DI 1 "" ""))
3614 (match_operand 2 "" "")))
3618 (clobber (reg:DI 27))])]
3621 { if (GET_CODE (operands[1]) != MEM)
3624 operands[1] = XEXP (operands[1], 0);
3626 /* Always load AI with argument information, then handle symbolic and
3627 indirect call differently. Load RA and set operands[3] to PV in
3630 emit_move_insn (gen_rtx_REG (DImode, 25), operands[2]);
3631 if (GET_CODE (operands[1]) == SYMBOL_REF)
3633 extern char *savealloc ();
3634 char *linksym, *symbol = XSTR (operands[1], 0);
3639 linksym = savealloc (strlen (symbol) + 6);
3641 alpha_need_linkage (symbol, 0);
3643 strcpy (linksym+1, symbol);
3644 strcat (linksym, \"..lk\");
3645 linkage = gen_rtx_SYMBOL_REF (Pmode, linksym);
3647 emit_move_insn (gen_rtx_REG (Pmode, 26), gen_rtx_MEM (Pmode, linkage));
3650 = validize_mem (gen_rtx_MEM (Pmode, plus_constant (linkage, 8)));
3654 emit_move_insn (gen_rtx_REG (Pmode, 26),
3655 gen_rtx_MEM (Pmode, plus_constant (operands[1], 8)));
3657 operands[3] = operands[1];
3662 [(call (mem:DI (match_operand:DI 0 "call_operand" "r,R,i"))
3663 (match_operand 1 "" ""))
3664 (clobber (reg:DI 27))
3665 (clobber (reg:DI 26))]
3666 "! TARGET_WINDOWS_NT && ! TARGET_OPEN_VMS"
3668 jsr $26,($27),0\;ldgp $29,0($26)
3670 jsr $26,%0\;ldgp $29,0($26)"
3671 [(set_attr "type" "jsr")
3672 (set_attr "length" "12,*,12")])
3675 [(call (mem:DI (match_operand:DI 0 "call_operand" "r,R,i"))
3676 (match_operand 1 "" ""))
3677 (clobber (reg:DI 26))]
3683 [(set_attr "type" "jsr")
3684 (set_attr "length" "*,*,12")])
3687 [(call (mem:DI (match_operand:DI 0 "call_operand" "r,i"))
3688 (match_operand 1 "" ""))
3689 (use (match_operand:DI 2 "general_operand" "r,m"))
3692 (clobber (reg:DI 27))]
3695 bis %2,%2,$27\;jsr $26,0\;ldq $27,0($29)
3696 ldq $27,%2\;jsr $26,%0\;ldq $27,0($29)"
3697 [(set_attr "type" "jsr")
3698 (set_attr "length" "12,16")])
3701 [(set (match_operand 0 "register_operand" "=rf,rf,rf")
3702 (call (mem:DI (match_operand:DI 1 "call_operand" "r,R,i"))
3703 (match_operand 2 "" "")))
3704 (clobber (reg:DI 27))
3705 (clobber (reg:DI 26))]
3706 "! TARGET_WINDOWS_NT && ! TARGET_OPEN_VMS"
3708 jsr $26,($27),0\;ldgp $29,0($26)
3710 jsr $26,%1\;ldgp $29,0($26)"
3711 [(set_attr "type" "jsr")
3712 (set_attr "length" "12,*,12")])
3715 [(set (match_operand 0 "register_operand" "=rf,rf,rf")
3716 (call (mem:DI (match_operand:DI 1 "call_operand" "r,R,i"))
3717 (match_operand 2 "" "")))
3718 (clobber (reg:DI 26))]
3724 [(set_attr "type" "jsr")
3725 (set_attr "length" "*,*,12")])
3728 [(set (match_operand 0 "register_operand" "")
3729 (call (mem:DI (match_operand:DI 1 "call_operand" "r,i"))
3730 (match_operand 2 "" "")))
3731 (use (match_operand:DI 3 "general_operand" "r,m"))
3734 (clobber (reg:DI 27))]
3737 bis %3,%3,$27\;jsr $26,0\;ldq $27,0($29)
3738 ldq $27,%3\;jsr $26,%1\;ldq $27,0($29)"
3739 [(set_attr "type" "jsr")
3740 (set_attr "length" "12,16")])
3742 ;; Call subroutine returning any type.
3744 (define_expand "untyped_call"
3745 [(parallel [(call (match_operand 0 "" "")
3747 (match_operand 1 "" "")
3748 (match_operand 2 "" "")])]
3754 emit_call_insn (gen_call (operands[0], const0_rtx, NULL, const0_rtx));
3756 for (i = 0; i < XVECLEN (operands[2], 0); i++)
3758 rtx set = XVECEXP (operands[2], 0, i);
3759 emit_move_insn (SET_DEST (set), SET_SRC (set));
3762 /* The optimizer does not know that the call sets the function value
3763 registers we stored in the result block. We avoid problems by
3764 claiming that all hard registers are used and clobbered at this
3766 emit_insn (gen_blockage ());
3771 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
3772 ;; all of memory. This blocks insns from being moved across this point.
3774 (define_insn "blockage"
3775 [(unspec_volatile [(const_int 0)] 1)]
3778 [(set_attr "length" "0")])
3782 (label_ref (match_operand 0 "" "")))]
3785 [(set_attr "type" "ibr")])
3787 (define_insn "return"
3791 [(set_attr "type" "ibr")])
3793 ;; Use a different pattern for functions which have non-trivial
3794 ;; epilogues so as not to confuse jump and reorg.
3795 (define_insn "return_internal"
3800 [(set_attr "type" "ibr")])
3802 (define_insn "indirect_jump"
3803 [(set (pc) (match_operand:DI 0 "register_operand" "r"))]
3806 [(set_attr "type" "ibr")])
3812 [(set_attr "type" "ilog")])
3814 (define_expand "tablejump"
3815 [(use (match_operand:SI 0 "register_operand" ""))
3816 (use (match_operand:SI 1 "" ""))]
3820 if (TARGET_WINDOWS_NT)
3821 emit_jump_insn (gen_tablejump_nt (operands[0], operands[1]));
3822 else if (TARGET_OPEN_VMS)
3823 emit_jump_insn (gen_tablejump_vms (operands[0], operands[1]));
3825 emit_jump_insn (gen_tablejump_osf (operands[0], operands[1]));
3830 (define_expand "tablejump_osf"
3832 (sign_extend:DI (match_operand:SI 0 "register_operand" "")))
3833 (parallel [(set (pc)
3834 (plus:DI (match_dup 3)
3835 (label_ref:DI (match_operand 1 "" ""))))
3836 (clobber (match_scratch:DI 2 "=r"))])]
3839 { operands[3] = gen_reg_rtx (DImode); }")
3841 (define_expand "tablejump_nt"
3843 (sign_extend:DI (match_operand:SI 0 "register_operand" "")))
3844 (parallel [(set (pc)
3846 (use (label_ref (match_operand 1 "" "")))])]
3849 { operands[3] = gen_reg_rtx (DImode); }")
3852 ;; tablejump, openVMS way
3854 ;; op 1: label preceding jump-table
3856 (define_expand "tablejump_vms"
3858 (match_operand:DI 0 "register_operand" ""))
3860 (plus:DI (match_dup 2)
3861 (label_ref:DI (match_operand 1 "" ""))))]
3864 { operands[2] = gen_reg_rtx (DImode); }")
3868 (plus:DI (match_operand:DI 0 "register_operand" "r")
3869 (label_ref:DI (match_operand 1 "" ""))))
3870 (clobber (match_scratch:DI 2 "=r"))]
3871 "! TARGET_WINDOWS_NT && ! TARGET_OPEN_VMS && next_active_insn (insn) != 0
3872 && GET_CODE (PATTERN (next_active_insn (insn))) == ADDR_DIFF_VEC
3873 && PREV_INSN (next_active_insn (insn)) == operands[1]"
3875 { rtx best_label = 0;
3876 rtx jump_table_insn = next_active_insn (operands[1]);
3878 if (GET_CODE (jump_table_insn) == JUMP_INSN
3879 && GET_CODE (PATTERN (jump_table_insn)) == ADDR_DIFF_VEC)
3881 rtx jump_table = PATTERN (jump_table_insn);
3882 int n_labels = XVECLEN (jump_table, 1);
3883 int best_count = -1;
3886 for (i = 0; i < n_labels; i++)
3890 for (j = i + 1; j < n_labels; j++)
3891 if (XEXP (XVECEXP (jump_table, 1, i), 0)
3892 == XEXP (XVECEXP (jump_table, 1, j), 0))
3895 if (count > best_count)
3896 best_count = count, best_label = XVECEXP (jump_table, 1, i);
3902 operands[3] = best_label;
3903 return \"addq %0,$29,%2\;jmp $31,(%2),%3\";
3906 return \"addq %0,$29,%2\;jmp $31,(%2),0\";
3908 [(set_attr "type" "ibr")
3909 (set_attr "length" "8")])
3913 (match_operand:DI 0 "register_operand" "r"))
3914 (use (label_ref (match_operand 1 "" "")))]
3915 "TARGET_WINDOWS_NT && next_active_insn (insn) != 0
3916 && GET_CODE (PATTERN (next_active_insn (insn))) == ADDR_DIFF_VEC
3917 && PREV_INSN (next_active_insn (insn)) == operands[1]"
3919 { rtx best_label = 0;
3920 rtx jump_table_insn = next_active_insn (operands[1]);
3922 if (GET_CODE (jump_table_insn) == JUMP_INSN
3923 && GET_CODE (PATTERN (jump_table_insn)) == ADDR_DIFF_VEC)
3925 rtx jump_table = PATTERN (jump_table_insn);
3926 int n_labels = XVECLEN (jump_table, 1);
3927 int best_count = -1;
3930 for (i = 0; i < n_labels; i++)
3934 for (j = i + 1; j < n_labels; j++)
3935 if (XEXP (XVECEXP (jump_table, 1, i), 0)
3936 == XEXP (XVECEXP (jump_table, 1, j), 0))
3939 if (count > best_count)
3940 best_count = count, best_label = XVECEXP (jump_table, 1, i);
3946 operands[2] = best_label;
3947 return \"jmp $31,(%0),%2\";
3950 return \"jmp $31,(%0),0\";
3952 [(set_attr "type" "ibr")])
3955 ;; op 0 is table offset
3956 ;; op 1 is table label
3961 (plus:DI (match_operand 0 "register_operand" "r")
3962 (label_ref (match_operand 1 "" ""))))]
3965 [(set_attr "type" "ibr")])
3967 ;; Cache flush. Used by INITIALIZE_TRAMPOLINE. 0x86 is PAL_imb, but we don't
3968 ;; want to have to include pal.h in our .s file.
3970 ;; Technically the type for call_pal is jsr, but we use that for determining
3971 ;; if we need a GP. Use ibr instead since it has the same EV5 scheduling
3974 [(unspec_volatile [(const_int 0)] 0)]
3977 [(set_attr "type" "ibr")])
3979 ;; Finally, we have the basic data motion insns. The byte and word insns
3980 ;; are done via define_expand. Start with the floating-point insns, since
3981 ;; they are simpler.
3984 [(set (match_operand:SF 0 "nonimmediate_operand" "=r,r,m,f,f,f,m")
3985 (match_operand:SF 1 "input_operand" "rG,m,rG,f,G,m,fG"))]
3987 && (register_operand (operands[0], SFmode)
3988 || reg_or_fp0_operand (operands[1], SFmode))"
3997 [(set_attr "type" "ilog,ild,ist,fcpys,fcpys,fld,fst")])
4000 [(set (match_operand:SF 0 "nonimmediate_operand" "=r,r,m,f,f,f,m,f,*r")
4001 (match_operand:SF 1 "input_operand" "rG,m,rG,f,G,m,fG,r,*f"))]
4003 && (register_operand (operands[0], SFmode)
4004 || reg_or_fp0_operand (operands[1], SFmode))"
4015 [(set_attr "type" "ilog,ild,ist,fcpys,fcpys,fld,fst,itof,ftoi")])
4018 [(set (match_operand:DF 0 "nonimmediate_operand" "=r,r,m,f,f,f,m")
4019 (match_operand:DF 1 "input_operand" "rG,m,rG,f,G,m,fG"))]
4021 && (register_operand (operands[0], DFmode)
4022 || reg_or_fp0_operand (operands[1], DFmode))"
4031 [(set_attr "type" "ilog,ild,ist,fcpys,fcpys,fld,fst")])
4034 [(set (match_operand:DF 0 "nonimmediate_operand" "=r,r,m,f,f,f,m,f,*r")
4035 (match_operand:DF 1 "input_operand" "rG,m,rG,f,G,m,fG,r,*f"))]
4037 && (register_operand (operands[0], DFmode)
4038 || reg_or_fp0_operand (operands[1], DFmode))"
4049 [(set_attr "type" "ilog,ild,ist,fcpys,fcpys,fld,fst,itof,ftoi")])
4051 (define_expand "movsf"
4052 [(set (match_operand:SF 0 "nonimmediate_operand" "")
4053 (match_operand:SF 1 "general_operand" ""))]
4057 if (GET_CODE (operands[0]) == MEM
4058 && ! reg_or_fp0_operand (operands[1], SFmode))
4059 operands[1] = force_reg (SFmode, operands[1]);
4062 (define_expand "movdf"
4063 [(set (match_operand:DF 0 "nonimmediate_operand" "")
4064 (match_operand:DF 1 "general_operand" ""))]
4068 if (GET_CODE (operands[0]) == MEM
4069 && ! reg_or_fp0_operand (operands[1], DFmode))
4070 operands[1] = force_reg (DFmode, operands[1]);
4074 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,r,r,r,r,r,m,f,f,f,m")
4075 (match_operand:SI 1 "input_operand" "r,J,I,K,L,m,rJ,f,J,m,fG"))]
4076 "! TARGET_WINDOWS_NT && ! TARGET_OPEN_VMS && ! TARGET_CIX
4077 && (register_operand (operands[0], SImode)
4078 || reg_or_0_operand (operands[1], SImode))"
4091 [(set_attr "type" "ilog,ilog,ilog,iadd,iadd,ild,ist,fcpys,fcpys,fld,fst")])
4094 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,r,r,r,r,r,m,f,f,f,m,r,*f")
4095 (match_operand:SI 1 "input_operand" "r,J,I,K,L,m,rJ,f,J,m,fG,f,*r"))]
4096 "! TARGET_WINDOWS_NT && ! TARGET_OPEN_VMS && TARGET_CIX
4097 && (register_operand (operands[0], SImode)
4098 || reg_or_0_operand (operands[1], SImode))"
4113 [(set_attr "type" "ilog,ilog,ilog,iadd,iadd,ild,ist,fcpys,fcpys,fld,fst,ftoi,itof")])
4116 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,r,r,r,r,r,r,m,f,f,f,m")
4117 (match_operand:SI 1 "input_operand" "r,J,I,K,L,s,m,rJ,f,J,m,fG"))]
4118 "(TARGET_WINDOWS_NT || TARGET_OPEN_VMS)
4119 && (register_operand (operands[0], SImode)
4120 || reg_or_0_operand (operands[1], SImode))"
4134 [(set_attr "type" "ilog,ilog,ilog,iadd,iadd,ldsym,ild,ist,fcpys,fcpys,fld,fst")])
4137 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,r,f,f")
4138 (match_operand:HI 1 "input_operand" "r,J,I,n,f,J"))]
4140 && (register_operand (operands[0], HImode)
4141 || register_operand (operands[1], HImode))"
4149 [(set_attr "type" "ilog,ilog,ilog,iadd,fcpys,fcpys")])
4152 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,r,r,m,f,f")
4153 (match_operand:HI 1 "input_operand" "r,J,I,n,m,rJ,f,J"))]
4155 && (register_operand (operands[0], HImode)
4156 || reg_or_0_operand (operands[1], HImode))"
4166 [(set_attr "type" "ilog,ilog,ilog,iadd,ild,ist,fcpys,fcpys")])
4169 [(set (match_operand:QI 0 "nonimmediate_operand" "=r,r,r,r,f,f")
4170 (match_operand:QI 1 "input_operand" "r,J,I,n,f,J"))]
4172 && (register_operand (operands[0], QImode)
4173 || register_operand (operands[1], QImode))"
4181 [(set_attr "type" "ilog,ilog,ilog,iadd,fcpys,fcpys")])
4184 [(set (match_operand:QI 0 "nonimmediate_operand" "=r,r,r,r,r,m,f,f")
4185 (match_operand:QI 1 "input_operand" "r,J,I,n,m,rJ,f,J"))]
4187 && (register_operand (operands[0], QImode)
4188 || reg_or_0_operand (operands[1], QImode))"
4198 [(set_attr "type" "ilog,ilog,ilog,iadd,ild,ist,fcpys,fcpys")])
4200 ;; We do two major things here: handle mem->mem and construct long
4203 (define_expand "movsi"
4204 [(set (match_operand:SI 0 "general_operand" "")
4205 (match_operand:SI 1 "general_operand" ""))]
4209 if (GET_CODE (operands[0]) == MEM
4210 && ! reg_or_0_operand (operands[1], SImode))
4211 operands[1] = force_reg (SImode, operands[1]);
4213 if (! CONSTANT_P (operands[1]) || input_operand (operands[1], SImode))
4215 else if (GET_CODE (operands[1]) == CONST_INT)
4218 = alpha_emit_set_const (operands[0], SImode, INTVAL (operands[1]), 3);
4219 if (rtx_equal_p (operands[0], operands[1]))
4224 ;; Split a load of a large constant into the appropriate two-insn
4228 [(set (match_operand:SI 0 "register_operand" "")
4229 (match_operand:SI 1 "const_int_operand" ""))]
4230 "! add_operand (operands[1], SImode)"
4231 [(set (match_dup 0) (match_dup 2))
4232 (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 3)))]
4235 = alpha_emit_set_const (operands[0], SImode, INTVAL (operands[1]), 2);
4237 if (tem == operands[0])
4244 [(set (match_operand:DI 0 "general_operand" "=r,r,r,r,r,r,r,m,f,f,f,Q")
4245 (match_operand:DI 1 "input_operand" "r,J,I,K,L,s,m,rJ,f,J,Q,fG"))]
4247 && (register_operand (operands[0], DImode)
4248 || reg_or_0_operand (operands[1], DImode))"
4262 [(set_attr "type" "ilog,ilog,ilog,iadd,iadd,ldsym,ild,ist,fcpys,fcpys,fld,fst")])
4265 [(set (match_operand:DI 0 "general_operand" "=r,r,r,r,r,r,r,m,f,f,f,Q,r,*f")
4266 (match_operand:DI 1 "input_operand" "r,J,I,K,L,s,m,rJ,f,J,Q,fG,f,*r"))]
4268 && (register_operand (operands[0], DImode)
4269 || reg_or_0_operand (operands[1], DImode))"
4285 [(set_attr "type" "ilog,ilog,ilog,iadd,iadd,ldsym,ild,ist,fcpys,fcpys,fld,fst,ftoi,itof")])
4287 ;; We do three major things here: handle mem->mem, put 64-bit constants in
4288 ;; memory, and construct long 32-bit constants.
4290 (define_expand "movdi"
4291 [(set (match_operand:DI 0 "general_operand" "")
4292 (match_operand:DI 1 "general_operand" ""))]
4298 if (GET_CODE (operands[0]) == MEM
4299 && ! reg_or_0_operand (operands[1], DImode))
4300 operands[1] = force_reg (DImode, operands[1]);
4302 if (! CONSTANT_P (operands[1]) || input_operand (operands[1], DImode))
4304 else if (GET_CODE (operands[1]) == CONST_INT
4305 && (tem = alpha_emit_set_const (operands[0], DImode,
4306 INTVAL (operands[1]), 3)) != 0)
4308 if (rtx_equal_p (tem, operands[0]))
4313 else if (CONSTANT_P (operands[1]))
4315 if (TARGET_BUILD_CONSTANTS)
4317 #if HOST_BITS_PER_WIDE_INT == 64
4320 if (GET_CODE (operands[1]) == CONST_INT)
4321 i = INTVAL (operands[1]);
4322 else if (GET_CODE (operands[1]) == CONST_DOUBLE)
4323 i = CONST_DOUBLE_LOW (operands[1]);
4327 tem = alpha_emit_set_long_const (operands[0], i);
4328 if (rtx_equal_p (tem, operands[0]))
4338 operands[1] = force_const_mem (DImode, operands[1]);
4339 if (reload_in_progress)
4341 emit_move_insn (operands[0], XEXP (operands[1], 0));
4342 operands[1] = copy_rtx (operands[1]);
4343 XEXP (operands[1], 0) = operands[0];
4346 operands[1] = validize_mem (operands[1]);
4353 ;; Split a load of a large constant into the appropriate two-insn
4357 [(set (match_operand:DI 0 "register_operand" "")
4358 (match_operand:DI 1 "const_int_operand" ""))]
4359 "! add_operand (operands[1], DImode)"
4360 [(set (match_dup 0) (match_dup 2))
4361 (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 3)))]
4364 = alpha_emit_set_const (operands[0], DImode, INTVAL (operands[1]), 2);
4366 if (tem == operands[0])
4372 ;; These are the partial-word cases.
4374 ;; First we have the code to load an aligned word. Operand 0 is the register
4375 ;; in which to place the result. It's mode is QImode or HImode. Operand 1
4376 ;; is an SImode MEM at the low-order byte of the proper word. Operand 2 is the
4377 ;; number of bits within the word that the value is. Operand 3 is an SImode
4378 ;; scratch register. If operand 0 is a hard register, operand 3 may be the
4379 ;; same register. It is allowed to conflict with operand 1 as well.
4381 (define_expand "aligned_loadqi"
4382 [(set (match_operand:SI 3 "register_operand" "")
4383 (match_operand:SI 1 "memory_operand" ""))
4384 (set (subreg:DI (match_operand:QI 0 "register_operand" "") 0)
4385 (zero_extract:DI (subreg:DI (match_dup 3) 0)
4387 (match_operand:DI 2 "const_int_operand" "")))]
4392 (define_expand "aligned_loadhi"
4393 [(set (match_operand:SI 3 "register_operand" "")
4394 (match_operand:SI 1 "memory_operand" ""))
4395 (set (subreg:DI (match_operand:HI 0 "register_operand" "") 0)
4396 (zero_extract:DI (subreg:DI (match_dup 3) 0)
4398 (match_operand:DI 2 "const_int_operand" "")))]
4403 ;; Similar for unaligned loads, where we use the sequence from the
4404 ;; Alpha Architecture manual.
4406 ;; Operand 1 is the address. Operands 2 and 3 are temporaries, where
4407 ;; operand 3 can overlap the input and output registers.
4409 (define_expand "unaligned_loadqi"
4410 [(set (match_operand:DI 2 "register_operand" "")
4411 (mem:DI (and:DI (match_operand:DI 1 "address_operand" "")
4413 (set (match_operand:DI 3 "register_operand" "")
4415 (set (subreg:DI (match_operand:QI 0 "register_operand" "") 0)
4416 (zero_extract:DI (match_dup 2)
4418 (ashift:DI (match_dup 3) (const_int 3))))]
4422 (define_expand "unaligned_loadhi"
4423 [(set (match_operand:DI 2 "register_operand" "")
4424 (mem:DI (and:DI (match_operand:DI 1 "address_operand" "")
4426 (set (match_operand:DI 3 "register_operand" "")
4428 (set (subreg:DI (match_operand:QI 0 "register_operand" "") 0)
4429 (zero_extract:DI (match_dup 2)
4431 (ashift:DI (match_dup 3) (const_int 3))))]
4435 ;; Storing an aligned byte or word requires two temporaries. Operand 0 is the
4436 ;; aligned SImode MEM. Operand 1 is the register containing the
4437 ;; byte or word to store. Operand 2 is the number of bits within the word that
4438 ;; the value should be placed. Operands 3 and 4 are SImode temporaries.
4440 (define_expand "aligned_store"
4441 [(set (match_operand:SI 3 "register_operand" "")
4442 (match_operand:SI 0 "memory_operand" ""))
4443 (set (subreg:DI (match_dup 3) 0)
4444 (and:DI (subreg:DI (match_dup 3) 0) (match_dup 5)))
4445 (set (subreg:DI (match_operand:SI 4 "register_operand" "") 0)
4446 (ashift:DI (zero_extend:DI (match_operand 1 "register_operand" ""))
4447 (match_operand:DI 2 "const_int_operand" "")))
4448 (set (subreg:DI (match_dup 4) 0)
4449 (ior:DI (subreg:DI (match_dup 4) 0) (subreg:DI (match_dup 3) 0)))
4450 (set (match_dup 0) (match_dup 4))]
4453 { operands[5] = GEN_INT (~ (GET_MODE_MASK (GET_MODE (operands[1]))
4454 << INTVAL (operands[2])));
4457 ;; For the unaligned byte and halfword cases, we use code similar to that
4458 ;; in the ;; Architecture book, but reordered to lower the number of registers
4459 ;; required. Operand 0 is the address. Operand 1 is the data to store.
4460 ;; Operands 2, 3, and 4 are DImode temporaries, where operands 2 and 4 may
4461 ;; be the same temporary, if desired. If the address is in a register,
4462 ;; operand 2 can be that register.
4464 (define_expand "unaligned_storeqi"
4465 [(set (match_operand:DI 3 "register_operand" "")
4466 (mem:DI (and:DI (match_operand:DI 0 "address_operand" "")
4468 (set (match_operand:DI 2 "register_operand" "")
4471 (and:DI (not:DI (ashift:DI (const_int 255)
4472 (ashift:DI (match_dup 2) (const_int 3))))
4474 (set (match_operand:DI 4 "register_operand" "")
4475 (ashift:DI (zero_extend:DI (match_operand:QI 1 "register_operand" ""))
4476 (ashift:DI (match_dup 2) (const_int 3))))
4477 (set (match_dup 4) (ior:DI (match_dup 4) (match_dup 3)))
4478 (set (mem:DI (and:DI (match_dup 0) (const_int -8)))
4483 (define_expand "unaligned_storehi"
4484 [(set (match_operand:DI 3 "register_operand" "")
4485 (mem:DI (and:DI (match_operand:DI 0 "address_operand" "")
4487 (set (match_operand:DI 2 "register_operand" "")
4490 (and:DI (not:DI (ashift:DI (const_int 65535)
4491 (ashift:DI (match_dup 2) (const_int 3))))
4493 (set (match_operand:DI 4 "register_operand" "")
4494 (ashift:DI (zero_extend:DI (match_operand:HI 1 "register_operand" ""))
4495 (ashift:DI (match_dup 2) (const_int 3))))
4496 (set (match_dup 4) (ior:DI (match_dup 4) (match_dup 3)))
4497 (set (mem:DI (and:DI (match_dup 0) (const_int -8)))
4502 ;; Here are the define_expand's for QI and HI moves that use the above
4503 ;; patterns. We have the normal sets, plus the ones that need scratch
4504 ;; registers for reload.
4506 (define_expand "movqi"
4507 [(set (match_operand:QI 0 "general_operand" "")
4508 (match_operand:QI 1 "general_operand" ""))]
4514 if (GET_CODE (operands[0]) == MEM
4515 && ! reg_or_0_operand (operands[1], QImode))
4516 operands[1] = force_reg (QImode, operands[1]);
4518 if (GET_CODE (operands[1]) == CONST_INT
4519 && ! input_operand (operands[1], QImode))
4521 operands[1] = alpha_emit_set_const (operands[0], QImode,
4522 INTVAL (operands[1]), 3);
4524 if (rtx_equal_p (operands[0], operands[1]))
4531 /* If the output is not a register, the input must be. */
4532 if (GET_CODE (operands[0]) == MEM)
4533 operands[1] = force_reg (QImode, operands[1]);
4535 /* Handle four memory cases, unaligned and aligned for either the input
4536 or the output. The only case where we can be called during reload is
4537 for aligned loads; all other cases require temporaries. */
4539 if (GET_CODE (operands[1]) == MEM
4540 || (GET_CODE (operands[1]) == SUBREG
4541 && GET_CODE (SUBREG_REG (operands[1])) == MEM)
4542 || (reload_in_progress && GET_CODE (operands[1]) == REG
4543 && REGNO (operands[1]) >= FIRST_PSEUDO_REGISTER)
4544 || (reload_in_progress && GET_CODE (operands[1]) == SUBREG
4545 && GET_CODE (SUBREG_REG (operands[1])) == REG
4546 && REGNO (SUBREG_REG (operands[1])) >= FIRST_PSEUDO_REGISTER))
4548 if (aligned_memory_operand (operands[1], QImode))
4550 rtx aligned_mem, bitnum;
4551 rtx scratch = (reload_in_progress
4552 ? gen_rtx_REG (SImode, REGNO (operands[0]))
4553 : gen_reg_rtx (SImode));
4555 get_aligned_mem (operands[1], &aligned_mem, &bitnum);
4557 emit_insn (gen_aligned_loadqi (operands[0], aligned_mem, bitnum,
4562 /* Don't pass these as parameters since that makes the generated
4563 code depend on parameter evaluation order which will cause
4564 bootstrap failures. */
4566 rtx temp1 = gen_reg_rtx (DImode);
4567 rtx temp2 = gen_reg_rtx (DImode);
4569 = gen_unaligned_loadqi (operands[0],
4570 get_unaligned_address (operands[1], 0),
4573 alpha_set_memflags (seq, operands[1]);
4580 else if (GET_CODE (operands[0]) == MEM
4581 || (GET_CODE (operands[0]) == SUBREG
4582 && GET_CODE (SUBREG_REG (operands[0])) == MEM)
4583 || (reload_in_progress && GET_CODE (operands[0]) == REG
4584 && REGNO (operands[0]) >= FIRST_PSEUDO_REGISTER)
4585 || (reload_in_progress && GET_CODE (operands[0]) == SUBREG
4586 && GET_CODE (SUBREG_REG (operands[0])) == REG
4587 && REGNO (operands[0]) >= FIRST_PSEUDO_REGISTER))
4589 if (aligned_memory_operand (operands[0], QImode))
4591 rtx aligned_mem, bitnum;
4592 rtx temp1 = gen_reg_rtx (SImode);
4593 rtx temp2 = gen_reg_rtx (SImode);
4595 get_aligned_mem (operands[0], &aligned_mem, &bitnum);
4597 emit_insn (gen_aligned_store (aligned_mem, operands[1], bitnum,
4602 rtx temp1 = gen_reg_rtx (DImode);
4603 rtx temp2 = gen_reg_rtx (DImode);
4604 rtx temp3 = gen_reg_rtx (DImode);
4606 = gen_unaligned_storeqi (get_unaligned_address (operands[0], 0),
4607 operands[1], temp1, temp2, temp3);
4609 alpha_set_memflags (seq, operands[0]);
4617 (define_expand "movhi"
4618 [(set (match_operand:HI 0 "general_operand" "")
4619 (match_operand:HI 1 "general_operand" ""))]
4625 if (GET_CODE (operands[0]) == MEM
4626 && ! reg_or_0_operand (operands[1], HImode))
4627 operands[1] = force_reg (HImode, operands[1]);
4629 if (GET_CODE (operands[1]) == CONST_INT
4630 && ! input_operand (operands[1], HImode))
4632 operands[1] = alpha_emit_set_const (operands[0], HImode,
4633 INTVAL (operands[1]), 3);
4635 if (rtx_equal_p (operands[0], operands[1]))
4642 /* If the output is not a register, the input must be. */
4643 if (GET_CODE (operands[0]) == MEM)
4644 operands[1] = force_reg (HImode, operands[1]);
4646 /* Handle four memory cases, unaligned and aligned for either the input
4647 or the output. The only case where we can be called during reload is
4648 for aligned loads; all other cases require temporaries. */
4650 if (GET_CODE (operands[1]) == MEM
4651 || (GET_CODE (operands[1]) == SUBREG
4652 && GET_CODE (SUBREG_REG (operands[1])) == MEM)
4653 || (reload_in_progress && GET_CODE (operands[1]) == REG
4654 && REGNO (operands[1]) >= FIRST_PSEUDO_REGISTER)
4655 || (reload_in_progress && GET_CODE (operands[1]) == SUBREG
4656 && GET_CODE (SUBREG_REG (operands[1])) == REG
4657 && REGNO (SUBREG_REG (operands[1])) >= FIRST_PSEUDO_REGISTER))
4659 if (aligned_memory_operand (operands[1], HImode))
4661 rtx aligned_mem, bitnum;
4662 rtx scratch = (reload_in_progress
4663 ? gen_rtx_REG (SImode, REGNO (operands[0]))
4664 : gen_reg_rtx (SImode));
4666 get_aligned_mem (operands[1], &aligned_mem, &bitnum);
4668 emit_insn (gen_aligned_loadhi (operands[0], aligned_mem, bitnum,
4673 /* Don't pass these as parameters since that makes the generated
4674 code depend on parameter evaluation order which will cause
4675 bootstrap failures. */
4677 rtx temp1 = gen_reg_rtx (DImode);
4678 rtx temp2 = gen_reg_rtx (DImode);
4680 = gen_unaligned_loadhi (operands[0],
4681 get_unaligned_address (operands[1], 0),
4684 alpha_set_memflags (seq, operands[1]);
4691 else if (GET_CODE (operands[0]) == MEM
4692 || (GET_CODE (operands[0]) == SUBREG
4693 && GET_CODE (SUBREG_REG (operands[0])) == MEM)
4694 || (reload_in_progress && GET_CODE (operands[0]) == REG
4695 && REGNO (operands[0]) >= FIRST_PSEUDO_REGISTER)
4696 || (reload_in_progress && GET_CODE (operands[0]) == SUBREG
4697 && GET_CODE (SUBREG_REG (operands[0])) == REG
4698 && REGNO (operands[0]) >= FIRST_PSEUDO_REGISTER))
4700 if (aligned_memory_operand (operands[0], HImode))
4702 rtx aligned_mem, bitnum;
4703 rtx temp1 = gen_reg_rtx (SImode);
4704 rtx temp2 = gen_reg_rtx (SImode);
4706 get_aligned_mem (operands[0], &aligned_mem, &bitnum);
4708 emit_insn (gen_aligned_store (aligned_mem, operands[1], bitnum,
4713 rtx temp1 = gen_reg_rtx (DImode);
4714 rtx temp2 = gen_reg_rtx (DImode);
4715 rtx temp3 = gen_reg_rtx (DImode);
4717 = gen_unaligned_storehi (get_unaligned_address (operands[0], 0),
4718 operands[1], temp1, temp2, temp3);
4720 alpha_set_memflags (seq, operands[0]);
4729 ;; Here are the versions for reload. Note that in the unaligned cases
4730 ;; we know that the operand must not be a pseudo-register because stack
4731 ;; slots are always aligned references.
4733 (define_expand "reload_inqi"
4734 [(parallel [(match_operand:QI 0 "register_operand" "=r")
4735 (match_operand:QI 1 "unaligned_memory_operand" "m")
4736 (match_operand:TI 2 "register_operand" "=&r")])]
4740 rtx addr = get_unaligned_address (operands[1], 0);
4742 /* It is possible that one of the registers we got for operands[2]
4743 might coincide with that of operands[0] (which is why we made
4744 it TImode). Pick the other one to use as our scratch. */
4745 rtx scratch = gen_rtx_REG (DImode,
4746 REGNO (operands[0]) == REGNO (operands[2])
4747 ? REGNO (operands[2]) + 1 : REGNO (operands[2]));
4749 rtx seq = gen_unaligned_loadqi (operands[0], addr, scratch,
4750 gen_rtx_REG (DImode, REGNO (operands[0])));
4752 alpha_set_memflags (seq, operands[1]);
4757 (define_expand "reload_inhi"
4758 [(parallel [(match_operand:HI 0 "register_operand" "=r")
4759 (match_operand:HI 1 "unaligned_memory_operand" "m")
4760 (match_operand:TI 2 "register_operand" "=&r")])]
4764 rtx addr = get_unaligned_address (operands[1], 0);
4766 /* It is possible that one of the registers we got for operands[2]
4767 might coincide with that of operands[0] (which is why we made
4768 it TImode). Pick the other one to use as our scratch. */
4769 rtx scratch = gen_rtx_REG (DImode,
4770 REGNO (operands[0]) == REGNO (operands[2])
4771 ? REGNO (operands[2]) + 1 : REGNO (operands[2]));
4773 rtx seq = gen_unaligned_loadhi (operands[0], addr, scratch,
4774 gen_rtx_REG (DImode, REGNO (operands[0])));
4776 alpha_set_memflags (seq, operands[1]);
4781 (define_expand "reload_outqi"
4782 [(parallel [(match_operand:QI 0 "any_memory_operand" "=m")
4783 (match_operand:QI 1 "register_operand" "r")
4784 (match_operand:TI 2 "register_operand" "=&r")])]
4788 if (aligned_memory_operand (operands[0], QImode))
4790 rtx aligned_mem, bitnum;
4792 get_aligned_mem (operands[0], &aligned_mem, &bitnum);
4794 emit_insn (gen_aligned_store (aligned_mem, operands[1], bitnum,
4795 gen_rtx_REG (SImode, REGNO (operands[2])),
4796 gen_rtx_REG (SImode,
4797 REGNO (operands[2]) + 1)));
4801 rtx addr = get_unaligned_address (operands[0], 0);
4802 rtx scratch1 = gen_rtx_REG (DImode, REGNO (operands[2]));
4803 rtx scratch2 = gen_rtx_REG (DImode, REGNO (operands[2]) + 1);
4804 rtx scratch3 = scratch1;
4807 if (GET_CODE (addr) == REG)
4810 seq = gen_unaligned_storeqi (addr, operands[1], scratch1,
4811 scratch2, scratch3);
4812 alpha_set_memflags (seq, operands[0]);
4819 (define_expand "reload_outhi"
4820 [(parallel [(match_operand:HI 0 "any_memory_operand" "=m")
4821 (match_operand:HI 1 "register_operand" "r")
4822 (match_operand:TI 2 "register_operand" "=&r")])]
4826 if (aligned_memory_operand (operands[0], HImode))
4828 rtx aligned_mem, bitnum;
4830 get_aligned_mem (operands[0], &aligned_mem, &bitnum);
4832 emit_insn (gen_aligned_store (aligned_mem, operands[1], bitnum,
4833 gen_rtx_REG (SImode, REGNO (operands[2])),
4834 gen_rtx_REG (SImode,
4835 REGNO (operands[2]) + 1)));
4839 rtx addr = get_unaligned_address (operands[0], 0);
4840 rtx scratch1 = gen_rtx_REG (DImode, REGNO (operands[2]));
4841 rtx scratch2 = gen_rtx_REG (DImode, REGNO (operands[2]) + 1);
4842 rtx scratch3 = scratch1;
4845 if (GET_CODE (addr) == REG)
4848 seq = gen_unaligned_storehi (addr, operands[1], scratch1,
4849 scratch2, scratch3);
4850 alpha_set_memflags (seq, operands[0]);
4857 ;; Bit field extract patterns which use ext[wlq][lh]
4859 (define_expand "extv"
4860 [(set (match_operand:DI 0 "register_operand" "")
4861 (sign_extract:DI (match_operand:QI 1 "memory_operand" "")
4862 (match_operand:DI 2 "immediate_operand" "")
4863 (match_operand:DI 3 "immediate_operand" "")))]
4867 /* We can do 16, 32 and 64 bit fields, if aligned on byte boundaries. */
4868 if (INTVAL (operands[3]) % 8 != 0
4869 || (INTVAL (operands[2]) != 16
4870 && INTVAL (operands[2]) != 32
4871 && INTVAL (operands[2]) != 64))
4874 /* From mips.md: extract_bit_field doesn't verify that our source
4875 matches the predicate, so we force it to be a MEM here. */
4876 if (GET_CODE (operands[1]) != MEM)
4879 alpha_expand_unaligned_load (operands[0], operands[1],
4880 INTVAL (operands[2]) / 8,
4881 INTVAL (operands[3]) / 8, 1);
4885 (define_expand "extzv"
4886 [(set (match_operand:DI 0 "register_operand" "")
4887 (zero_extract:DI (match_operand:DI 1 "general_operand" "")
4888 (match_operand:DI 2 "immediate_operand" "")
4889 (match_operand:DI 3 "immediate_operand" "")))]
4893 /* We can do 8, 16, 32 and 64 bit fields, if aligned on byte boundaries. */
4894 if (INTVAL (operands[3]) % 8 != 0
4895 || (INTVAL (operands[2]) != 8
4896 && INTVAL (operands[2]) != 16
4897 && INTVAL (operands[2]) != 32
4898 && INTVAL (operands[2]) != 64))
4901 if (GET_CODE (operands[1]) == MEM)
4903 /* Fail 8 bit fields, falling back on a simple byte load. */
4904 if (INTVAL (operands[2]) == 8)
4907 alpha_expand_unaligned_load (operands[0], operands[1],
4908 INTVAL (operands[2]) / 8,
4909 INTVAL (operands[3]) / 8, 0);
4914 (define_expand "insv"
4915 [(set (zero_extract:DI (match_operand:QI 0 "memory_operand" "")
4916 (match_operand:DI 1 "immediate_operand" "")
4917 (match_operand:DI 2 "immediate_operand" ""))
4918 (match_operand:DI 3 "register_operand" ""))]
4922 /* We can do 16, 32 and 64 bit fields, if aligned on byte boundaries. */
4923 if (INTVAL (operands[2]) % 8 != 0
4924 || (INTVAL (operands[1]) != 16
4925 && INTVAL (operands[1]) != 32
4926 && INTVAL (operands[1]) != 64))
4929 /* From mips.md: store_bit_field doesn't verify that our source
4930 matches the predicate, so we force it to be a MEM here. */
4931 if (GET_CODE (operands[0]) != MEM)
4934 alpha_expand_unaligned_store (operands[0], operands[3],
4935 INTVAL (operands[1]) / 8,
4936 INTVAL (operands[2]) / 8);
4942 ;; Block move/clear, see alpha.c for more details.
4943 ;; Argument 0 is the destination
4944 ;; Argument 1 is the source
4945 ;; Argument 2 is the length
4946 ;; Argument 3 is the alignment
4948 (define_expand "movstrqi"
4949 [(parallel [(set (match_operand:BLK 0 "general_operand" "")
4950 (match_operand:BLK 1 "general_operand" ""))
4951 (use (match_operand:DI 2 "immediate_operand" ""))
4952 (use (match_operand:DI 3 "immediate_operand" ""))])]
4956 if (alpha_expand_block_move (operands))
4962 (define_expand "clrstrqi"
4963 [(parallel [(set (match_operand:BLK 0 "general_operand" "")
4965 (use (match_operand:DI 1 "immediate_operand" ""))
4966 (use (match_operand:DI 2 "immediate_operand" ""))])]
4970 if (alpha_expand_block_clear (operands))
4976 ;; Subroutine of stack space allocation. Perform a stack probe.
4977 (define_expand "probe_stack"
4978 [(set (match_dup 1) (match_operand:DI 0 "const_int_operand" ""))]
4982 operands[1] = gen_rtx_MEM (DImode, plus_constant (stack_pointer_rtx,
4983 INTVAL (operands[0])));
4984 MEM_VOLATILE_P (operands[1]) = 1;
4986 operands[0] = const0_rtx;
4989 ;; This is how we allocate stack space. If we are allocating a
4990 ;; constant amount of space and we know it is less than 4096
4991 ;; bytes, we need do nothing.
4993 ;; If it is more than 4096 bytes, we need to probe the stack
4995 (define_expand "allocate_stack"
4997 (plus:DI (reg:DI 30)
4998 (match_operand:DI 1 "reg_or_cint_operand" "")))
4999 (set (match_operand:DI 0 "register_operand" "=r")
5004 if (GET_CODE (operands[1]) == CONST_INT
5005 && INTVAL (operands[1]) < 32768)
5007 if (INTVAL (operands[1]) >= 4096)
5009 /* We do this the same way as in the prologue and generate explicit
5010 probes. Then we update the stack by the constant. */
5014 emit_insn (gen_probe_stack (GEN_INT (- probed)));
5015 while (probed + 8192 < INTVAL (operands[1]))
5016 emit_insn (gen_probe_stack (GEN_INT (- (probed += 8192))));
5018 if (probed + 4096 < INTVAL (operands[1]))
5019 emit_insn (gen_probe_stack (GEN_INT (- INTVAL(operands[1]))));
5022 operands[1] = GEN_INT (- INTVAL (operands[1]));
5023 operands[2] = virtual_stack_dynamic_rtx;
5028 rtx loop_label = gen_label_rtx ();
5029 rtx want = gen_reg_rtx (Pmode);
5030 rtx tmp = gen_reg_rtx (Pmode);
5033 emit_insn (gen_subdi3 (want, stack_pointer_rtx,
5034 force_reg (Pmode, operands[1])));
5035 emit_insn (gen_adddi3 (tmp, stack_pointer_rtx, GEN_INT (-4096)));
5037 if (GET_CODE (operands[1]) != CONST_INT)
5039 out_label = gen_label_rtx ();
5040 emit_insn (gen_cmpdi (want, tmp));
5041 emit_jump_insn (gen_bgeu (out_label));
5044 emit_label (loop_label);
5045 memref = gen_rtx_MEM (DImode, tmp);
5046 MEM_VOLATILE_P (memref) = 1;
5047 emit_move_insn (memref, const0_rtx);
5048 emit_insn (gen_adddi3 (tmp, tmp, GEN_INT(-8192)));
5049 emit_insn (gen_cmpdi (tmp, want));
5050 emit_jump_insn (gen_bgtu (loop_label));
5052 gen_rtx_USE (VOIDmode, tmp);
5054 memref = gen_rtx_MEM (DImode, want);
5055 MEM_VOLATILE_P (memref) = 1;
5056 emit_move_insn (memref, const0_rtx);
5059 emit_label (out_label);
5061 emit_move_insn (stack_pointer_rtx, want);
5062 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
5067 ;; This is used by alpha_expand_prolog to do the same thing as above,
5068 ;; except we cannot at that time generate new basic blocks, so we hide
5069 ;; the loop in this one insn.
5071 (define_insn "prologue_stack_probe_loop"
5072 [(unspec_volatile [(match_operand 0 "register_operand" "r")
5073 (match_operand 1 "register_operand" "r")] 5)]
5077 static int label_no;
5078 int count_regno = REGNO (operands[0]);
5079 int ptr_regno = REGNO (operands[1]);
5082 /* Ho hum, output the hard way to get the label at the beginning of
5083 the line. Wish there were a magic char you could get
5084 asm_output_printf to do that. Then we could use %= as well and
5085 get rid of the label_no bits here too. */
5087 ASM_GENERATE_INTERNAL_LABEL (label, \"LSC\", label_no);
5088 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, \"LSC\", label_no++);
5090 fprintf (asm_out_file, \"\\tstq $31,-8192($%d)\\n\", ptr_regno);
5091 fprintf (asm_out_file, \"\\tsubq $%d,1,$%d\\n\", count_regno, count_regno);
5092 fprintf (asm_out_file, \"\\tlda $%d,-8192($%d)\\n\", ptr_regno, ptr_regno);
5093 fprintf (asm_out_file, \"\\tbne $%d,\", count_regno);
5094 assemble_name (asm_out_file, label);
5095 putc ('\\n', asm_out_file);
5099 [(set_attr "length" "16")])
5101 (define_expand "prologue"
5102 [(clobber (const_int 0))]
5104 "alpha_expand_prologue (); DONE;")
5106 (define_insn "init_fp"
5107 [(set (match_operand:DI 0 "register_operand" "r")
5108 (match_operand:DI 1 "register_operand" "r"))
5109 (clobber (mem:BLK (match_operand:DI 2 "register_operand" "r")))]
5113 (define_expand "epilogue"
5114 [(clobber (const_int 0))]
5116 "alpha_expand_epilogue (); DONE;")
5118 (define_expand "builtin_longjmp"
5119 [(unspec_volatile [(match_operand 0 "register_operand" "r")] 3)]
5120 "! TARGET_OPEN_VMS && ! TARGET_WINDOWS_NT"
5123 /* The elements of the buffer are, in order: */
5124 rtx fp = gen_rtx_MEM (Pmode, operands[0]);
5125 rtx lab = gen_rtx_MEM (Pmode, plus_constant (operands[0], 8));
5126 rtx stack = gen_rtx_MEM (Pmode, plus_constant (operands[0], 16));
5127 rtx pv = gen_rtx_REG (Pmode, 27);
5129 /* This bit is the same as expand_builtin_longjmp. */
5130 emit_move_insn (hard_frame_pointer_rtx, fp);
5131 emit_move_insn (pv, lab);
5132 emit_stack_restore (SAVE_NONLOCAL, stack, NULL_RTX);
5133 emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
5134 emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
5136 /* Load the label we are jumping through into $27 so that we know
5137 where to look for it when we get back to setjmp's function for
5138 restoring the gp. */
5139 emit_indirect_jump (pv);
5142 (define_insn "builtin_setjmp_receiver"
5143 [(unspec_volatile [(match_operand 0 "" "")] 2)]
5144 "! TARGET_OPEN_VMS && ! TARGET_WINDOWS_NT && TARGET_AS_CAN_SUBTRACT_LABELS"
5145 "\\n$LSJ%=:\;ldgp $29,$LSJ%=-%l0($27)"
5146 [(set_attr "length" "8")])
5149 [(unspec_volatile [(match_operand 0 "" "")] 2)]
5150 "! TARGET_OPEN_VMS && ! TARGET_WINDOWS_NT"
5151 "br $27,$LSJ%=\\n$LSJ%=:\;ldgp $29,0($27)"
5152 [(set_attr "length" "12")])
5154 (define_expand "nonlocal_goto_receiver"
5155 [(unspec_volatile [(const_int 0)] 1)
5156 (set (reg:DI 27) (mem:DI (reg:DI 29)))
5157 (unspec_volatile [(const_int 0)] 1)
5162 (define_insn "arg_home"
5163 [(unspec [(const_int 0)] 0)
5178 (clobber (mem:BLK (const_int 0)))
5179 (clobber (reg:DI 24))
5180 (clobber (reg:DI 25))
5181 (clobber (reg:DI 0))]
5183 "lda $0,OTS$HOME_ARGS\;ldq $0,8($0)\;jsr $0,OTS$HOME_ARGS"
5184 [(set_attr "length" "16")])
5186 ;; Close the trap shadow of preceeding instructions. This is generated
5189 (define_insn "trapb"
5190 [(unspec_volatile [(const_int 0)] 4)]
5193 [(set_attr "type" "misc")])
5195 ;; Peepholes go at the end.
5197 ;; Optimize sign-extension of SImode loads. This shows up in the wake of
5198 ;; reload when converting fp->int.
5200 ;; ??? What to do now that we actually care about the packing and
5201 ;; alignment of instructions? Perhaps reload can be enlightened, or
5202 ;; the peephole pass moved up after reload but before sched2?
5205 ; [(set (match_operand:SI 0 "register_operand" "=r")
5206 ; (match_operand:SI 1 "memory_operand" "m"))
5207 ; (set (match_operand:DI 2 "register_operand" "=r")
5208 ; (sign_extend:DI (match_dup 0)))]
5209 ; "dead_or_set_p (insn, operands[0])"
5213 ; [(set (match_operand:SI 0 "register_operand" "=r")
5214 ; (match_operand:SI 1 "hard_fp_register_operand" "f"))
5215 ; (set (match_operand:DI 2 "register_operand" "=r")
5216 ; (sign_extend:DI (match_dup 0)))]
5217 ; "TARGET_CIX && dead_or_set_p (insn, operands[0])"