OSDN Git Service

* config/alpha/alpha.md (trap): New.
[pf3gnuchains/gcc-fork.git] / gcc / config / alpha / alpha.md
1 ;; Machine description for DEC Alpha for GNU C compiler
2 ;; Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
3 ;; 2000, 2001 Free Software Foundation, Inc.
4 ;; Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu)
5 ;;
6 ;; This file is part of GNU CC.
7 ;;
8 ;; GNU CC is free software; you can redistribute it and/or modify
9 ;; it under the terms of the GNU General Public License as published by
10 ;; the Free Software Foundation; either version 2, or (at your option)
11 ;; any later version.
12 ;;
13 ;; GNU CC is distributed in the hope that it will be useful,
14 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
15 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 ;; GNU General Public License for more details.
17 ;;
18 ;; You should have received a copy of the GNU General Public License
19 ;; along with GNU CC; see the file COPYING.  If not, write to
20 ;; the Free Software Foundation, 59 Temple Place - Suite 330,
21 ;; Boston, MA 02111-1307, USA.
22
23 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
24
25 ;; Uses of UNSPEC in this file:
26
27 (define_constants
28   [(UNSPEC_ARG_HOME     0)
29    (UNSPEC_CTTZ         1)
30    (UNSPEC_INSXH        2)
31    (UNSPEC_MSKXH        3)
32    (UNSPEC_CVTQL        4)
33    (UNSPEC_NT_LDA       5)
34    (UNSPEC_UMK_LAUM     6)
35    (UNSPEC_UMK_LALM     7)
36    (UNSPEC_UMK_LAL      8)
37    (UNSPEC_UMK_LOAD_CIW 9)
38    (UNSPEC_LDGP2        10)
39    (UNSPEC_LITERAL      11)
40    (UNSPEC_LITUSE       12)
41    (UNSPEC_SIBCALL      13)
42   ])
43
44 ;; UNSPEC_VOLATILE:
45
46 (define_constants
47   [(UNSPECV_IMB         0)
48    (UNSPECV_BLOCKAGE    1)
49    (UNSPECV_SETJMPR     2)      ; builtin_setjmp_receiver
50    (UNSPECV_LONGJMP     3)      ; builtin_longjmp
51    (UNSPECV_TRAPB       4)
52    (UNSPECV_PSPL        5)      ; prologue_stack_probe_loop
53    (UNSPECV_REALIGN     6)
54    (UNSPECV_EHR         7)      ; exception_receiver
55    (UNSPECV_MCOUNT      8)
56    (UNSPECV_FORCE_MOV   9)
57    (UNSPECV_LDGP1       10)
58    (UNSPECV_PLDGP2      11)     ; prologue ldgp
59   ])
60
61 ;; Where necessary, the suffixes _le and _be are used to distinguish between
62 ;; little-endian and big-endian patterns.
63 ;;
64 ;; Note that the Unicos/Mk assembler does not support the following
65 ;; opcodes: mov, fmov, nop, fnop, unop.
66 \f
67 ;; Processor type -- this attribute must exactly match the processor_type
68 ;; enumeration in alpha.h.
69
70 (define_attr "cpu" "ev4,ev5,ev6"
71   (const (symbol_ref "alpha_cpu")))
72
73 ;; Define an insn type attribute.  This is used in function unit delay
74 ;; computations, among other purposes.  For the most part, we use the names
75 ;; defined in the EV4 documentation, but add a few that we have to know about
76 ;; separately.
77
78 (define_attr "type"
79   "ild,fld,ldsym,ist,fst,ibr,fbr,jsr,iadd,ilog,shift,icmov,fcmov,icmp,imul,\
80 fadd,fmul,fcpys,fdiv,fsqrt,misc,mvi,ftoi,itof,multi"
81   (const_string "iadd"))
82
83 ;; Describe a user's asm statement.
84 (define_asm_attributes
85   [(set_attr "type" "multi")])
86
87 ;; Define the operand size an insn operates on.  Used primarily by mul
88 ;; and div operations that have size dependent timings.
89
90 (define_attr "opsize" "si,di,udi"
91   (const_string "di"))
92
93 ;; The TRAP attribute marks instructions that may generate traps
94 ;; (which are imprecise and may need a trapb if software completion
95 ;; is desired).
96
97 (define_attr "trap" "no,yes"
98   (const_string "no"))
99
100 ;; The ROUND_SUFFIX attribute marks which instructions require a
101 ;; rounding-mode suffix.  The value NONE indicates no suffix,
102 ;; the value NORMAL indicates a suffix controled by alpha_fprm.
103
104 (define_attr "round_suffix" "none,normal,c"
105   (const_string "none"))
106
107 ;; The TRAP_SUFFIX attribute marks instructions requiring a trap-mode suffix:
108 ;;   NONE       no suffix
109 ;;   SU         accepts only /su (cmpt et al)
110 ;;   SUI        accepts only /sui (cvtqt and cvtqs)
111 ;;   V_SV       accepts /v and /sv (cvtql only)
112 ;;   V_SV_SVI   accepts /v, /sv and /svi (cvttq only)
113 ;;   U_SU_SUI   accepts /u, /su and /sui (most fp instructions)
114 ;;
115 ;; The actual suffix emitted is controled by alpha_fptm.
116
117 (define_attr "trap_suffix" "none,su,sui,v_sv,v_sv_svi,u_su_sui"
118   (const_string "none"))
119
120 ;; The length of an instruction sequence in bytes.
121
122 (define_attr "length" ""
123   (const_int 4))
124 \f
125 ;; On EV4 there are two classes of resources to consider: resources needed
126 ;; to issue, and resources needed to execute.  IBUS[01] are in the first
127 ;; category.  ABOX, BBOX, EBOX, FBOX, IMUL & FDIV make up the second.
128 ;; (There are a few other register-like resources, but ...)
129
130 ; First, describe all of the issue constraints with single cycle delays.
131 ; All insns need a bus, but all except loads require one or the other.
132 (define_function_unit "ev4_ibus0" 1 0
133   (and (eq_attr "cpu" "ev4")
134        (eq_attr "type" "fst,fbr,iadd,imul,ilog,shift,icmov,icmp"))
135   1 1)
136
137 (define_function_unit "ev4_ibus1" 1 0
138   (and (eq_attr "cpu" "ev4")
139        (eq_attr "type" "ist,ibr,jsr,fadd,fcmov,fcpys,fmul,fdiv,misc"))
140   1 1)
141
142 ; Memory delivers its result in three cycles.  Actually return one and
143 ; take care of this in adjust_cost, since we want to handle user-defined
144 ; memory latencies.
145 (define_function_unit "ev4_abox" 1 0
146   (and (eq_attr "cpu" "ev4")
147        (eq_attr "type" "ild,fld,ldsym,ist,fst"))
148   1 1)
149
150 ; Branches have no delay cost, but do tie up the unit for two cycles.
151 (define_function_unit "ev4_bbox" 1 1
152   (and (eq_attr "cpu" "ev4")
153        (eq_attr "type" "ibr,fbr,jsr"))
154   2 2)
155
156 ; Arithmetic insns are normally have their results available after
157 ; two cycles.  There are a number of exceptions.  They are encoded in
158 ; ADJUST_COST.  Some of the other insns have similar exceptions.
159 (define_function_unit "ev4_ebox" 1 0
160   (and (eq_attr "cpu" "ev4")
161        (eq_attr "type" "iadd,ilog,shift,icmov,icmp,misc"))
162   2 1)
163
164 (define_function_unit "imul" 1 0
165   (and (eq_attr "cpu" "ev4")
166        (and (eq_attr "type" "imul")
167             (eq_attr "opsize" "si")))
168   21 19)
169
170 (define_function_unit "imul" 1 0
171   (and (eq_attr "cpu" "ev4")
172        (and (eq_attr "type" "imul")
173             (eq_attr "opsize" "!si")))
174   23 21)
175
176 (define_function_unit "ev4_fbox" 1 0
177   (and (eq_attr "cpu" "ev4")
178        (eq_attr "type" "fadd,fmul,fcpys,fcmov"))
179   6 1)
180
181 (define_function_unit "fdiv" 1 0
182   (and (eq_attr "cpu" "ev4")
183        (and (eq_attr "type" "fdiv")
184             (eq_attr "opsize" "si")))
185   34 30)
186
187 (define_function_unit "fdiv" 1 0
188   (and (eq_attr "cpu" "ev4")
189        (and (eq_attr "type" "fdiv")
190             (eq_attr "opsize" "di")))
191   63 59)
192 \f
193 ;; EV5 scheduling.  EV5 can issue 4 insns per clock.
194 ;;
195 ;; EV5 has two asymetric integer units.  Model this with E0 & E1 along
196 ;; with the combined resource EBOX.
197
198 (define_function_unit "ev5_ebox" 2 0
199   (and (eq_attr "cpu" "ev5")
200        (eq_attr "type" "!fbr,fcmov,fadd,fmul,fcpys,fdiv"))
201   1 1)
202
203 ; Memory takes at least 2 clocks.  Return one from here and fix up with
204 ; user-defined latencies in adjust_cost.
205 (define_function_unit "ev5_ebox" 2 0
206   (and (eq_attr "cpu" "ev5")
207        (eq_attr "type" "ild,fld,ldsym"))
208   1 1)
209
210 ; Loads can dual issue with one another, but loads and stores do not mix.
211 (define_function_unit "ev5_e0" 1 0
212   (and (eq_attr "cpu" "ev5")
213        (eq_attr "type" "ild,fld,ldsym"))
214   1 1
215   [(eq_attr "type" "ist,fst")])
216
217 ; Stores, shifts, multiplies can only issue to E0
218 (define_function_unit "ev5_e0" 1 0
219   (and (eq_attr "cpu" "ev5")
220        (eq_attr "type" "ist,fst,shift,imul"))
221   1 1)
222
223 ; Motion video insns also issue only to E0, and take two ticks.
224 (define_function_unit "ev5_e0" 1 0
225   (and (eq_attr "cpu" "ev5")
226        (eq_attr "type" "mvi"))
227   2 1)
228
229 ; Conditional moves always take 2 ticks.
230 (define_function_unit "ev5_ebox" 2 0
231   (and (eq_attr "cpu" "ev5")
232        (eq_attr "type" "icmov"))
233   2 1)
234
235 ; Branches can only issue to E1
236 (define_function_unit "ev5_e1" 1 0
237   (and (eq_attr "cpu" "ev5")
238        (eq_attr "type" "ibr,jsr"))
239   1 1)
240
241 ; Multiplies also use the integer multiplier.
242 ; ??? How to: "No instruction can be issued to pipe E0 exactly two
243 ; cycles before an integer multiplication completes."
244 (define_function_unit "imul" 1 0
245   (and (eq_attr "cpu" "ev5")
246        (and (eq_attr "type" "imul")
247             (eq_attr "opsize" "si")))
248   8 4)
249
250 (define_function_unit "imul" 1 0
251   (and (eq_attr "cpu" "ev5")
252        (and (eq_attr "type" "imul")
253             (eq_attr "opsize" "di")))
254   12 8)
255
256 (define_function_unit "imul" 1 0
257   (and (eq_attr "cpu" "ev5")
258        (and (eq_attr "type" "imul")
259             (eq_attr "opsize" "udi")))
260   14 8)
261
262 ;; Similarly for the FPU we have two asymetric units.  But fcpys can issue
263 ;; on either so we have to play the game again.
264
265 (define_function_unit "ev5_fbox" 2 0
266   (and (eq_attr "cpu" "ev5")
267        (eq_attr "type" "fadd,fcmov,fmul,fcpys,fbr,fdiv"))
268   4 1)
269
270 (define_function_unit "ev5_fm" 1 0
271   (and (eq_attr "cpu" "ev5")
272        (eq_attr "type" "fmul"))
273   4 1)
274
275 ; Add and cmov as you would expect; fbr never produces a result;
276 ; fdiv issues through fa to the divider,
277 (define_function_unit "ev5_fa" 1 0
278   (and (eq_attr "cpu" "ev5")
279        (eq_attr "type" "fadd,fcmov,fbr,fdiv"))
280   4 1)
281
282 ; ??? How to: "No instruction can be issued to pipe FA exactly five
283 ; cycles before a floating point divide completes."
284 (define_function_unit "fdiv" 1 0
285   (and (eq_attr "cpu" "ev5")
286        (and (eq_attr "type" "fdiv")
287             (eq_attr "opsize" "si")))
288   15 15)                                ; 15 to 31 data dependent
289
290 (define_function_unit "fdiv" 1 0
291   (and (eq_attr "cpu" "ev5")
292        (and (eq_attr "type" "fdiv")
293             (eq_attr "opsize" "di")))
294   22 22)                                ; 22 to 60 data dependent
295 \f
296 ;; EV6 scheduling.  EV6 can issue 4 insns per clock.
297 ;;
298 ;; EV6 has two symmetric pairs ("clusters") of two asymetric integer units
299 ;; ("upper" and "lower"), yielding pipe names U0, U1, L0, L1.
300
301 ;; Conditional moves decompose into two independent primitives, each
302 ;; taking one cycle.  Since ev6 is out-of-order, we can't see anything
303 ;; but two cycles.
304 (define_function_unit "ev6_ebox" 4 0
305   (and (eq_attr "cpu" "ev6")
306        (eq_attr "type" "icmov"))
307   2 1)
308
309 (define_function_unit "ev6_ebox" 4 0
310   (and (eq_attr "cpu" "ev6")
311        (eq_attr "type" "!fbr,fcmov,fadd,fmul,fcpys,fdiv,fsqrt"))
312   1 1)
313
314 ;; Integer loads take at least 3 clocks, and only issue to lower units.
315 ;; Return one from here and fix up with user-defined latencies in adjust_cost.
316 (define_function_unit "ev6_l" 2 0
317   (and (eq_attr "cpu" "ev6")
318        (eq_attr "type" "ild,ldsym,ist,fst"))
319   1 1)
320
321 ;; FP loads take at least 4 clocks.  Return two from here...
322 (define_function_unit "ev6_l" 2 0
323   (and (eq_attr "cpu" "ev6")
324        (eq_attr "type" "fld"))
325   2 1)
326
327 ;; Motion video insns also issue only to U0, and take three ticks.
328 (define_function_unit "ev6_u0" 1 0
329   (and (eq_attr "cpu" "ev6")
330        (eq_attr "type" "mvi"))
331   3 1)
332
333 (define_function_unit "ev6_u" 2 0
334   (and (eq_attr "cpu" "ev6")
335        (eq_attr "type" "mvi"))
336   3 1)
337
338 ;; Shifts issue to either upper pipe.
339 (define_function_unit "ev6_u" 2 0
340   (and (eq_attr "cpu" "ev6")
341        (eq_attr "type" "shift"))
342   1 1)
343
344 ;; Multiplies issue only to U1, and all take 7 ticks.
345 ;; Rather than create a new function unit just for U1, reuse IMUL
346 (define_function_unit "imul" 1 0
347   (and (eq_attr "cpu" "ev6")
348        (eq_attr "type" "imul"))
349   7 1)
350
351 (define_function_unit "ev6_u" 2 0
352   (and (eq_attr "cpu" "ev6")
353        (eq_attr "type" "imul"))
354   7 1)
355
356 ;; Branches issue to either upper pipe
357 (define_function_unit "ev6_u" 2 0
358   (and (eq_attr "cpu" "ev6")
359        (eq_attr "type" "ibr"))
360   3 1)
361
362 ;; Calls only issue to L0.
363 (define_function_unit "ev6_l0" 1 0
364   (and (eq_attr "cpu" "ev6")
365        (eq_attr "type" "jsr"))
366   1 1)
367
368 (define_function_unit "ev6_l" 2 0
369   (and (eq_attr "cpu" "ev6")
370        (eq_attr "type" "jsr"))
371   1 1)
372
373 ;; Ftoi/itof only issue to lower pipes
374 (define_function_unit "ev6_l" 2 0
375   (and (eq_attr "cpu" "ev6")
376        (eq_attr "type" "ftoi"))
377   3 1)
378
379 (define_function_unit "ev6_l" 2 0
380   (and (eq_attr "cpu" "ev6")
381        (eq_attr "type" "itof"))
382   4 1)
383
384 ;; For the FPU we are very similar to EV5, except there's no insn that
385 ;; can issue to fm & fa, so we get to leave that out.
386
387 (define_function_unit "ev6_fm" 1 0
388   (and (eq_attr "cpu" "ev6")
389        (eq_attr "type" "fmul"))
390   4 1)
391
392 (define_function_unit "ev6_fa" 1 0
393   (and (eq_attr "cpu" "ev6")
394        (eq_attr "type" "fadd,fcpys,fbr,fdiv,fsqrt"))
395   4 1)
396
397 (define_function_unit "ev6_fa" 1 0
398   (and (eq_attr "cpu" "ev6")
399        (eq_attr "type" "fcmov"))
400   8 1)
401
402 (define_function_unit "fdiv" 1 0
403   (and (eq_attr "cpu" "ev6")
404        (and (eq_attr "type" "fdiv")
405             (eq_attr "opsize" "si")))
406   12 10)
407
408 (define_function_unit "fdiv" 1 0
409   (and (eq_attr "cpu" "ev6")
410        (and (eq_attr "type" "fdiv")
411             (eq_attr "opsize" "di")))
412   15 13)
413
414 (define_function_unit "fsqrt" 1 0
415   (and (eq_attr "cpu" "ev6")
416        (and (eq_attr "type" "fsqrt")
417             (eq_attr "opsize" "si")))
418   16 14)
419
420 (define_function_unit "fsqrt" 1 0
421   (and (eq_attr "cpu" "ev6")
422        (and (eq_attr "type" "fsqrt")
423             (eq_attr "opsize" "di")))
424   32 30)
425
426 ; ??? The FPU communicates with memory and the integer register file
427 ; via two fp store units.  We need a slot in the fst immediately, and
428 ; a slot in LOW after the operand data is ready.  At which point the
429 ; data may be moved either to the store queue or the integer register
430 ; file and the insn retired.
431
432 \f
433 ;; First define the arithmetic insns.  Note that the 32-bit forms also
434 ;; sign-extend.
435
436 ;; Handle 32-64 bit extension from memory to a floating point register
437 ;; specially, since this occurs frequently in int->double conversions.
438 ;;
439 ;; Note that while we must retain the =f case in the insn for reload's
440 ;; benefit, it should be eliminated after reload, so we should never emit
441 ;; code for that case.  But we don't reject the possibility.
442
443 (define_expand "extendsidi2"
444   [(set (match_operand:DI 0 "register_operand" "")
445         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
446   ""
447   "")
448
449 (define_insn "*extendsidi2_nofix"
450   [(set (match_operand:DI 0 "register_operand" "=r,r,*f,?*f")
451         (sign_extend:DI
452           (match_operand:SI 1 "nonimmediate_operand" "r,m,*f,m")))]
453   "! TARGET_FIX"
454   "@
455    addl %1,$31,%0
456    ldl %0,%1
457    cvtlq %1,%0
458    lds %0,%1\;cvtlq %0,%0"
459   [(set_attr "type" "iadd,ild,fadd,fld")
460    (set_attr "length" "*,*,*,8")])
461
462 (define_insn "*extendsidi2_fix"
463   [(set (match_operand:DI 0 "register_operand" "=r,r,r,?*f,?*f")
464         (sign_extend:DI
465           (match_operand:SI 1 "nonimmediate_operand" "r,m,*f,*f,m")))]
466   "TARGET_FIX"
467   "@
468    addl %1,$31,%0
469    ldl %0,%1
470    ftois %1,%0
471    cvtlq %1,%0
472    lds %0,%1\;cvtlq %0,%0"
473   [(set_attr "type" "iadd,ild,ftoi,fadd,fld")
474    (set_attr "length" "*,*,*,*,8")])
475
476 ;; Due to issues with CLASS_CANNOT_CHANGE_SIZE, we cannot use a subreg here.
477 (define_split
478   [(set (match_operand:DI 0 "hard_fp_register_operand" "")
479         (sign_extend:DI (match_operand:SI 1 "memory_operand" "")))]
480   "reload_completed"
481   [(set (match_dup 2) (match_dup 1))
482    (set (match_dup 0) (sign_extend:DI (match_dup 2)))]
483   "operands[2] = gen_rtx_REG (SImode, REGNO (operands[0]));")
484
485 ;; Optimize sign-extension of SImode loads.  This shows up in the wake of
486 ;; reload when converting fp->int.
487
488 (define_peephole2
489   [(set (match_operand:SI 0 "hard_int_register_operand" "")
490         (match_operand:SI 1 "memory_operand" ""))
491    (set (match_operand:DI 2 "hard_int_register_operand" "")
492         (sign_extend:DI (match_dup 0)))]
493   "true_regnum (operands[0]) == true_regnum (operands[2])
494    || peep2_reg_dead_p (2, operands[0])"
495   [(set (match_dup 2)
496         (sign_extend:DI (match_dup 1)))]
497   "")
498
499 (define_peephole2
500   [(set (match_operand:SI 0 "hard_int_register_operand" "")
501         (match_operand:SI 1 "hard_fp_register_operand" ""))
502    (set (match_operand:DI 2 "hard_int_register_operand" "")
503         (sign_extend:DI (match_dup 0)))]
504   "TARGET_FIX
505    && (true_regnum (operands[0]) == true_regnum (operands[2])
506        || peep2_reg_dead_p (2, operands[0]))"
507   [(set (match_dup 2)
508         (sign_extend:DI (match_dup 1)))]
509   "")
510
511 (define_peephole2
512   [(set (match_operand:DI 0 "hard_fp_register_operand" "")
513         (sign_extend:DI (match_operand:SI 1 "hard_fp_register_operand" "")))
514    (set (match_operand:DI 2 "hard_int_register_operand" "")
515         (match_dup 0))]
516   "TARGET_FIX && peep2_reg_dead_p (2, operands[0])"
517   [(set (match_dup 2)
518         (sign_extend:DI (match_dup 1)))]
519   "")
520
521 ;; Don't say we have addsi3 if optimizing.  This generates better code.  We
522 ;; have the anonymous addsi3 pattern below in case combine wants to make it.
523 (define_expand "addsi3"
524   [(set (match_operand:SI 0 "register_operand" "")
525         (plus:SI (match_operand:SI 1 "reg_or_0_operand" "")
526                  (match_operand:SI 2 "add_operand" "")))]
527   "! optimize"
528   "")
529
530 (define_insn "*addsi_internal"
531   [(set (match_operand:SI 0 "register_operand" "=r,r,r,r")
532         (plus:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ,rJ,rJ,rJ")
533                  (match_operand:SI 2 "add_operand" "rI,O,K,L")))]
534   ""
535   "@
536    addl %r1,%2,%0
537    subl %r1,%n2,%0
538    lda %0,%2(%r1)
539    ldah %0,%h2(%r1)")
540
541 (define_split
542   [(set (match_operand:SI 0 "register_operand" "")
543         (plus:SI (match_operand:SI 1 "register_operand" "")
544                  (match_operand:SI 2 "const_int_operand" "")))]
545   "! add_operand (operands[2], SImode)"
546   [(set (match_dup 0) (plus:SI (match_dup 1) (match_dup 3)))
547    (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 4)))]
548 {
549   HOST_WIDE_INT val = INTVAL (operands[2]);
550   HOST_WIDE_INT low = (val & 0xffff) - 2 * (val & 0x8000);
551   HOST_WIDE_INT rest = val - low;
552
553   operands[3] = GEN_INT (rest);
554   operands[4] = GEN_INT (low);
555 })
556
557 (define_insn "*addsi_se"
558   [(set (match_operand:DI 0 "register_operand" "=r,r")
559         (sign_extend:DI
560          (plus:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ,rJ")
561                   (match_operand:SI 2 "sext_add_operand" "rI,O"))))]
562   ""
563   "@
564    addl %r1,%2,%0
565    subl %r1,%n2,%0")
566
567 (define_insn "*addsi_se2"
568   [(set (match_operand:DI 0 "register_operand" "=r,r")
569         (sign_extend:DI
570          (subreg:SI (plus:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ")
571                              (match_operand:DI 2 "sext_add_operand" "rI,O"))
572                     0)))]
573   ""
574   "@
575    addl %r1,%2,%0
576    subl %r1,%n2,%0")
577
578 (define_split
579   [(set (match_operand:DI 0 "register_operand" "")
580         (sign_extend:DI
581          (plus:SI (match_operand:SI 1 "reg_not_elim_operand" "")
582                   (match_operand:SI 2 "const_int_operand" ""))))
583    (clobber (match_operand:SI 3 "reg_not_elim_operand" ""))]
584   "! sext_add_operand (operands[2], SImode) && INTVAL (operands[2]) > 0
585    && INTVAL (operands[2]) % 4 == 0"
586   [(set (match_dup 3) (match_dup 4))
587    (set (match_dup 0) (sign_extend:DI (plus:SI (mult:SI (match_dup 3)
588                                                         (match_dup 5))
589                                                (match_dup 1))))]
590 {
591   HOST_WIDE_INT val = INTVAL (operands[2]) / 4;
592   int mult = 4;
593
594   if (val % 2 == 0)
595     val /= 2, mult = 8;
596
597   operands[4] = GEN_INT (val);
598   operands[5] = GEN_INT (mult);
599 })
600
601 (define_split
602   [(set (match_operand:DI 0 "register_operand" "")
603         (sign_extend:DI
604          (plus:SI (match_operator:SI 1 "comparison_operator"
605                                      [(match_operand 2 "" "")
606                                       (match_operand 3 "" "")])
607                   (match_operand:SI 4 "add_operand" ""))))
608    (clobber (match_operand:DI 5 "register_operand" ""))]
609   ""
610   [(set (match_dup 5) (match_dup 6))
611    (set (match_dup 0) (sign_extend:DI (plus:SI (match_dup 7) (match_dup 4))))]
612 {
613   operands[6] = gen_rtx_fmt_ee (GET_CODE (operands[1]), DImode,
614                                 operands[2], operands[3]);
615   operands[7] = gen_lowpart (SImode, operands[5]);
616 })
617
618 (define_insn "addvsi3"
619   [(set (match_operand:SI 0 "register_operand" "=r,r")
620         (plus:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ,rJ")
621                  (match_operand:SI 2 "sext_add_operand" "rI,O")))
622    (trap_if (ne (plus:DI (sign_extend:DI (match_dup 1))
623                          (sign_extend:DI (match_dup 2)))
624                 (sign_extend:DI (plus:SI (match_dup 1)
625                                          (match_dup 2))))
626             (const_int 0))]
627   ""
628   "@
629    addlv %r1,%2,%0
630    sublv %r1,%n2,%0")
631
632 (define_expand "adddi3"
633   [(set (match_operand:DI 0 "register_operand" "")
634         (plus:DI (match_operand:DI 1 "register_operand" "")
635                  (match_operand:DI 2 "add_operand" "")))]
636   ""
637   "")
638
639 (define_insn "*adddi_er_high_l"
640   [(set (match_operand:DI 0 "register_operand" "=r")
641         (plus:DI (match_operand:DI 1 "register_operand" "r")
642                  (high:DI (match_operand:DI 2 "local_symbolic_operand" ""))))]
643   "TARGET_EXPLICIT_RELOCS"
644   "ldah %0,%2(%1)\t\t!gprelhigh")
645
646 (define_split
647   [(set (match_operand:DI 0 "register_operand" "")
648         (high:DI (match_operand:DI 1 "local_symbolic_operand" "")))]
649   "TARGET_EXPLICIT_RELOCS && reload_completed"
650   [(set (match_dup 0)
651         (plus:DI (match_dup 2) (high:DI (match_dup 1))))]
652   "operands[2] = pic_offset_table_rtx;")
653
654 ;; We used to expend quite a lot of effort choosing addq/subq/lda.
655 ;; With complications like
656 ;;
657 ;;   The NT stack unwind code can't handle a subq to adjust the stack
658 ;;   (that's a bug, but not one we can do anything about).  As of NT4.0 SP3,
659 ;;   the exception handling code will loop if a subq is used and an
660 ;;   exception occurs.
661 ;;
662 ;;   The 19980616 change to emit prologues as RTL also confused some
663 ;;   versions of GDB, which also interprets prologues.  This has been
664 ;;   fixed as of GDB 4.18, but it does not harm to unconditionally
665 ;;   use lda here.
666 ;;
667 ;; and the fact that the three insns schedule exactly the same, it's
668 ;; just not worth the effort.
669
670 (define_insn "*adddi_internal"
671   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
672         (plus:DI (match_operand:DI 1 "register_operand" "%r,r,r")
673                  (match_operand:DI 2 "add_operand" "r,K,L")))]
674   ""
675   "@
676    addq %1,%2,%0
677    lda %0,%2(%1)
678    ldah %0,%h2(%1)")
679
680 ;; ??? Allow large constants when basing off the frame pointer or some
681 ;; virtual register that may eliminate to the frame pointer.  This is
682 ;; done because register elimination offsets will change the hi/lo split,
683 ;; and if we split before reload, we will require additional instructions.
684
685 (define_insn "*adddi_fp_hack"
686   [(set (match_operand:DI 0 "register_operand" "=r")
687         (plus:DI (match_operand:DI 1 "reg_no_subreg_operand" "r")
688                  (match_operand:DI 2 "const_int_operand" "n")))]
689   "NONSTRICT_REG_OK_FP_BASE_P (operands[1])
690    && INTVAL (operands[2]) >= 0
691    /* This is the largest constant an lda+ldah pair can add, minus
692       an upper bound on the displacement between SP and AP during
693       register elimination.  See INITIAL_ELIMINATION_OFFSET.  */
694    && INTVAL (operands[2])
695         < (0x7fff8000
696            - FIRST_PSEUDO_REGISTER * UNITS_PER_WORD
697            - ALPHA_ROUND(current_function_outgoing_args_size)
698            - (ALPHA_ROUND (get_frame_size ()
699                            + max_reg_num () * UNITS_PER_WORD
700                            + current_function_pretend_args_size)
701               - current_function_pretend_args_size))"
702   "#")
703
704 ;; Don't do this if we are adjusting SP since we don't want to do it
705 ;; in two steps.  Don't split FP sources for the reason listed above.
706 (define_split
707   [(set (match_operand:DI 0 "register_operand" "")
708         (plus:DI (match_operand:DI 1 "register_operand" "")
709                  (match_operand:DI 2 "const_int_operand" "")))]
710   "! add_operand (operands[2], DImode)
711    && operands[0] != stack_pointer_rtx
712    && operands[1] != frame_pointer_rtx
713    && operands[1] != arg_pointer_rtx"
714   [(set (match_dup 0) (plus:DI (match_dup 1) (match_dup 3)))
715    (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 4)))]
716 {
717   HOST_WIDE_INT val = INTVAL (operands[2]);
718   HOST_WIDE_INT low = (val & 0xffff) - 2 * (val & 0x8000);
719   HOST_WIDE_INT rest = val - low;
720
721   operands[4] = GEN_INT (low);
722   if (CONST_OK_FOR_LETTER_P (rest, 'L'))
723     operands[3] = GEN_INT (rest);
724   else if (! no_new_pseudos)
725     {
726       operands[3] = gen_reg_rtx (DImode);
727       emit_move_insn (operands[3], operands[2]);
728       emit_insn (gen_adddi3 (operands[0], operands[1], operands[3]));
729       DONE;
730     }
731   else
732     FAIL;
733 })
734
735 (define_insn "*saddl"
736   [(set (match_operand:SI 0 "register_operand" "=r,r")
737         (plus:SI (mult:SI (match_operand:SI 1 "reg_not_elim_operand" "r,r")
738                           (match_operand:SI 2 "const48_operand" "I,I"))
739                  (match_operand:SI 3 "sext_add_operand" "rI,O")))]
740   ""
741   "@
742    s%2addl %1,%3,%0
743    s%2subl %1,%n3,%0")
744
745 (define_insn "*saddl_se"
746   [(set (match_operand:DI 0 "register_operand" "=r,r")
747         (sign_extend:DI
748          (plus:SI (mult:SI (match_operand:SI 1 "reg_not_elim_operand" "r,r")
749                            (match_operand:SI 2 "const48_operand" "I,I"))
750                   (match_operand:SI 3 "sext_add_operand" "rI,O"))))]
751   ""
752   "@
753    s%2addl %1,%3,%0
754    s%2subl %1,%n3,%0")
755
756 (define_split
757   [(set (match_operand:DI 0 "register_operand" "")
758         (sign_extend:DI
759          (plus:SI (mult:SI (match_operator:SI 1 "comparison_operator"
760                                               [(match_operand 2 "" "")
761                                                (match_operand 3 "" "")])
762                            (match_operand:SI 4 "const48_operand" ""))
763                   (match_operand:SI 5 "sext_add_operand" ""))))
764    (clobber (match_operand:DI 6 "reg_not_elim_operand" ""))]
765   ""
766   [(set (match_dup 6) (match_dup 7))
767    (set (match_dup 0)
768         (sign_extend:DI (plus:SI (mult:SI (match_dup 8) (match_dup 4))
769                                  (match_dup 5))))]
770 {
771   operands[7] = gen_rtx_fmt_ee (GET_CODE (operands[1]), DImode,
772                                 operands[2], operands[3]);
773   operands[8] = gen_lowpart (SImode, operands[6]);
774 })
775
776 (define_insn "*saddq"
777   [(set (match_operand:DI 0 "register_operand" "=r,r")
778         (plus:DI (mult:DI (match_operand:DI 1 "reg_not_elim_operand" "r,r")
779                           (match_operand:DI 2 "const48_operand" "I,I"))
780                  (match_operand:DI 3 "sext_add_operand" "rI,O")))]
781   ""
782   "@
783    s%2addq %1,%3,%0
784    s%2subq %1,%n3,%0")
785
786 (define_insn "addvdi3"
787   [(set (match_operand:DI 0 "register_operand" "=r,r")
788         (plus:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ")
789                  (match_operand:DI 2 "sext_add_operand" "rI,O")))
790    (trap_if (ne (plus:TI (sign_extend:TI (match_dup 1))
791                          (sign_extend:TI (match_dup 2)))
792                 (sign_extend:TI (plus:DI (match_dup 1)
793                                          (match_dup 2))))
794             (const_int 0))]
795   ""
796   "@
797    addqv %r1,%2,%0
798    subqv %r1,%n2,%0")
799
800 (define_insn "negsi2"
801   [(set (match_operand:SI 0 "register_operand" "=r")
802         (neg:SI (match_operand:SI 1 "reg_or_8bit_operand" "rI")))]
803   ""
804   "subl $31,%1,%0")
805
806 (define_insn "*negsi_se"
807   [(set (match_operand:DI 0 "register_operand" "=r")
808         (sign_extend:DI (neg:SI
809                          (match_operand:SI 1 "reg_or_8bit_operand" "rI"))))]
810   ""
811   "subl $31,%1,%0")
812
813 (define_insn "negvsi2"
814   [(set (match_operand:SI 0 "register_operand" "=r")
815         (neg:SI (match_operand:SI 1 "register_operand" "r")))
816    (trap_if (ne (neg:DI (sign_extend:DI (match_dup 1)))
817                 (sign_extend:DI (neg:SI (match_dup 1))))
818             (const_int 0))]
819   ""
820   "sublv $31,%1,%0")
821
822 (define_insn "negdi2"
823   [(set (match_operand:DI 0 "register_operand" "=r")
824         (neg:DI (match_operand:DI 1 "reg_or_8bit_operand" "rI")))]
825   ""
826   "subq $31,%1,%0")
827
828 (define_insn "negvdi2"
829   [(set (match_operand:DI 0 "register_operand" "=r")
830         (neg:DI (match_operand:DI 1 "register_operand" "r")))
831    (trap_if (ne (neg:TI (sign_extend:TI (match_dup 1)))
832                 (sign_extend:TI (neg:DI (match_dup 1))))
833             (const_int 0))]
834   ""
835   "subqv $31,%1,%0")
836
837 (define_expand "subsi3"
838   [(set (match_operand:SI 0 "register_operand" "")
839         (minus:SI (match_operand:SI 1 "reg_or_0_operand" "")
840                   (match_operand:SI 2 "reg_or_8bit_operand" "")))]
841   "! optimize"
842   "")
843
844 (define_insn "*subsi_internal"
845   [(set (match_operand:SI 0 "register_operand" "=r")
846         (minus:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
847                   (match_operand:SI 2 "reg_or_8bit_operand" "rI")))]
848   ""
849   "subl %r1,%2,%0")
850
851 (define_insn "*subsi_se"
852   [(set (match_operand:DI 0 "register_operand" "=r")
853         (sign_extend:DI (minus:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
854                                   (match_operand:SI 2 "reg_or_8bit_operand" "rI"))))]
855   ""
856   "subl %r1,%2,%0")
857
858 (define_insn "*subsi_se2"
859   [(set (match_operand:DI 0 "register_operand" "=r")
860         (sign_extend:DI
861          (subreg:SI (minus:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
862                               (match_operand:DI 2 "reg_or_8bit_operand" "rI"))
863                     0)))]
864   ""
865   "subl %r1,%2,%0")
866
867 (define_insn "subvsi3"
868   [(set (match_operand:SI 0 "register_operand" "=r")
869         (minus:SI (match_operand:SI 1 "reg_or_0_operand" "rJ")
870                   (match_operand:SI 2 "reg_or_8bit_operand" "rI")))
871    (trap_if (ne (minus:DI (sign_extend:DI (match_dup 1))
872                           (sign_extend:DI (match_dup 2)))
873                 (sign_extend:DI (minus:SI (match_dup 1)
874                                           (match_dup 2))))
875             (const_int 0))]
876   ""
877   "sublv %r1,%2,%0")
878
879 (define_insn "subdi3"
880   [(set (match_operand:DI 0 "register_operand" "=r")
881         (minus:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
882                   (match_operand:DI 2 "reg_or_8bit_operand" "rI")))]
883   ""
884   "subq %r1,%2,%0")
885
886 (define_insn "*ssubl"
887   [(set (match_operand:SI 0 "register_operand" "=r")
888         (minus:SI (mult:SI (match_operand:SI 1 "reg_not_elim_operand" "r")
889                            (match_operand:SI 2 "const48_operand" "I"))
890                   (match_operand:SI 3 "reg_or_8bit_operand" "rI")))]
891   ""
892   "s%2subl %1,%3,%0")
893
894 (define_insn "*ssubl_se"
895   [(set (match_operand:DI 0 "register_operand" "=r")
896         (sign_extend:DI
897          (minus:SI (mult:SI (match_operand:SI 1 "reg_not_elim_operand" "r")
898                             (match_operand:SI 2 "const48_operand" "I"))
899                    (match_operand:SI 3 "reg_or_8bit_operand" "rI"))))]
900   ""
901   "s%2subl %1,%3,%0")
902
903 (define_insn "*ssubq"
904   [(set (match_operand:DI 0 "register_operand" "=r")
905         (minus:DI (mult:DI (match_operand:DI 1 "reg_not_elim_operand" "r")
906                            (match_operand:DI 2 "const48_operand" "I"))
907                   (match_operand:DI 3 "reg_or_8bit_operand" "rI")))]
908   ""
909   "s%2subq %1,%3,%0")
910
911 (define_insn "subvdi3"
912   [(set (match_operand:DI 0 "register_operand" "=r")
913         (minus:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
914                   (match_operand:DI 2 "reg_or_8bit_operand" "rI")))
915    (trap_if (ne (minus:TI (sign_extend:TI (match_dup 1))
916                           (sign_extend:TI (match_dup 2)))
917                 (sign_extend:TI (minus:DI (match_dup 1)
918                                           (match_dup 2))))
919             (const_int 0))]
920   ""
921   "subqv %r1,%2,%0")
922
923 ;; The Unicos/Mk assembler doesn't support mull.
924
925 (define_insn "mulsi3"
926   [(set (match_operand:SI 0 "register_operand" "=r")
927         (mult:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ")
928                  (match_operand:SI 2 "reg_or_8bit_operand" "rI")))]
929   "!TARGET_ABI_UNICOSMK"
930   "mull %r1,%2,%0"
931   [(set_attr "type" "imul")
932    (set_attr "opsize" "si")])
933
934 (define_insn "*mulsi_se"
935   [(set (match_operand:DI 0 "register_operand" "=r")
936         (sign_extend:DI
937           (mult:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ")
938                    (match_operand:SI 2 "reg_or_8bit_operand" "rI"))))]
939   "!TARGET_ABI_UNICOSMK"
940   "mull %r1,%2,%0"
941   [(set_attr "type" "imul")
942    (set_attr "opsize" "si")])
943
944 (define_insn "mulvsi3"
945   [(set (match_operand:SI 0 "register_operand" "=r")
946         (mult:SI (match_operand:SI 1 "reg_or_0_operand" "%rJ")
947                  (match_operand:SI 2 "reg_or_8bit_operand" "rI")))
948    (trap_if (ne (mult:DI (sign_extend:DI (match_dup 1))
949                          (sign_extend:DI (match_dup 2)))
950                 (sign_extend:DI (mult:SI (match_dup 1)
951                                          (match_dup 2))))
952             (const_int 0))]
953   "!TARGET_ABI_UNICOSMK"
954   "mullv %r1,%2,%0"
955   [(set_attr "type" "imul")
956    (set_attr "opsize" "si")])
957
958 (define_insn "muldi3"
959   [(set (match_operand:DI 0 "register_operand" "=r")
960         (mult:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ")
961                  (match_operand:DI 2 "reg_or_8bit_operand" "rI")))]
962   ""
963   "mulq %r1,%2,%0"
964   [(set_attr "type" "imul")])
965
966 (define_insn "mulvdi3"
967   [(set (match_operand:DI 0 "register_operand" "=r")
968         (mult:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ")
969                  (match_operand:DI 2 "reg_or_8bit_operand" "rI")))
970    (trap_if (ne (mult:TI (sign_extend:TI (match_dup 1))
971                          (sign_extend:TI (match_dup 2)))
972                 (sign_extend:TI (mult:DI (match_dup 1)
973                                          (match_dup 2))))
974             (const_int 0))]
975   ""
976   "mulqv %r1,%2,%0"
977   [(set_attr "type" "imul")])
978
979 (define_insn "umuldi3_highpart"
980   [(set (match_operand:DI 0 "register_operand" "=r")
981         (truncate:DI
982          (lshiftrt:TI
983           (mult:TI (zero_extend:TI
984                      (match_operand:DI 1 "reg_or_0_operand" "%rJ"))
985                    (zero_extend:TI
986                      (match_operand:DI 2 "reg_or_8bit_operand" "rI")))
987           (const_int 64))))]
988   ""
989   "umulh %r1,%2,%0"
990   [(set_attr "type" "imul")
991    (set_attr "opsize" "udi")])
992
993 (define_insn "*umuldi3_highpart_const"
994   [(set (match_operand:DI 0 "register_operand" "=r")
995         (truncate:DI
996          (lshiftrt:TI
997           (mult:TI (zero_extend:TI (match_operand:DI 1 "register_operand" "r"))
998                    (match_operand:TI 2 "cint8_operand" "I"))
999           (const_int 64))))]
1000   ""
1001   "umulh %1,%2,%0"
1002   [(set_attr "type" "imul")
1003    (set_attr "opsize" "udi")])
1004 \f
1005 ;; The divide and remainder operations take their inputs from r24 and
1006 ;; r25, put their output in r27, and clobber r23 and r28 on all
1007 ;; systems except Unicos/Mk. On Unicos, the standard library provides
1008 ;; subroutines which use the standard calling convention and work on
1009 ;; DImode operands.
1010
1011 ;; ??? Force sign-extension here because some versions of OSF/1 and
1012 ;; Interix/NT don't do the right thing if the inputs are not properly
1013 ;; sign-extended.  But Linux, for instance, does not have this
1014 ;; problem.  Is it worth the complication here to eliminate the sign
1015 ;; extension?
1016
1017 (define_expand "divsi3"
1018   [(set (match_dup 3)
1019         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))
1020    (set (match_dup 4)
1021         (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "")))
1022    (parallel [(set (match_dup 5)
1023                    (sign_extend:DI (div:SI (match_dup 3) (match_dup 4))))
1024               (clobber (reg:DI 23))
1025               (clobber (reg:DI 28))])
1026    (set (match_operand:SI 0 "nonimmediate_operand" "")
1027         (subreg:SI (match_dup 5) 0))]
1028   "! TARGET_ABI_OPEN_VMS && ! TARGET_ABI_UNICOSMK"
1029 {
1030   operands[3] = gen_reg_rtx (DImode);
1031   operands[4] = gen_reg_rtx (DImode);
1032   operands[5] = gen_reg_rtx (DImode);
1033 })
1034
1035 (define_expand "udivsi3"
1036   [(set (match_dup 3)
1037         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))
1038    (set (match_dup 4)
1039         (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "")))
1040    (parallel [(set (match_dup 5)
1041                    (sign_extend:DI (udiv:SI (match_dup 3) (match_dup 4))))
1042               (clobber (reg:DI 23))
1043               (clobber (reg:DI 28))])
1044    (set (match_operand:SI 0 "nonimmediate_operand" "")
1045         (subreg:SI (match_dup 5) 0))]
1046   "! TARGET_ABI_OPEN_VMS && ! TARGET_ABI_UNICOSMK"
1047 {
1048   operands[3] = gen_reg_rtx (DImode);
1049   operands[4] = gen_reg_rtx (DImode);
1050   operands[5] = gen_reg_rtx (DImode);
1051 })
1052
1053 (define_expand "modsi3"
1054   [(set (match_dup 3)
1055         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))
1056    (set (match_dup 4)
1057         (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "")))
1058    (parallel [(set (match_dup 5)
1059                    (sign_extend:DI (mod:SI (match_dup 3) (match_dup 4))))
1060               (clobber (reg:DI 23))
1061               (clobber (reg:DI 28))])
1062    (set (match_operand:SI 0 "nonimmediate_operand" "")
1063         (subreg:SI (match_dup 5) 0))]
1064   "! TARGET_ABI_OPEN_VMS && ! TARGET_ABI_UNICOSMK"
1065 {
1066   operands[3] = gen_reg_rtx (DImode);
1067   operands[4] = gen_reg_rtx (DImode);
1068   operands[5] = gen_reg_rtx (DImode);
1069 })
1070
1071 (define_expand "umodsi3"
1072   [(set (match_dup 3)
1073         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))
1074    (set (match_dup 4)
1075         (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "")))
1076    (parallel [(set (match_dup 5)
1077                    (sign_extend:DI (umod:SI (match_dup 3) (match_dup 4))))
1078               (clobber (reg:DI 23))
1079               (clobber (reg:DI 28))])
1080    (set (match_operand:SI 0 "nonimmediate_operand" "")
1081         (subreg:SI (match_dup 5) 0))]
1082   "! TARGET_ABI_OPEN_VMS && ! TARGET_ABI_UNICOSMK"
1083 {
1084   operands[3] = gen_reg_rtx (DImode);
1085   operands[4] = gen_reg_rtx (DImode);
1086   operands[5] = gen_reg_rtx (DImode);
1087 })
1088
1089 (define_expand "divdi3"
1090   [(parallel [(set (match_operand:DI 0 "register_operand" "")
1091                    (div:DI (match_operand:DI 1 "register_operand" "")
1092                            (match_operand:DI 2 "register_operand" "")))
1093               (clobber (reg:DI 23))
1094               (clobber (reg:DI 28))])]
1095   "! TARGET_ABI_OPEN_VMS && ! TARGET_ABI_UNICOSMK"
1096   "")
1097
1098 (define_expand "udivdi3"
1099   [(parallel [(set (match_operand:DI 0 "register_operand" "")
1100                    (udiv:DI (match_operand:DI 1 "register_operand" "")
1101                             (match_operand:DI 2 "register_operand" "")))
1102               (clobber (reg:DI 23))
1103               (clobber (reg:DI 28))])]
1104   "! TARGET_ABI_OPEN_VMS && ! TARGET_ABI_UNICOSMK"
1105   "")
1106
1107 (define_expand "moddi3"
1108   [(use (match_operand:DI 0 "register_operand" ""))
1109    (use (match_operand:DI 1 "register_operand" ""))
1110    (use (match_operand:DI 2 "register_operand" ""))]
1111   "!TARGET_ABI_OPEN_VMS"
1112 {
1113   if (TARGET_ABI_UNICOSMK)
1114     emit_insn (gen_moddi3_umk (operands[0], operands[1], operands[2]));
1115   else
1116     emit_insn (gen_moddi3_dft (operands[0], operands[1], operands[2]));
1117   DONE;
1118 })
1119
1120 (define_expand "moddi3_dft"
1121   [(parallel [(set (match_operand:DI 0 "register_operand" "")
1122                    (mod:DI (match_operand:DI 1 "register_operand" "")
1123                            (match_operand:DI 2 "register_operand" "")))
1124               (clobber (reg:DI 23))
1125               (clobber (reg:DI 28))])]
1126   "! TARGET_ABI_OPEN_VMS && ! TARGET_ABI_UNICOSMK"
1127   "")
1128
1129 ;; On Unicos/Mk, we do as the system's C compiler does:
1130 ;; compute the quotient, multiply and subtract.
1131
1132 (define_expand "moddi3_umk"
1133   [(use (match_operand:DI 0 "register_operand" ""))
1134    (use (match_operand:DI 1 "register_operand" ""))
1135    (use (match_operand:DI 2 "register_operand" ""))]
1136   "TARGET_ABI_UNICOSMK"
1137 {
1138   rtx div, mul = gen_reg_rtx (DImode);
1139
1140   div = expand_binop (DImode, sdiv_optab, operands[1], operands[2],
1141                       NULL_RTX, 0, OPTAB_LIB);
1142   div = force_reg (DImode, div);
1143   emit_insn (gen_muldi3 (mul, operands[2], div));
1144   emit_insn (gen_subdi3 (operands[0], operands[1], mul));
1145   DONE;
1146 })
1147
1148 (define_expand "umoddi3"
1149   [(use (match_operand:DI 0 "register_operand" ""))
1150    (use (match_operand:DI 1 "register_operand" ""))
1151    (use (match_operand:DI 2 "register_operand" ""))]
1152   "! TARGET_ABI_OPEN_VMS"
1153 {
1154   if (TARGET_ABI_UNICOSMK)
1155     emit_insn (gen_umoddi3_umk (operands[0], operands[1], operands[2]));
1156   else
1157     emit_insn (gen_umoddi3_dft (operands[0], operands[1], operands[2]));
1158   DONE;
1159 })
1160
1161 (define_expand "umoddi3_dft"
1162   [(parallel [(set (match_operand:DI 0 "register_operand" "")
1163                    (umod:DI (match_operand:DI 1 "register_operand" "")
1164                             (match_operand:DI 2 "register_operand" "")))
1165               (clobber (reg:DI 23))
1166               (clobber (reg:DI 28))])]
1167   "! TARGET_ABI_OPEN_VMS && ! TARGET_ABI_UNICOSMK"
1168   "")
1169
1170 (define_expand "umoddi3_umk"
1171   [(use (match_operand:DI 0 "register_operand" ""))
1172    (use (match_operand:DI 1 "register_operand" ""))
1173    (use (match_operand:DI 2 "register_operand" ""))]
1174   "TARGET_ABI_UNICOSMK"
1175 {
1176   rtx div, mul = gen_reg_rtx (DImode);
1177
1178   div = expand_binop (DImode, udiv_optab, operands[1], operands[2],
1179                       NULL_RTX, 1, OPTAB_LIB);
1180   div = force_reg (DImode, div);
1181   emit_insn (gen_muldi3 (mul, operands[2], div));
1182   emit_insn (gen_subdi3 (operands[0], operands[1], mul));
1183   DONE;
1184 })
1185
1186 ;; Lengths of 8 for ldq $t12,__divq($gp); jsr $t9,($t12),__divq as
1187 ;; expanded by the assembler.
1188
1189 (define_insn_and_split "*divmodsi_internal_er"
1190   [(set (match_operand:DI 0 "register_operand" "=c")
1191         (sign_extend:DI (match_operator:SI 3 "divmod_operator"
1192                         [(match_operand:DI 1 "register_operand" "a")
1193                          (match_operand:DI 2 "register_operand" "b")])))
1194    (clobber (reg:DI 23))
1195    (clobber (reg:DI 28))]
1196   "TARGET_EXPLICIT_RELOCS && ! TARGET_ABI_OPEN_VMS"
1197   "ldq $27,__%E3($29)\t\t!literal!%#\;jsr $23,($27),__%E3\t\t!lituse_jsr!%#"
1198   "&& reload_completed"
1199   [(parallel [(set (match_dup 0)
1200                    (sign_extend:DI (match_dup 3)))
1201               (use (match_dup 0))
1202               (use (match_dup 4))
1203               (clobber (reg:DI 23))
1204               (clobber (reg:DI 28))])]
1205 {
1206   const char *str;
1207   switch (GET_CODE (operands[3]))
1208     {
1209     case DIV: 
1210       str = "__divl";
1211       break; 
1212     case UDIV:
1213       str = "__divlu";
1214       break;
1215     case MOD:
1216       str = "__reml";
1217       break;
1218     case UMOD:
1219       str = "__remlu";
1220       break;
1221     default:
1222       abort ();
1223     }
1224   operands[4] = GEN_INT (alpha_next_sequence_number++);
1225   emit_insn (gen_movdi_er_high_g (operands[0], pic_offset_table_rtx,
1226                                   gen_rtx_SYMBOL_REF (DImode, str),
1227                                   operands[4]));
1228 }
1229   [(set_attr "type" "jsr")
1230    (set_attr "length" "8")])
1231
1232 (define_insn "*divmodsi_internal_er_1"
1233   [(set (match_operand:DI 0 "register_operand" "=c")
1234         (sign_extend:DI (match_operator:SI 3 "divmod_operator"
1235                         [(match_operand:DI 1 "register_operand" "a")
1236                          (match_operand:DI 2 "register_operand" "b")])))
1237    (use (match_operand:DI 4 "register_operand" "c"))
1238    (use (match_operand 5 "const_int_operand" ""))
1239    (clobber (reg:DI 23))
1240    (clobber (reg:DI 28))]
1241   "TARGET_EXPLICIT_RELOCS && ! TARGET_ABI_OPEN_VMS"
1242   "jsr $23,($27),__%E3%J5"
1243   [(set_attr "type" "jsr")
1244    (set_attr "length" "4")])
1245
1246 (define_insn "*divmodsi_internal"
1247   [(set (match_operand:DI 0 "register_operand" "=c")
1248         (sign_extend:DI (match_operator:SI 3 "divmod_operator"
1249                         [(match_operand:DI 1 "register_operand" "a")
1250                          (match_operand:DI 2 "register_operand" "b")])))
1251    (clobber (reg:DI 23))
1252    (clobber (reg:DI 28))]
1253   "! TARGET_ABI_OPEN_VMS && ! TARGET_ABI_UNICOSMK"
1254   "%E3 %1,%2,%0"
1255   [(set_attr "type" "jsr")
1256    (set_attr "length" "8")])
1257
1258 (define_insn_and_split "*divmoddi_internal_er"
1259   [(set (match_operand:DI 0 "register_operand" "=c")
1260         (match_operator:DI 3 "divmod_operator"
1261                         [(match_operand:DI 1 "register_operand" "a")
1262                          (match_operand:DI 2 "register_operand" "b")]))
1263    (clobber (reg:DI 23))
1264    (clobber (reg:DI 28))]
1265   "TARGET_EXPLICIT_RELOCS && ! TARGET_ABI_OPEN_VMS"
1266   "ldq $27,__%E3($29)\t\t!literal!%#\;jsr $23,($27),__%E3\t\t!lituse_jsr!%#"
1267   "&& reload_completed"
1268   [(parallel [(set (match_dup 0) (match_dup 3))
1269               (use (match_dup 0))
1270               (use (match_dup 4))
1271               (clobber (reg:DI 23))
1272               (clobber (reg:DI 28))])]
1273 {
1274   const char *str;
1275   switch (GET_CODE (operands[3]))
1276     {
1277     case DIV: 
1278       str = "__divq";
1279       break; 
1280     case UDIV:
1281       str = "__divqu";
1282       break;
1283     case MOD:
1284       str = "__remq";
1285       break;
1286     case UMOD:
1287       str = "__remqu";
1288       break;
1289     default:
1290       abort ();
1291     }
1292   operands[4] = GEN_INT (alpha_next_sequence_number++);
1293   emit_insn (gen_movdi_er_high_g (operands[0], pic_offset_table_rtx,
1294                                   gen_rtx_SYMBOL_REF (DImode, str),
1295                                   operands[4]));
1296 }
1297   [(set_attr "type" "jsr")
1298    (set_attr "length" "8")])
1299
1300 (define_insn "*divmoddi_internal_er_1"
1301   [(set (match_operand:DI 0 "register_operand" "=c")
1302         (match_operator:DI 3 "divmod_operator"
1303                         [(match_operand:DI 1 "register_operand" "a")
1304                          (match_operand:DI 2 "register_operand" "b")]))
1305    (use (match_operand:DI 4 "register_operand" "c"))
1306    (use (match_operand 5 "const_int_operand" ""))
1307    (clobber (reg:DI 23))
1308    (clobber (reg:DI 28))]
1309   "TARGET_EXPLICIT_RELOCS && ! TARGET_ABI_OPEN_VMS"
1310   "jsr $23,($27),__%E3%J5"
1311   [(set_attr "type" "jsr")
1312    (set_attr "length" "4")])
1313
1314 (define_insn "*divmoddi_internal"
1315   [(set (match_operand:DI 0 "register_operand" "=c")
1316         (match_operator:DI 3 "divmod_operator"
1317                         [(match_operand:DI 1 "register_operand" "a")
1318                          (match_operand:DI 2 "register_operand" "b")]))
1319    (clobber (reg:DI 23))
1320    (clobber (reg:DI 28))]
1321   "! TARGET_ABI_OPEN_VMS && ! TARGET_ABI_UNICOSMK"
1322   "%E3 %1,%2,%0"
1323   [(set_attr "type" "jsr")
1324    (set_attr "length" "8")])
1325 \f
1326 ;; Next are the basic logical operations.  These only exist in DImode.
1327
1328 (define_insn "anddi3"
1329   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
1330         (and:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ,rJ")
1331                 (match_operand:DI 2 "and_operand" "rI,N,MH")))]
1332   ""
1333   "@
1334    and %r1,%2,%0
1335    bic %r1,%N2,%0
1336    zapnot %r1,%m2,%0"
1337   [(set_attr "type" "ilog,ilog,shift")])
1338
1339 ;; There are times when we can split an AND into two AND insns.  This occurs
1340 ;; when we can first clear any bytes and then clear anything else.  For
1341 ;; example "I & 0xffff07" is "(I & 0xffffff) & 0xffffffffffffff07".
1342 ;; Only do this when running on 64-bit host since the computations are
1343 ;; too messy otherwise.
1344
1345 (define_split
1346   [(set (match_operand:DI 0 "register_operand" "")
1347         (and:DI (match_operand:DI 1 "register_operand" "")
1348                 (match_operand:DI 2 "const_int_operand" "")))]
1349   "HOST_BITS_PER_WIDE_INT == 64 && ! and_operand (operands[2], DImode)"
1350   [(set (match_dup 0) (and:DI (match_dup 1) (match_dup 3)))
1351    (set (match_dup 0) (and:DI (match_dup 0) (match_dup 4)))]
1352 {
1353   unsigned HOST_WIDE_INT mask1 = INTVAL (operands[2]);
1354   unsigned HOST_WIDE_INT mask2 = mask1;
1355   int i;
1356
1357   /* For each byte that isn't all zeros, make it all ones.  */
1358   for (i = 0; i < 64; i += 8)
1359     if ((mask1 & ((HOST_WIDE_INT) 0xff << i)) != 0)
1360       mask1 |= (HOST_WIDE_INT) 0xff << i;
1361
1362   /* Now turn on any bits we've just turned off.  */
1363   mask2 |= ~ mask1;
1364
1365   operands[3] = GEN_INT (mask1);
1366   operands[4] = GEN_INT (mask2);
1367 })
1368
1369 (define_expand "zero_extendqihi2"
1370   [(set (match_operand:HI 0 "register_operand" "")
1371         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))]
1372   ""
1373 {
1374   if (! TARGET_BWX)
1375     operands[1] = force_reg (QImode, operands[1]);
1376 })
1377
1378 (define_insn "*zero_extendqihi2_bwx"
1379   [(set (match_operand:HI 0 "register_operand" "=r,r")
1380         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "r,m")))]
1381   "TARGET_BWX"
1382   "@
1383    and %1,0xff,%0
1384    ldbu %0,%1"
1385   [(set_attr "type" "ilog,ild")])
1386
1387 (define_insn "*zero_extendqihi2_nobwx"
1388   [(set (match_operand:HI 0 "register_operand" "=r")
1389         (zero_extend:HI (match_operand:QI 1 "register_operand" "r")))]
1390   "! TARGET_BWX"
1391   "and %1,0xff,%0"
1392   [(set_attr "type" "ilog")])
1393
1394 (define_expand "zero_extendqisi2"
1395   [(set (match_operand:SI 0 "register_operand" "")
1396         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))]
1397   ""
1398 {
1399   if (! TARGET_BWX)
1400     operands[1] = force_reg (QImode, operands[1]);
1401 })
1402
1403 (define_insn "*zero_extendqisi2_bwx"
1404   [(set (match_operand:SI 0 "register_operand" "=r,r")
1405         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "r,m")))]
1406   "TARGET_BWX"
1407   "@
1408    and %1,0xff,%0
1409    ldbu %0,%1"
1410   [(set_attr "type" "ilog,ild")])
1411
1412 (define_insn "*zero_extendqisi2_nobwx"
1413   [(set (match_operand:SI 0 "register_operand" "=r")
1414         (zero_extend:SI (match_operand:QI 1 "register_operand" "r")))]
1415   "! TARGET_BWX"
1416   "and %1,0xff,%0"
1417   [(set_attr "type" "ilog")])
1418
1419 (define_expand "zero_extendqidi2"
1420   [(set (match_operand:DI 0 "register_operand" "")
1421         (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "")))]
1422   ""
1423 {
1424   if (! TARGET_BWX)
1425     operands[1] = force_reg (QImode, operands[1]);
1426 })
1427
1428 (define_insn "*zero_extendqidi2_bwx"
1429   [(set (match_operand:DI 0 "register_operand" "=r,r")
1430         (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "r,m")))]
1431   "TARGET_BWX"
1432   "@
1433    and %1,0xff,%0
1434    ldbu %0,%1"
1435   [(set_attr "type" "ilog,ild")])
1436
1437 (define_insn "*zero_extendqidi2_nobwx"
1438   [(set (match_operand:DI 0 "register_operand" "=r")
1439         (zero_extend:DI (match_operand:QI 1 "register_operand" "r")))]
1440   "! TARGET_BWX"
1441   "and %1,0xff,%0"
1442   [(set_attr "type" "ilog")])
1443
1444 (define_expand "zero_extendhisi2"
1445   [(set (match_operand:SI 0 "register_operand" "")
1446         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
1447   ""
1448 {
1449   if (! TARGET_BWX)
1450     operands[1] = force_reg (HImode, operands[1]);
1451 })
1452
1453 (define_insn "*zero_extendhisi2_bwx"
1454   [(set (match_operand:SI 0 "register_operand" "=r,r")
1455         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "r,m")))]
1456   "TARGET_BWX"
1457   "@
1458    zapnot %1,3,%0
1459    ldwu %0,%1"
1460   [(set_attr "type" "shift,ild")])
1461
1462 (define_insn "*zero_extendhisi2_nobwx"
1463   [(set (match_operand:SI 0 "register_operand" "=r")
1464         (zero_extend:SI (match_operand:HI 1 "register_operand" "r")))]
1465   "! TARGET_BWX"
1466   "zapnot %1,3,%0"
1467   [(set_attr "type" "shift")])
1468
1469 (define_expand "zero_extendhidi2"
1470   [(set (match_operand:DI 0 "register_operand" "")
1471         (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "")))]
1472   ""
1473 {
1474   if (! TARGET_BWX)
1475     operands[1] = force_reg (HImode, operands[1]);
1476 })
1477
1478 (define_insn "*zero_extendhidi2_bwx"
1479   [(set (match_operand:DI 0 "register_operand" "=r,r")
1480         (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "r,m")))]
1481   "TARGET_BWX"
1482   "@
1483    zapnot %1,3,%0
1484    ldwu %0,%1"
1485   [(set_attr "type" "shift,ild")])
1486
1487 (define_insn "*zero_extendhidi2_nobwx"
1488   [(set (match_operand:DI 0 "register_operand" "=r")
1489         (zero_extend:DI (match_operand:HI 1 "register_operand" "r")))]
1490   ""
1491   "zapnot %1,3,%0"
1492   [(set_attr "type" "shift")])
1493
1494 (define_insn "zero_extendsidi2"
1495   [(set (match_operand:DI 0 "register_operand" "=r")
1496         (zero_extend:DI (match_operand:SI 1 "register_operand" "r")))]
1497   ""
1498   "zapnot %1,15,%0"
1499   [(set_attr "type" "shift")])
1500
1501 (define_insn "andnotdi3"
1502   [(set (match_operand:DI 0 "register_operand" "=r")
1503         (and:DI (not:DI (match_operand:DI 1 "reg_or_8bit_operand" "rI"))
1504                 (match_operand:DI 2 "reg_or_0_operand" "rJ")))]
1505   ""
1506   "bic %r2,%1,%0"
1507   [(set_attr "type" "ilog")])
1508
1509 (define_insn "iordi3"
1510   [(set (match_operand:DI 0 "register_operand" "=r,r")
1511         (ior:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ")
1512                 (match_operand:DI 2 "or_operand" "rI,N")))]
1513   ""
1514   "@
1515    bis %r1,%2,%0
1516    ornot %r1,%N2,%0"
1517   [(set_attr "type" "ilog")])
1518
1519 (define_insn "one_cmpldi2"
1520   [(set (match_operand:DI 0 "register_operand" "=r")
1521         (not:DI (match_operand:DI 1 "reg_or_8bit_operand" "rI")))]
1522   ""
1523   "ornot $31,%1,%0"
1524   [(set_attr "type" "ilog")])
1525
1526 (define_insn "*iornot"
1527   [(set (match_operand:DI 0 "register_operand" "=r")
1528         (ior:DI (not:DI (match_operand:DI 1 "reg_or_8bit_operand" "rI"))
1529                 (match_operand:DI 2 "reg_or_0_operand" "rJ")))]
1530   ""
1531   "ornot %r2,%1,%0"
1532   [(set_attr "type" "ilog")])
1533
1534 (define_insn "xordi3"
1535   [(set (match_operand:DI 0 "register_operand" "=r,r")
1536         (xor:DI (match_operand:DI 1 "reg_or_0_operand" "%rJ,rJ")
1537                 (match_operand:DI 2 "or_operand" "rI,N")))]
1538   ""
1539   "@
1540    xor %r1,%2,%0
1541    eqv %r1,%N2,%0"
1542   [(set_attr "type" "ilog")])
1543
1544 (define_insn "*xornot"
1545   [(set (match_operand:DI 0 "register_operand" "=r")
1546         (not:DI (xor:DI (match_operand:DI 1 "register_operand" "%rJ")
1547                         (match_operand:DI 2 "register_operand" "rI"))))]
1548   ""
1549   "eqv %r1,%2,%0"
1550   [(set_attr "type" "ilog")])
1551 \f
1552 ;; Handle the FFS insn iff we support CIX.
1553
1554 (define_expand "ffsdi2"
1555   [(set (match_dup 2)
1556         (unspec:DI [(match_operand:DI 1 "register_operand" "")] UNSPEC_CTTZ))
1557    (set (match_dup 3)
1558         (plus:DI (match_dup 2) (const_int 1)))
1559    (set (match_operand:DI 0 "register_operand" "")
1560         (if_then_else:DI (eq (match_dup 1) (const_int 0))
1561                          (const_int 0) (match_dup 3)))]
1562   "TARGET_CIX"
1563 {
1564   operands[2] = gen_reg_rtx (DImode);
1565   operands[3] = gen_reg_rtx (DImode);
1566 })
1567
1568 (define_insn "*cttz"
1569   [(set (match_operand:DI 0 "register_operand" "=r")
1570         (unspec:DI [(match_operand:DI 1 "register_operand" "r")] UNSPEC_CTTZ))]
1571   "TARGET_CIX"
1572   "cttz %1,%0"
1573   ; EV6 calls all mvi and cttz/ctlz/popc class imisc, so just
1574   ; reuse the existing type name.
1575   [(set_attr "type" "mvi")])
1576 \f
1577 ;; Next come the shifts and the various extract and insert operations.
1578
1579 (define_insn "ashldi3"
1580   [(set (match_operand:DI 0 "register_operand" "=r,r")
1581         (ashift:DI (match_operand:DI 1 "reg_or_0_operand" "rJ,rJ")
1582                    (match_operand:DI 2 "reg_or_6bit_operand" "P,rS")))]
1583   ""
1584 {
1585   switch (which_alternative)
1586     {
1587     case 0:
1588       if (operands[2] == const1_rtx)
1589         return "addq %r1,%r1,%0";
1590       else
1591         return "s%P2addq %r1,0,%0";
1592     case 1:
1593       return "sll %r1,%2,%0";
1594     default:
1595       abort();
1596     }
1597 }
1598   [(set_attr "type" "iadd,shift")])
1599
1600 (define_insn "*ashldi_se"
1601   [(set (match_operand:DI 0 "register_operand" "=r")
1602         (sign_extend:DI
1603          (subreg:SI (ashift:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1604                                (match_operand:DI 2 "const_int_operand" "P"))
1605                     0)))]
1606   "INTVAL (operands[2]) >= 1 && INTVAL (operands[2]) <= 3"
1607 {
1608   if (operands[2] == const1_rtx)
1609     return "addl %r1,%r1,%0";
1610   else
1611     return "s%P2addl %r1,0,%0";
1612 }
1613   [(set_attr "type" "iadd")])
1614
1615 (define_insn "lshrdi3"
1616   [(set (match_operand:DI 0 "register_operand" "=r")
1617         (lshiftrt:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1618                      (match_operand:DI 2 "reg_or_6bit_operand" "rS")))]
1619   ""
1620   "srl %r1,%2,%0"
1621   [(set_attr "type" "shift")])
1622
1623 (define_insn "ashrdi3"
1624   [(set (match_operand:DI 0 "register_operand" "=r")
1625         (ashiftrt:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1626                      (match_operand:DI 2 "reg_or_6bit_operand" "rS")))]
1627   ""
1628   "sra %r1,%2,%0"
1629   [(set_attr "type" "shift")])
1630
1631 (define_expand "extendqihi2"
1632   [(set (match_dup 2)
1633         (ashift:DI (match_operand:QI 1 "some_operand" "")
1634                    (const_int 56)))
1635    (set (match_operand:HI 0 "register_operand" "")
1636         (ashiftrt:DI (match_dup 2)
1637                      (const_int 56)))]
1638   ""
1639 {
1640   if (TARGET_BWX)
1641     {
1642       emit_insn (gen_extendqihi2x (operands[0],
1643                                    force_reg (QImode, operands[1])));
1644       DONE;
1645     }
1646
1647  /* If we have an unaligned MEM, extend to DImode (which we do
1648      specially) and then copy to the result.  */
1649   if (unaligned_memory_operand (operands[1], HImode))
1650     {
1651       rtx temp = gen_reg_rtx (DImode);
1652
1653       emit_insn (gen_extendqidi2 (temp, operands[1]));
1654       emit_move_insn (operands[0], gen_lowpart (HImode, temp));
1655       DONE;
1656     }
1657
1658   operands[0] = gen_lowpart (DImode, operands[0]);
1659   operands[1] = gen_lowpart (DImode, force_reg (QImode, operands[1]));
1660   operands[2] = gen_reg_rtx (DImode);
1661 })
1662
1663 (define_insn "extendqidi2x"
1664   [(set (match_operand:DI 0 "register_operand" "=r")
1665         (sign_extend:DI (match_operand:QI 1 "register_operand" "r")))]
1666   "TARGET_BWX"
1667   "sextb %1,%0"
1668   [(set_attr "type" "shift")])
1669
1670 (define_insn "extendhidi2x"
1671   [(set (match_operand:DI 0 "register_operand" "=r")
1672         (sign_extend:DI (match_operand:HI 1 "register_operand" "r")))]
1673   "TARGET_BWX"
1674   "sextw %1,%0"
1675   [(set_attr "type" "shift")])
1676
1677 (define_insn "extendqisi2x"
1678   [(set (match_operand:SI 0 "register_operand" "=r")
1679         (sign_extend:SI (match_operand:QI 1 "register_operand" "r")))]
1680   "TARGET_BWX"
1681   "sextb %1,%0"
1682   [(set_attr "type" "shift")])
1683
1684 (define_insn "extendhisi2x"
1685   [(set (match_operand:SI 0 "register_operand" "=r")
1686         (sign_extend:SI (match_operand:HI 1 "register_operand" "r")))]
1687   "TARGET_BWX"
1688   "sextw %1,%0"
1689   [(set_attr "type" "shift")])
1690
1691 (define_insn "extendqihi2x"
1692   [(set (match_operand:HI 0 "register_operand" "=r")
1693         (sign_extend:HI (match_operand:QI 1 "register_operand" "r")))]
1694   "TARGET_BWX"
1695   "sextb %1,%0"
1696   [(set_attr "type" "shift")])
1697
1698 (define_expand "extendqisi2"
1699   [(set (match_dup 2)
1700         (ashift:DI (match_operand:QI 1 "some_operand" "")
1701                    (const_int 56)))
1702    (set (match_operand:SI 0 "register_operand" "")
1703         (ashiftrt:DI (match_dup 2)
1704                      (const_int 56)))]
1705   ""
1706 {
1707   if (TARGET_BWX)
1708     {
1709       emit_insn (gen_extendqisi2x (operands[0],
1710                                    force_reg (QImode, operands[1])));
1711       DONE;
1712     }
1713
1714   /* If we have an unaligned MEM, extend to a DImode form of
1715      the result (which we do specially).  */
1716   if (unaligned_memory_operand (operands[1], QImode))
1717     {
1718       rtx temp = gen_reg_rtx (DImode);
1719
1720       emit_insn (gen_extendqidi2 (temp, operands[1]));
1721       emit_move_insn (operands[0], gen_lowpart (SImode, temp));
1722       DONE;
1723     }
1724
1725   operands[0] = gen_lowpart (DImode, operands[0]);
1726   operands[1] = gen_lowpart (DImode, force_reg (QImode, operands[1]));
1727   operands[2] = gen_reg_rtx (DImode);
1728 })
1729
1730 (define_expand "extendqidi2"
1731   [(set (match_dup 2)
1732         (ashift:DI (match_operand:QI 1 "some_operand" "")
1733                    (const_int 56)))
1734    (set (match_operand:DI 0 "register_operand" "")
1735         (ashiftrt:DI (match_dup 2)
1736                      (const_int 56)))]
1737   ""
1738 {
1739   if (TARGET_BWX)
1740     {
1741       emit_insn (gen_extendqidi2x (operands[0],
1742                                    force_reg (QImode, operands[1])));
1743       DONE;
1744     }
1745
1746   if (unaligned_memory_operand (operands[1], QImode))
1747     {
1748       rtx seq
1749         = gen_unaligned_extendqidi (operands[0],
1750                                     get_unaligned_address (operands[1], 1));
1751
1752       alpha_set_memflags (seq, operands[1]);
1753       emit_insn (seq);
1754       DONE;
1755     }
1756
1757   operands[1] = gen_lowpart (DImode, force_reg (QImode, operands[1]));
1758   operands[2] = gen_reg_rtx (DImode);
1759 })
1760
1761 (define_expand "extendhisi2"
1762   [(set (match_dup 2)
1763         (ashift:DI (match_operand:HI 1 "some_operand" "")
1764                    (const_int 48)))
1765    (set (match_operand:SI 0 "register_operand" "")
1766         (ashiftrt:DI (match_dup 2)
1767                      (const_int 48)))]
1768   ""
1769 {
1770   if (TARGET_BWX)
1771     {
1772       emit_insn (gen_extendhisi2x (operands[0],
1773                                    force_reg (HImode, operands[1])));
1774       DONE;
1775     }
1776
1777   /* If we have an unaligned MEM, extend to a DImode form of
1778      the result (which we do specially).  */
1779   if (unaligned_memory_operand (operands[1], HImode))
1780     {
1781       rtx temp = gen_reg_rtx (DImode);
1782
1783       emit_insn (gen_extendhidi2 (temp, operands[1]));
1784       emit_move_insn (operands[0], gen_lowpart (SImode, temp));
1785       DONE;
1786     }
1787
1788   operands[0] = gen_lowpart (DImode, operands[0]);
1789   operands[1] = gen_lowpart (DImode, force_reg (HImode, operands[1]));
1790   operands[2] = gen_reg_rtx (DImode);
1791 })
1792
1793 (define_expand "extendhidi2"
1794   [(set (match_dup 2)
1795         (ashift:DI (match_operand:HI 1 "some_operand" "")
1796                    (const_int 48)))
1797    (set (match_operand:DI 0 "register_operand" "")
1798         (ashiftrt:DI (match_dup 2)
1799                      (const_int 48)))]
1800   ""
1801 {
1802   if (TARGET_BWX)
1803     {
1804       emit_insn (gen_extendhidi2x (operands[0],
1805                                    force_reg (HImode, operands[1])));
1806       DONE;
1807     }
1808
1809   if (unaligned_memory_operand (operands[1], HImode))
1810     {
1811       rtx seq
1812         = gen_unaligned_extendhidi (operands[0],
1813                                     get_unaligned_address (operands[1], 2));
1814
1815       alpha_set_memflags (seq, operands[1]);
1816       emit_insn (seq);
1817       DONE;
1818     }
1819
1820   operands[1] = gen_lowpart (DImode, force_reg (HImode, operands[1]));
1821   operands[2] = gen_reg_rtx (DImode);
1822 })
1823
1824 ;; Here's how we sign extend an unaligned byte and halfword.  Doing this
1825 ;; as a pattern saves one instruction.  The code is similar to that for
1826 ;; the unaligned loads (see below).
1827 ;;
1828 ;; Operand 1 is the address + 1 (+2 for HI), operand 0 is the result.
1829 (define_expand "unaligned_extendqidi"
1830   [(use (match_operand:QI 0 "register_operand" ""))
1831    (use (match_operand:DI 1 "address_operand" ""))]
1832   ""
1833 {
1834   if (WORDS_BIG_ENDIAN)
1835     emit_insn (gen_unaligned_extendqidi_be (operands[0], operands[1]));
1836   else
1837     emit_insn (gen_unaligned_extendqidi_le (operands[0], operands[1]));
1838   DONE;
1839 })
1840
1841 (define_expand "unaligned_extendqidi_le"
1842   [(set (match_dup 2) (match_operand:DI 1 "address_operand" ""))
1843    (set (match_dup 3)
1844         (mem:DI (and:DI (plus:DI (match_dup 2) (const_int -1))
1845                         (const_int -8))))
1846    (set (match_dup 4)
1847         (ashift:DI (match_dup 3)
1848                    (minus:DI (const_int 64)
1849                              (ashift:DI
1850                               (and:DI (match_dup 2) (const_int 7))
1851                               (const_int 3)))))
1852    (set (subreg:DI (match_operand:QI 0 "register_operand" "") 0)
1853         (ashiftrt:DI (match_dup 4) (const_int 56)))]
1854   "! WORDS_BIG_ENDIAN"
1855 {
1856   operands[2] = gen_reg_rtx (DImode);
1857   operands[3] = gen_reg_rtx (DImode);
1858   operands[4] = gen_reg_rtx (DImode);
1859 })
1860
1861 (define_expand "unaligned_extendqidi_be"
1862   [(set (match_dup 2) (match_operand:DI 1 "address_operand" ""))
1863    (set (match_dup 3) (plus:DI (match_dup 2) (const_int -1)))
1864    (set (match_dup 4)
1865         (mem:DI (and:DI (match_dup 3)
1866                         (const_int -8))))
1867    (set (match_dup 5) (plus:DI (match_dup 2) (const_int -2)))
1868    (set (match_dup 6)
1869         (ashift:DI (match_dup 4)
1870                    (ashift:DI
1871                      (and:DI
1872                        (plus:DI (match_dup 5) (const_int 1))
1873                        (const_int 7))
1874                      (const_int 3))))
1875    (set (subreg:DI (match_operand:QI 0 "register_operand" "") 0)
1876         (ashiftrt:DI (match_dup 6) (const_int 56)))]
1877   "WORDS_BIG_ENDIAN"
1878 {
1879   operands[2] = gen_reg_rtx (DImode);
1880   operands[3] = gen_reg_rtx (DImode);
1881   operands[4] = gen_reg_rtx (DImode);
1882   operands[5] = gen_reg_rtx (DImode);
1883   operands[6] = gen_reg_rtx (DImode);
1884 })
1885
1886 (define_expand "unaligned_extendhidi"
1887   [(use (match_operand:QI 0 "register_operand" ""))
1888    (use (match_operand:DI 1 "address_operand" ""))]
1889   ""
1890 {
1891   operands[0] = gen_lowpart (DImode, operands[0]);
1892   emit_insn ((WORDS_BIG_ENDIAN
1893               ? gen_unaligned_extendhidi_be
1894               : gen_unaligned_extendhidi_le) (operands[0], operands[1]));
1895   DONE;
1896 })
1897
1898 (define_expand "unaligned_extendhidi_le"
1899   [(set (match_dup 2) (match_operand:DI 1 "address_operand" ""))
1900    (set (match_dup 3)
1901         (mem:DI (and:DI (plus:DI (match_dup 2) (const_int -2))
1902                         (const_int -8))))
1903    (set (match_dup 4)
1904         (ashift:DI (match_dup 3)
1905                    (minus:DI (const_int 64)
1906                              (ashift:DI
1907                               (and:DI (match_dup 2) (const_int 7))
1908                               (const_int 3)))))
1909    (set (match_operand:DI 0 "register_operand" "")
1910         (ashiftrt:DI (match_dup 4) (const_int 48)))]
1911   "! WORDS_BIG_ENDIAN"
1912 {
1913   operands[2] = gen_reg_rtx (DImode);
1914   operands[3] = gen_reg_rtx (DImode);
1915   operands[4] = gen_reg_rtx (DImode);
1916 })
1917
1918 (define_expand "unaligned_extendhidi_be"
1919   [(set (match_dup 2) (match_operand:DI 1 "address_operand" ""))
1920    (set (match_dup 3) (plus:DI (match_dup 2) (const_int -2)))
1921    (set (match_dup 4)
1922         (mem:DI (and:DI (match_dup 3)
1923                         (const_int -8))))
1924    (set (match_dup 5) (plus:DI (match_dup 2) (const_int -3)))
1925    (set (match_dup 6)
1926         (ashift:DI (match_dup 4)
1927                    (ashift:DI
1928                      (and:DI
1929                        (plus:DI (match_dup 5) (const_int 1))
1930                        (const_int 7))
1931                      (const_int 3))))
1932    (set (match_operand:DI 0 "register_operand" "")
1933         (ashiftrt:DI (match_dup 6) (const_int 48)))]
1934   "WORDS_BIG_ENDIAN"
1935 {
1936   operands[2] = gen_reg_rtx (DImode);
1937   operands[3] = gen_reg_rtx (DImode);
1938   operands[4] = gen_reg_rtx (DImode);
1939   operands[5] = gen_reg_rtx (DImode);
1940   operands[6] = gen_reg_rtx (DImode);
1941 })
1942
1943 (define_insn "*extxl_const"
1944   [(set (match_operand:DI 0 "register_operand" "=r")
1945         (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1946                          (match_operand:DI 2 "mode_width_operand" "n")
1947                          (match_operand:DI 3 "mul8_operand" "I")))]
1948   ""
1949   "ext%M2l %r1,%s3,%0"
1950   [(set_attr "type" "shift")])
1951
1952 (define_insn "extxl_le"
1953   [(set (match_operand:DI 0 "register_operand" "=r")
1954         (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1955                          (match_operand:DI 2 "mode_width_operand" "n")
1956                          (ashift:DI (match_operand:DI 3 "reg_or_8bit_operand" "rI")
1957                                     (const_int 3))))]
1958   "! WORDS_BIG_ENDIAN"
1959   "ext%M2l %r1,%3,%0"
1960   [(set_attr "type" "shift")])
1961
1962 (define_insn "extxl_be"
1963   [(set (match_operand:DI 0 "register_operand" "=r")
1964         (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1965                          (match_operand:DI 2 "mode_width_operand" "n")
1966                          (minus:DI
1967                            (const_int 56)
1968                            (ashift:DI
1969                              (match_operand:DI 3 "reg_or_8bit_operand" "rI")
1970                              (const_int 3)))))]
1971   "WORDS_BIG_ENDIAN"
1972   "ext%M2l %r1,%3,%0"
1973   [(set_attr "type" "shift")])
1974
1975 ;; Combine has some strange notion of preserving existing undefined behaviour
1976 ;; in shifts larger than a word size.  So capture these patterns that it
1977 ;; should have turned into zero_extracts.
1978
1979 (define_insn "*extxl_1_le"
1980   [(set (match_operand:DI 0 "register_operand" "=r")
1981         (and:DI (lshiftrt:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
1982                   (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
1983                              (const_int 3)))
1984              (match_operand:DI 3 "mode_mask_operand" "n")))]
1985   "! WORDS_BIG_ENDIAN"
1986   "ext%U3l %1,%2,%0"
1987   [(set_attr "type" "shift")])
1988
1989 (define_insn "*extxl_1_be"
1990   [(set (match_operand:DI 0 "register_operand" "=r")
1991         (and:DI (lshiftrt:DI
1992                   (match_operand:DI 1 "reg_or_0_operand" "rJ")
1993                   (minus:DI (const_int 56)
1994                     (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
1995                                (const_int 3))))
1996                 (match_operand:DI 3 "mode_mask_operand" "n")))]
1997   "WORDS_BIG_ENDIAN"
1998   "ext%U3l %1,%2,%0"
1999   [(set_attr "type" "shift")])
2000
2001 (define_insn "*extql_2_le"
2002   [(set (match_operand:DI 0 "register_operand" "=r")
2003         (lshiftrt:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
2004           (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2005                      (const_int 3))))]
2006   "! WORDS_BIG_ENDIAN"
2007   "extql %1,%2,%0"
2008   [(set_attr "type" "shift")])
2009
2010 (define_insn "*extql_2_be"
2011   [(set (match_operand:DI 0 "register_operand" "=r")
2012         (lshiftrt:DI
2013           (match_operand:DI 1 "reg_or_0_operand" "rJ")
2014           (minus:DI (const_int 56)
2015                     (ashift:DI
2016                       (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2017                       (const_int 3)))))]
2018   "WORDS_BIG_ENDIAN"
2019   "extql %1,%2,%0"
2020   [(set_attr "type" "shift")])
2021
2022 (define_insn "extqh_le"
2023   [(set (match_operand:DI 0 "register_operand" "=r")
2024         (ashift:DI
2025          (match_operand:DI 1 "reg_or_0_operand" "rJ")
2026           (minus:DI (const_int 64)
2027                     (ashift:DI
2028                      (and:DI
2029                       (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2030                       (const_int 7))
2031                      (const_int 3)))))]
2032   "! WORDS_BIG_ENDIAN"
2033   "extqh %r1,%2,%0"
2034   [(set_attr "type" "shift")])
2035
2036 (define_insn "extqh_be"
2037   [(set (match_operand:DI 0 "register_operand" "=r")
2038         (ashift:DI
2039           (match_operand:DI 1 "reg_or_0_operand" "rJ")
2040           (ashift:DI
2041             (and:DI
2042               (plus:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2043                        (const_int 1))
2044               (const_int 7))
2045             (const_int 3))))]
2046   "WORDS_BIG_ENDIAN"
2047   "extqh %r1,%2,%0"
2048   [(set_attr "type" "shift")])
2049
2050 (define_insn "extlh_le"
2051   [(set (match_operand:DI 0 "register_operand" "=r")
2052         (ashift:DI
2053          (and:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
2054                  (const_int 2147483647))
2055          (minus:DI (const_int 64)
2056                     (ashift:DI
2057                      (and:DI
2058                       (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2059                       (const_int 7))
2060                      (const_int 3)))))]
2061   "! WORDS_BIG_ENDIAN"
2062   "extlh %r1,%2,%0"
2063   [(set_attr "type" "shift")])
2064
2065 (define_insn "extlh_be"
2066   [(set (match_operand:DI 0 "register_operand" "=r")
2067         (and:DI
2068           (ashift:DI
2069             (match_operand:DI 1 "reg_or_0_operand" "rJ")
2070             (ashift:DI
2071               (and:DI
2072                 (plus:DI
2073                   (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2074                   (const_int 1))
2075                 (const_int 7))
2076               (const_int 3)))
2077           (const_int 2147483647)))]
2078   "WORDS_BIG_ENDIAN"
2079   "extlh %r1,%2,%0"
2080   [(set_attr "type" "shift")])
2081
2082 (define_insn "extwh_le"
2083   [(set (match_operand:DI 0 "register_operand" "=r")
2084         (ashift:DI
2085          (and:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
2086                  (const_int 65535))
2087          (minus:DI (const_int 64)
2088                     (ashift:DI
2089                      (and:DI
2090                       (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2091                       (const_int 7))
2092                      (const_int 3)))))]
2093   "! WORDS_BIG_ENDIAN"
2094   "extwh %r1,%2,%0"
2095   [(set_attr "type" "shift")])
2096
2097 (define_insn "extwh_be"
2098   [(set (match_operand:DI 0 "register_operand" "=r")
2099         (and:DI
2100           (ashift:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
2101                      (ashift:DI
2102                        (and:DI
2103                          (plus:DI
2104                            (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2105                            (const_int 1))
2106                          (const_int 7))
2107                        (const_int 3)))
2108           (const_int 65535)))]
2109   "WORDS_BIG_ENDIAN"
2110   "extwh %r1,%2,%0"
2111   [(set_attr "type" "shift")])
2112
2113 ;; This converts an extXl into an extXh with an appropriate adjustment
2114 ;; to the address calculation.
2115
2116 ;;(define_split
2117 ;;  [(set (match_operand:DI 0 "register_operand" "")
2118 ;;      (ashift:DI (zero_extract:DI (match_operand:DI 1 "register_operand" "")
2119 ;;                                  (match_operand:DI 2 "mode_width_operand" "")
2120 ;;                                  (ashift:DI (match_operand:DI 3 "" "")
2121 ;;                                             (const_int 3)))
2122 ;;                 (match_operand:DI 4 "const_int_operand" "")))
2123 ;;   (clobber (match_operand:DI 5 "register_operand" ""))]
2124 ;;  "INTVAL (operands[4]) == 64 - INTVAL (operands[2])"
2125 ;;  [(set (match_dup 5) (match_dup 6))
2126 ;;   (set (match_dup 0)
2127 ;;      (ashift:DI (zero_extract:DI (match_dup 1) (match_dup 2)
2128 ;;                                  (ashift:DI (plus:DI (match_dup 5)
2129 ;;                                                      (match_dup 7))
2130 ;;                                             (const_int 3)))
2131 ;;                 (match_dup 4)))]
2132 ;;  "
2133 ;;{
2134 ;;  operands[6] = plus_constant (operands[3],
2135 ;;                             INTVAL (operands[2]) / BITS_PER_UNIT);
2136 ;;  operands[7] = GEN_INT (- INTVAL (operands[2]) / BITS_PER_UNIT);
2137 ;;}")
2138
2139 (define_insn "*insbl_const"
2140   [(set (match_operand:DI 0 "register_operand" "=r")
2141         (ashift:DI (zero_extend:DI (match_operand:QI 1 "register_operand" "r"))
2142                    (match_operand:DI 2 "mul8_operand" "I")))]
2143   ""
2144   "insbl %1,%s2,%0"
2145   [(set_attr "type" "shift")])
2146
2147 (define_insn "*inswl_const"
2148   [(set (match_operand:DI 0 "register_operand" "=r")
2149         (ashift:DI (zero_extend:DI (match_operand:HI 1 "register_operand" "r"))
2150                    (match_operand:DI 2 "mul8_operand" "I")))]
2151   ""
2152   "inswl %1,%s2,%0"
2153   [(set_attr "type" "shift")])
2154
2155 (define_insn "*insll_const"
2156   [(set (match_operand:DI 0 "register_operand" "=r")
2157         (ashift:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
2158                    (match_operand:DI 2 "mul8_operand" "I")))]
2159   ""
2160   "insll %1,%s2,%0"
2161   [(set_attr "type" "shift")])
2162
2163 (define_insn "insbl_le"
2164   [(set (match_operand:DI 0 "register_operand" "=r")
2165         (ashift:DI (zero_extend:DI (match_operand:QI 1 "register_operand" "r"))
2166                    (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2167                               (const_int 3))))]
2168   "! WORDS_BIG_ENDIAN"
2169   "insbl %1,%2,%0"
2170   [(set_attr "type" "shift")])
2171
2172 (define_insn "insbl_be"
2173  [(set (match_operand:DI 0 "register_operand" "=r")
2174        (ashift:DI (zero_extend:DI (match_operand:QI 1 "register_operand" "r"))
2175          (minus:DI (const_int 56)
2176            (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2177                       (const_int 3)))))]
2178   "WORDS_BIG_ENDIAN"
2179   "insbl %1,%2,%0"
2180   [(set_attr "type" "shift")])
2181
2182 (define_insn "inswl_le"
2183   [(set (match_operand:DI 0 "register_operand" "=r")
2184         (ashift:DI (zero_extend:DI (match_operand:HI 1 "register_operand" "r"))
2185                    (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2186                               (const_int 3))))]
2187   "! WORDS_BIG_ENDIAN"
2188   "inswl %1,%2,%0"
2189   [(set_attr "type" "shift")])
2190
2191 (define_insn "inswl_be"
2192   [(set (match_operand:DI 0 "register_operand" "=r")
2193         (ashift:DI (zero_extend:DI (match_operand:HI 1 "register_operand" "r"))
2194           (minus:DI (const_int 56)
2195             (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2196                        (const_int 3)))))]
2197   "WORDS_BIG_ENDIAN"
2198   "inswl %1,%2,%0"
2199   [(set_attr "type" "shift")])
2200
2201 (define_insn "insll_le"
2202   [(set (match_operand:DI 0 "register_operand" "=r")
2203         (ashift:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
2204                    (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2205                               (const_int 3))))]
2206   "! WORDS_BIG_ENDIAN"
2207   "insll %1,%2,%0"
2208   [(set_attr "type" "shift")])
2209
2210 (define_insn "insll_be"
2211   [(set (match_operand:DI 0 "register_operand" "=r")
2212         (ashift:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
2213           (minus:DI (const_int 56)
2214             (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2215                        (const_int 3)))))]
2216   "WORDS_BIG_ENDIAN"
2217   "insll %1,%2,%0"
2218   [(set_attr "type" "shift")])
2219
2220 (define_insn "insql_le"
2221   [(set (match_operand:DI 0 "register_operand" "=r")
2222         (ashift:DI (match_operand:DI 1 "register_operand" "r")
2223                    (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2224                               (const_int 3))))]
2225   "! WORDS_BIG_ENDIAN"
2226   "insql %1,%2,%0"
2227   [(set_attr "type" "shift")])
2228
2229 (define_insn "insql_be"
2230   [(set (match_operand:DI 0 "register_operand" "=r")
2231         (ashift:DI (match_operand:DI 1 "register_operand" "r")
2232           (minus:DI (const_int 56)
2233             (ashift:DI (match_operand:DI 2 "reg_or_8bit_operand" "rI")
2234                        (const_int 3)))))]
2235   "WORDS_BIG_ENDIAN"
2236   "insql %1,%2,%0"
2237   [(set_attr "type" "shift")])
2238
2239 ;; Combine has this sometimes habit of moving the and outside of the
2240 ;; shift, making life more interesting.
2241
2242 (define_insn "*insxl"
2243   [(set (match_operand:DI 0 "register_operand" "=r")
2244         (and:DI (ashift:DI (match_operand:DI 1 "register_operand" "r")
2245                            (match_operand:DI 2 "mul8_operand" "I"))
2246                 (match_operand:DI 3 "immediate_operand" "i")))]
2247   "HOST_BITS_PER_WIDE_INT == 64
2248    && GET_CODE (operands[3]) == CONST_INT
2249    && (((unsigned HOST_WIDE_INT) 0xff << INTVAL (operands[2])
2250         == (unsigned HOST_WIDE_INT) INTVAL (operands[3]))
2251        || ((unsigned HOST_WIDE_INT) 0xffff << INTVAL (operands[2])
2252         == (unsigned HOST_WIDE_INT) INTVAL (operands[3]))
2253        || ((unsigned HOST_WIDE_INT) 0xffffffff << INTVAL (operands[2])
2254         == (unsigned HOST_WIDE_INT) INTVAL (operands[3])))"
2255 {
2256 #if HOST_BITS_PER_WIDE_INT == 64
2257   if ((unsigned HOST_WIDE_INT) 0xff << INTVAL (operands[2])
2258       == (unsigned HOST_WIDE_INT) INTVAL (operands[3]))
2259     return "insbl %1,%s2,%0";
2260   if ((unsigned HOST_WIDE_INT) 0xffff << INTVAL (operands[2])
2261       == (unsigned HOST_WIDE_INT) INTVAL (operands[3]))
2262     return "inswl %1,%s2,%0";
2263   if ((unsigned HOST_WIDE_INT) 0xffffffff << INTVAL (operands[2])
2264       == (unsigned HOST_WIDE_INT) INTVAL (operands[3]))
2265     return "insll %1,%s2,%0";
2266 #endif
2267   abort();
2268 }
2269   [(set_attr "type" "shift")])
2270
2271 ;; We do not include the insXh insns because they are complex to express
2272 ;; and it does not appear that we would ever want to generate them.
2273 ;;
2274 ;; Since we need them for block moves, though, cop out and use unspec.
2275
2276 (define_insn "insxh"
2277   [(set (match_operand:DI 0 "register_operand" "=r")
2278         (unspec:DI [(match_operand:DI 1 "register_operand" "r")
2279                     (match_operand:DI 2 "mode_width_operand" "n")
2280                     (match_operand:DI 3 "reg_or_8bit_operand" "rI")]
2281                    UNSPEC_INSXH))]
2282   ""
2283   "ins%M2h %1,%3,%0"
2284   [(set_attr "type" "shift")])
2285
2286 (define_insn "mskxl_le"
2287   [(set (match_operand:DI 0 "register_operand" "=r")
2288         (and:DI (not:DI (ashift:DI
2289                          (match_operand:DI 2 "mode_mask_operand" "n")
2290                          (ashift:DI
2291                           (match_operand:DI 3 "reg_or_8bit_operand" "rI")
2292                           (const_int 3))))
2293                 (match_operand:DI 1 "reg_or_0_operand" "rJ")))]
2294   "! WORDS_BIG_ENDIAN"
2295   "msk%U2l %r1,%3,%0"
2296   [(set_attr "type" "shift")])
2297
2298 (define_insn "mskxl_be"
2299   [(set (match_operand:DI 0 "register_operand" "=r")
2300         (and:DI (not:DI (ashift:DI
2301                           (match_operand:DI 2 "mode_mask_operand" "n")
2302                           (minus:DI (const_int 56)
2303                             (ashift:DI
2304                               (match_operand:DI 3 "reg_or_8bit_operand" "rI")
2305                               (const_int 3)))))
2306                 (match_operand:DI 1 "reg_or_0_operand" "rJ")))]
2307   "WORDS_BIG_ENDIAN"
2308   "msk%U2l %r1,%3,%0"
2309   [(set_attr "type" "shift")])
2310
2311 ;; We do not include the mskXh insns because it does not appear we would
2312 ;; ever generate one.
2313 ;;
2314 ;; Again, we do for block moves and we use unspec again.
2315
2316 (define_insn "mskxh"
2317   [(set (match_operand:DI 0 "register_operand" "=r")
2318         (unspec:DI [(match_operand:DI 1 "register_operand" "r")
2319                     (match_operand:DI 2 "mode_width_operand" "n")
2320                     (match_operand:DI 3 "reg_or_8bit_operand" "rI")]
2321                    UNSPEC_MSKXH))]
2322   ""
2323   "msk%M2h %1,%3,%0"
2324   [(set_attr "type" "shift")])
2325
2326 ;; Prefer AND + NE over LSHIFTRT + AND.
2327
2328 (define_insn_and_split "*ze_and_ne"
2329   [(set (match_operand:DI 0 "register_operand" "=r")
2330         (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
2331                          (const_int 1)
2332                          (match_operand 2 "const_int_operand" "I")))]
2333   "(unsigned HOST_WIDE_INT) INTVAL (operands[2]) < 8"
2334   "#"
2335   "(unsigned HOST_WIDE_INT) INTVAL (operands[2]) < 8"
2336   [(set (match_dup 0)
2337         (and:DI (match_dup 1) (match_dup 3)))
2338    (set (match_dup 0)
2339         (ne:DI (match_dup 0) (const_int 0)))]
2340   "operands[3] = GEN_INT (1 << INTVAL (operands[2]));")
2341 \f
2342 ;; Floating-point operations.  All the double-precision insns can extend
2343 ;; from single, so indicate that.  The exception are the ones that simply
2344 ;; play with the sign bits; it's not clear what to do there.
2345
2346 (define_insn "abssf2"
2347   [(set (match_operand:SF 0 "register_operand" "=f")
2348         (abs:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")))]
2349   "TARGET_FP"
2350   "cpys $f31,%R1,%0"
2351   [(set_attr "type" "fcpys")])
2352
2353 (define_insn "*nabssf2"
2354   [(set (match_operand:SF 0 "register_operand" "=f")
2355         (neg:SF (abs:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG"))))]
2356   "TARGET_FP"
2357   "cpysn $f31,%R1,%0"
2358   [(set_attr "type" "fadd")])
2359
2360 (define_insn "absdf2"
2361   [(set (match_operand:DF 0 "register_operand" "=f")
2362         (abs:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
2363   "TARGET_FP"
2364   "cpys $f31,%R1,%0"
2365   [(set_attr "type" "fcpys")])
2366
2367 (define_insn "*nabsdf2"
2368   [(set (match_operand:DF 0 "register_operand" "=f")
2369         (neg:DF (abs:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG"))))]
2370   "TARGET_FP"
2371   "cpysn $f31,%R1,%0"
2372   [(set_attr "type" "fadd")])
2373
2374 (define_expand "abstf2"
2375   [(parallel [(set (match_operand:TF 0 "register_operand" "")
2376                    (neg:TF (match_operand:TF 1 "reg_or_fp0_operand" "")))
2377               (use (match_dup 2))])]
2378   "TARGET_HAS_XFLOATING_LIBS"
2379 {
2380 #if HOST_BITS_PER_WIDE_INT >= 64
2381   operands[2] = force_reg (DImode, GEN_INT ((HOST_WIDE_INT) 1 << 63));
2382 #else
2383   operands[2] = force_reg (DImode, immed_double_const (0, 0x80000000, DImode));
2384 #endif
2385 })
2386
2387 (define_insn_and_split "*abstf_internal"
2388   [(set (match_operand:TF 0 "register_operand" "=r")
2389         (abs:TF (match_operand:TF 1 "reg_or_fp0_operand" "rG")))
2390    (use (match_operand:DI 2 "register_operand" "r"))]
2391   "TARGET_HAS_XFLOATING_LIBS"
2392   "#"
2393   "&& reload_completed"
2394   [(const_int 0)]
2395   "alpha_split_tfmode_frobsign (operands, gen_andnotdi3); DONE;")
2396
2397 (define_insn "negsf2"
2398   [(set (match_operand:SF 0 "register_operand" "=f")
2399         (neg:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")))]
2400   "TARGET_FP"
2401   "cpysn %R1,%R1,%0"
2402   [(set_attr "type" "fadd")])
2403
2404 (define_insn "negdf2"
2405   [(set (match_operand:DF 0 "register_operand" "=f")
2406         (neg:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
2407   "TARGET_FP"
2408   "cpysn %R1,%R1,%0"
2409   [(set_attr "type" "fadd")])
2410
2411 (define_expand "negtf2"
2412   [(parallel [(set (match_operand:TF 0 "register_operand" "")
2413                    (neg:TF (match_operand:TF 1 "reg_or_fp0_operand" "")))
2414               (use (match_dup 2))])]
2415   "TARGET_HAS_XFLOATING_LIBS"
2416 {
2417 #if HOST_BITS_PER_WIDE_INT >= 64
2418   operands[2] = force_reg (DImode, GEN_INT ((HOST_WIDE_INT) 1 << 63));
2419 #else
2420   operands[2] = force_reg (DImode, immed_double_const (0, 0x80000000, DImode));
2421 #endif
2422 })
2423
2424 (define_insn_and_split "*negtf_internal"
2425   [(set (match_operand:TF 0 "register_operand" "=r")
2426         (neg:TF (match_operand:TF 1 "reg_or_fp0_operand" "rG")))
2427    (use (match_operand:DI 2 "register_operand" "r"))]
2428   "TARGET_HAS_XFLOATING_LIBS"
2429   "#"
2430   "&& reload_completed"
2431   [(const_int 0)]
2432   "alpha_split_tfmode_frobsign (operands, gen_xordi3); DONE;")
2433
2434 (define_insn "*addsf_ieee"
2435   [(set (match_operand:SF 0 "register_operand" "=&f")
2436         (plus:SF (match_operand:SF 1 "reg_or_fp0_operand" "%fG")
2437                  (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2438   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2439   "add%,%/ %R1,%R2,%0"
2440   [(set_attr "type" "fadd")
2441    (set_attr "trap" "yes")
2442    (set_attr "round_suffix" "normal")
2443    (set_attr "trap_suffix" "u_su_sui")])
2444
2445 (define_insn "addsf3"
2446   [(set (match_operand:SF 0 "register_operand" "=f")
2447         (plus:SF (match_operand:SF 1 "reg_or_fp0_operand" "%fG")
2448                  (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2449   "TARGET_FP"
2450   "add%,%/ %R1,%R2,%0"
2451   [(set_attr "type" "fadd")
2452    (set_attr "trap" "yes")
2453    (set_attr "round_suffix" "normal")
2454    (set_attr "trap_suffix" "u_su_sui")])
2455
2456 (define_insn "*adddf_ieee"
2457   [(set (match_operand:DF 0 "register_operand" "=&f")
2458         (plus:DF (match_operand:DF 1 "reg_or_fp0_operand" "%fG")
2459                  (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2460   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2461   "add%-%/ %R1,%R2,%0"
2462   [(set_attr "type" "fadd")
2463    (set_attr "trap" "yes")
2464    (set_attr "round_suffix" "normal")
2465    (set_attr "trap_suffix" "u_su_sui")])
2466
2467 (define_insn "adddf3"
2468   [(set (match_operand:DF 0 "register_operand" "=f")
2469         (plus:DF (match_operand:DF 1 "reg_or_fp0_operand" "%fG")
2470                  (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2471   "TARGET_FP"
2472   "add%-%/ %R1,%R2,%0"
2473   [(set_attr "type" "fadd")
2474    (set_attr "trap" "yes")
2475    (set_attr "round_suffix" "normal")
2476    (set_attr "trap_suffix" "u_su_sui")])
2477
2478 (define_insn "*adddf_ext1"
2479   [(set (match_operand:DF 0 "register_operand" "=f")
2480         (plus:DF (float_extend:DF
2481                   (match_operand:SF 1 "reg_or_fp0_operand" "fG"))
2482                  (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2483   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
2484   "add%-%/ %R1,%R2,%0"
2485   [(set_attr "type" "fadd")
2486    (set_attr "trap" "yes")
2487    (set_attr "round_suffix" "normal")
2488    (set_attr "trap_suffix" "u_su_sui")])
2489
2490 (define_insn "*adddf_ext2"
2491   [(set (match_operand:DF 0 "register_operand" "=f")
2492         (plus:DF (float_extend:DF
2493                   (match_operand:SF 1 "reg_or_fp0_operand" "%fG"))
2494                  (float_extend:DF
2495                   (match_operand:SF 2 "reg_or_fp0_operand" "fG"))))]
2496   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
2497   "add%-%/ %R1,%R2,%0"
2498   [(set_attr "type" "fadd")
2499    (set_attr "trap" "yes")
2500    (set_attr "round_suffix" "normal")
2501    (set_attr "trap_suffix" "u_su_sui")])
2502
2503 (define_expand "addtf3"
2504   [(use (match_operand 0 "register_operand" ""))
2505    (use (match_operand 1 "general_operand" ""))
2506    (use (match_operand 2 "general_operand" ""))]
2507   "TARGET_HAS_XFLOATING_LIBS"
2508   "alpha_emit_xfloating_arith (PLUS, operands); DONE;")
2509
2510 ;; Define conversion operators between DFmode and SImode, using the cvtql
2511 ;; instruction.  To allow combine et al to do useful things, we keep the
2512 ;; operation as a unit until after reload, at which point we split the
2513 ;; instructions.
2514 ;;
2515 ;; Note that we (attempt to) only consider this optimization when the
2516 ;; ultimate destination is memory.  If we will be doing further integer
2517 ;; processing, it is cheaper to do the truncation in the int regs.
2518
2519 (define_insn "*cvtql"
2520   [(set (match_operand:SI 0 "register_operand" "=f")
2521         (unspec:SI [(match_operand:DI 1 "reg_or_fp0_operand" "fG")]
2522                    UNSPEC_CVTQL))]
2523   "TARGET_FP"
2524   "cvtql%/ %R1,%0"
2525   [(set_attr "type" "fadd")
2526    (set_attr "trap" "yes")
2527    (set_attr "trap_suffix" "v_sv")])
2528
2529 (define_insn_and_split "*fix_truncdfsi_ieee"
2530   [(set (match_operand:SI 0 "memory_operand" "=m")
2531         (subreg:SI (fix:DI (match_operand:DF 1 "reg_or_fp0_operand" "fG")) 0))
2532    (clobber (match_scratch:DI 2 "=&f"))
2533    (clobber (match_scratch:SI 3 "=&f"))]
2534   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2535   "#"
2536   "&& reload_completed"
2537   [(set (match_dup 2) (fix:DI (match_dup 1)))
2538    (set (match_dup 3) (unspec:SI [(match_dup 2)] UNSPEC_CVTQL))
2539    (set (match_dup 0) (match_dup 3))]
2540   ""
2541   [(set_attr "type" "fadd")
2542    (set_attr "trap" "yes")])
2543
2544 (define_insn_and_split "*fix_truncdfsi_internal"
2545   [(set (match_operand:SI 0 "memory_operand" "=m")
2546         (subreg:SI (fix:DI (match_operand:DF 1 "reg_or_fp0_operand" "fG")) 0))
2547    (clobber (match_scratch:DI 2 "=f"))]
2548   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
2549   "#"
2550   "&& reload_completed"
2551   [(set (match_dup 2) (fix:DI (match_dup 1)))
2552    (set (match_dup 3) (unspec:SI [(match_dup 2)] UNSPEC_CVTQL))
2553    (set (match_dup 0) (match_dup 3))]
2554   ;; Due to REG_CANNOT_CHANGE_SIZE issues, we cannot simply use SUBREG.
2555   "operands[3] = gen_rtx_REG (SImode, REGNO (operands[2]));"
2556   [(set_attr "type" "fadd")
2557    (set_attr "trap" "yes")])
2558
2559 (define_insn "*fix_truncdfdi_ieee"
2560   [(set (match_operand:DI 0 "reg_no_subreg_operand" "=&f")
2561         (fix:DI (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
2562   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2563   "cvt%-q%/ %R1,%0"
2564   [(set_attr "type" "fadd")
2565    (set_attr "trap" "yes")
2566    (set_attr "round_suffix" "c")
2567    (set_attr "trap_suffix" "v_sv_svi")])
2568
2569 (define_insn "fix_truncdfdi2"
2570   [(set (match_operand:DI 0 "reg_no_subreg_operand" "=f")
2571         (fix:DI (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
2572   "TARGET_FP"
2573   "cvt%-q%/ %R1,%0"
2574   [(set_attr "type" "fadd")
2575    (set_attr "trap" "yes")
2576    (set_attr "round_suffix" "c")
2577    (set_attr "trap_suffix" "v_sv_svi")])
2578
2579 ;; Likewise between SFmode and SImode.
2580
2581 (define_insn_and_split "*fix_truncsfsi_ieee"
2582   [(set (match_operand:SI 0 "memory_operand" "=m")
2583         (subreg:SI (fix:DI (float_extend:DF
2584                  (match_operand:SF 1 "reg_or_fp0_operand" "fG"))) 0))
2585    (clobber (match_scratch:DI 2 "=&f"))
2586    (clobber (match_scratch:SI 3 "=&f"))]
2587   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2588   "#"
2589   "&& reload_completed"
2590   [(set (match_dup 2) (fix:DI (float_extend:DF (match_dup 1))))
2591    (set (match_dup 3) (unspec:SI [(match_dup 2)] UNSPEC_CVTQL))
2592    (set (match_dup 0) (match_dup 3))]
2593   ""
2594   [(set_attr "type" "fadd")
2595    (set_attr "trap" "yes")])
2596
2597 (define_insn_and_split "*fix_truncsfsi_internal"
2598   [(set (match_operand:SI 0 "memory_operand" "=m")
2599         (subreg:SI (fix:DI (float_extend:DF
2600                  (match_operand:SF 1 "reg_or_fp0_operand" "fG"))) 0))
2601    (clobber (match_scratch:DI 2 "=f"))]
2602   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
2603   "#"
2604   "&& reload_completed"
2605   [(set (match_dup 2) (fix:DI (float_extend:DF (match_dup 1))))
2606    (set (match_dup 3) (unspec:SI [(match_dup 2)] UNSPEC_CVTQL))
2607    (set (match_dup 0) (match_dup 3))]
2608   ;; Due to REG_CANNOT_CHANGE_SIZE issues, we cannot simply use SUBREG.
2609   "operands[3] = gen_rtx_REG (SImode, REGNO (operands[2]));"
2610   [(set_attr "type" "fadd")
2611    (set_attr "trap" "yes")])
2612
2613 (define_insn "*fix_truncsfdi_ieee"
2614   [(set (match_operand:DI 0 "reg_no_subreg_operand" "=&f")
2615         (fix:DI (float_extend:DF
2616                  (match_operand:SF 1 "reg_or_fp0_operand" "fG"))))]
2617   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2618   "cvt%-q%/ %R1,%0"
2619   [(set_attr "type" "fadd")
2620    (set_attr "trap" "yes")
2621    (set_attr "round_suffix" "c")
2622    (set_attr "trap_suffix" "v_sv_svi")])
2623
2624 (define_insn "fix_truncsfdi2"
2625   [(set (match_operand:DI 0 "reg_no_subreg_operand" "=f")
2626         (fix:DI (float_extend:DF
2627                  (match_operand:SF 1 "reg_or_fp0_operand" "fG"))))]
2628   "TARGET_FP"
2629   "cvt%-q%/ %R1,%0"
2630   [(set_attr "type" "fadd")
2631    (set_attr "trap" "yes")
2632    (set_attr "round_suffix" "c")
2633    (set_attr "trap_suffix" "v_sv_svi")])
2634
2635 (define_expand "fix_trunctfdi2"
2636   [(use (match_operand:DI 0 "register_operand" ""))
2637    (use (match_operand:TF 1 "general_operand" ""))]
2638   "TARGET_HAS_XFLOATING_LIBS"
2639   "alpha_emit_xfloating_cvt (FIX, operands); DONE;")
2640
2641 (define_insn "*floatdisf_ieee"
2642   [(set (match_operand:SF 0 "register_operand" "=&f")
2643         (float:SF (match_operand:DI 1 "reg_no_subreg_operand" "f")))]
2644   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2645   "cvtq%,%/ %1,%0"
2646   [(set_attr "type" "fadd")
2647    (set_attr "trap" "yes")
2648    (set_attr "round_suffix" "normal")
2649    (set_attr "trap_suffix" "sui")])
2650
2651 (define_insn "floatdisf2"
2652   [(set (match_operand:SF 0 "register_operand" "=f")
2653         (float:SF (match_operand:DI 1 "reg_no_subreg_operand" "f")))]
2654   "TARGET_FP"
2655   "cvtq%,%/ %1,%0"
2656   [(set_attr "type" "fadd")
2657    (set_attr "trap" "yes")
2658    (set_attr "round_suffix" "normal")
2659    (set_attr "trap_suffix" "sui")])
2660
2661 (define_insn "*floatdidf_ieee"
2662   [(set (match_operand:DF 0 "register_operand" "=&f")
2663         (float:DF (match_operand:DI 1 "reg_no_subreg_operand" "f")))]
2664   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2665   "cvtq%-%/ %1,%0"
2666   [(set_attr "type" "fadd")
2667    (set_attr "trap" "yes")
2668    (set_attr "round_suffix" "normal")
2669    (set_attr "trap_suffix" "sui")])
2670
2671 (define_insn "floatdidf2"
2672   [(set (match_operand:DF 0 "register_operand" "=f")
2673         (float:DF (match_operand:DI 1 "reg_no_subreg_operand" "f")))]
2674   "TARGET_FP"
2675   "cvtq%-%/ %1,%0"
2676   [(set_attr "type" "fadd")
2677    (set_attr "trap" "yes")
2678    (set_attr "round_suffix" "normal")
2679    (set_attr "trap_suffix" "sui")])
2680
2681 (define_expand "floatditf2"
2682   [(use (match_operand:TF 0 "register_operand" ""))
2683    (use (match_operand:DI 1 "general_operand" ""))]
2684   "TARGET_HAS_XFLOATING_LIBS"
2685   "alpha_emit_xfloating_cvt (FLOAT, operands); DONE;")
2686
2687 (define_expand "floatunsdisf2"
2688   [(use (match_operand:SF 0 "register_operand" ""))
2689    (use (match_operand:DI 1 "register_operand" ""))]
2690   "TARGET_FP"
2691   "alpha_emit_floatuns (operands); DONE;")
2692
2693 (define_expand "floatunsdidf2"
2694   [(use (match_operand:DF 0 "register_operand" ""))
2695    (use (match_operand:DI 1 "register_operand" ""))]
2696   "TARGET_FP"
2697   "alpha_emit_floatuns (operands); DONE;")
2698
2699 (define_expand "floatunsditf2"
2700   [(use (match_operand:TF 0 "register_operand" ""))
2701    (use (match_operand:DI 1 "general_operand" ""))]
2702   "TARGET_HAS_XFLOATING_LIBS"
2703   "alpha_emit_xfloating_cvt (UNSIGNED_FLOAT, operands); DONE;")
2704
2705 (define_expand "extendsfdf2"
2706   [(set (match_operand:DF 0 "register_operand" "")
2707         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "")))]
2708   "TARGET_FP"
2709 {
2710   if (alpha_fptm >= ALPHA_FPTM_SU)
2711     operands[1] = force_reg (SFmode, operands[1]);
2712 })
2713
2714 ;; The Unicos/Mk assembler doesn't support cvtst, but we've already
2715 ;; asserted that alpha_fptm == ALPHA_FPTM_N.
2716
2717 (define_insn "*extendsfdf2_ieee"
2718   [(set (match_operand:DF 0 "register_operand" "=&f")
2719         (float_extend:DF (match_operand:SF 1 "register_operand" "f")))]
2720   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2721   "cvtsts %1,%0"
2722   [(set_attr "type" "fadd")
2723    (set_attr "trap" "yes")])
2724
2725 (define_insn "*extendsfdf2_internal"
2726   [(set (match_operand:DF 0 "register_operand" "=f,f,m")
2727         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "f,m,f")))]
2728   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
2729   "@
2730    cpys %1,%1,%0
2731    ld%, %0,%1
2732    st%- %1,%0"
2733   [(set_attr "type" "fcpys,fld,fst")])
2734
2735 (define_expand "extendsftf2"
2736   [(use (match_operand:TF 0 "register_operand" ""))
2737    (use (match_operand:SF 1 "general_operand" ""))]
2738   "TARGET_HAS_XFLOATING_LIBS"
2739 {
2740   rtx tmp = gen_reg_rtx (DFmode);
2741   emit_insn (gen_extendsfdf2 (tmp, operands[1]));
2742   emit_insn (gen_extenddftf2 (operands[0], tmp));
2743   DONE;
2744 })
2745
2746 (define_expand "extenddftf2"
2747   [(use (match_operand:TF 0 "register_operand" ""))
2748    (use (match_operand:DF 1 "general_operand" ""))]
2749   "TARGET_HAS_XFLOATING_LIBS"
2750   "alpha_emit_xfloating_cvt (FLOAT_EXTEND, operands); DONE;")
2751
2752 (define_insn "*truncdfsf2_ieee"
2753   [(set (match_operand:SF 0 "register_operand" "=&f")
2754         (float_truncate:SF (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
2755   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2756   "cvt%-%,%/ %R1,%0"
2757   [(set_attr "type" "fadd")
2758    (set_attr "trap" "yes")
2759    (set_attr "round_suffix" "normal")
2760    (set_attr "trap_suffix" "u_su_sui")])
2761
2762 (define_insn "truncdfsf2"
2763   [(set (match_operand:SF 0 "register_operand" "=f")
2764         (float_truncate:SF (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
2765   "TARGET_FP"
2766   "cvt%-%,%/ %R1,%0"
2767   [(set_attr "type" "fadd")
2768    (set_attr "trap" "yes")
2769    (set_attr "round_suffix" "normal")
2770    (set_attr "trap_suffix" "u_su_sui")])
2771
2772 (define_expand "trunctfdf2"
2773   [(use (match_operand:DF 0 "register_operand" ""))
2774    (use (match_operand:TF 1 "general_operand" ""))]
2775   "TARGET_HAS_XFLOATING_LIBS"
2776   "alpha_emit_xfloating_cvt (FLOAT_TRUNCATE, operands); DONE;")
2777
2778 (define_expand "trunctfsf2"
2779   [(use (match_operand:SF 0 "register_operand" ""))
2780    (use (match_operand:TF 1 "general_operand" ""))]
2781   "TARGET_FP && TARGET_HAS_XFLOATING_LIBS"
2782 {
2783   rtx tmpf, sticky, arg, lo, hi;
2784
2785   tmpf = gen_reg_rtx (DFmode);
2786   sticky = gen_reg_rtx (DImode);
2787   arg = copy_to_mode_reg (TFmode, operands[1]);
2788   lo = gen_lowpart (DImode, arg);
2789   hi = gen_highpart (DImode, arg);
2790
2791   /* Convert the low word of the TFmode value into a sticky rounding bit,
2792      then or it into the low bit of the high word.  This leaves the sticky
2793      bit at bit 48 of the fraction, which is representable in DFmode,
2794      which prevents rounding error in the final conversion to SFmode.  */
2795
2796   emit_insn (gen_rtx_SET (VOIDmode, sticky,
2797                           gen_rtx_NE (DImode, lo, const0_rtx)));
2798   emit_insn (gen_iordi3 (hi, hi, sticky));
2799   emit_insn (gen_trunctfdf2 (tmpf, arg));
2800   emit_insn (gen_truncdfsf2 (operands[0], tmpf));
2801   DONE;
2802 })
2803
2804 (define_insn "*divsf3_ieee"
2805   [(set (match_operand:SF 0 "register_operand" "=&f")
2806         (div:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")
2807                 (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2808   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2809   "div%,%/ %R1,%R2,%0"
2810   [(set_attr "type" "fdiv")
2811    (set_attr "opsize" "si")
2812    (set_attr "trap" "yes")
2813    (set_attr "round_suffix" "normal")
2814    (set_attr "trap_suffix" "u_su_sui")])
2815
2816 (define_insn "divsf3"
2817   [(set (match_operand:SF 0 "register_operand" "=f")
2818         (div:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")
2819                 (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2820   "TARGET_FP"
2821   "div%,%/ %R1,%R2,%0"
2822   [(set_attr "type" "fdiv")
2823    (set_attr "opsize" "si")
2824    (set_attr "trap" "yes")
2825    (set_attr "round_suffix" "normal")
2826    (set_attr "trap_suffix" "u_su_sui")])
2827
2828 (define_insn "*divdf3_ieee"
2829   [(set (match_operand:DF 0 "register_operand" "=&f")
2830         (div:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")
2831                 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2832   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2833   "div%-%/ %R1,%R2,%0"
2834   [(set_attr "type" "fdiv")
2835    (set_attr "trap" "yes")
2836    (set_attr "round_suffix" "normal")
2837    (set_attr "trap_suffix" "u_su_sui")])
2838
2839 (define_insn "divdf3"
2840   [(set (match_operand:DF 0 "register_operand" "=f")
2841         (div:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")
2842                 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2843   "TARGET_FP"
2844   "div%-%/ %R1,%R2,%0"
2845   [(set_attr "type" "fdiv")
2846    (set_attr "trap" "yes")
2847    (set_attr "round_suffix" "normal")
2848    (set_attr "trap_suffix" "u_su_sui")])
2849
2850 (define_insn "*divdf_ext1"
2851   [(set (match_operand:DF 0 "register_operand" "=f")
2852         (div:DF (float_extend:DF (match_operand:SF 1 "reg_or_fp0_operand" "fG"))
2853                 (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2854   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
2855   "div%-%/ %R1,%R2,%0"
2856   [(set_attr "type" "fdiv")
2857    (set_attr "trap" "yes")
2858    (set_attr "round_suffix" "normal")
2859    (set_attr "trap_suffix" "u_su_sui")])
2860
2861 (define_insn "*divdf_ext2"
2862   [(set (match_operand:DF 0 "register_operand" "=f")
2863         (div:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")
2864                 (float_extend:DF
2865                  (match_operand:SF 2 "reg_or_fp0_operand" "fG"))))]
2866   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
2867   "div%-%/ %R1,%R2,%0"
2868   [(set_attr "type" "fdiv")
2869    (set_attr "trap" "yes")
2870    (set_attr "round_suffix" "normal")
2871    (set_attr "trap_suffix" "u_su_sui")])
2872
2873 (define_insn "*divdf_ext3"
2874   [(set (match_operand:DF 0 "register_operand" "=f")
2875         (div:DF (float_extend:DF (match_operand:SF 1 "reg_or_fp0_operand" "fG"))
2876                 (float_extend:DF (match_operand:SF 2 "reg_or_fp0_operand" "fG"))))]
2877   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
2878   "div%-%/ %R1,%R2,%0"
2879   [(set_attr "type" "fdiv")
2880    (set_attr "trap" "yes")
2881    (set_attr "round_suffix" "normal")
2882    (set_attr "trap_suffix" "u_su_sui")])
2883
2884 (define_expand "divtf3"
2885   [(use (match_operand 0 "register_operand" ""))
2886    (use (match_operand 1 "general_operand" ""))
2887    (use (match_operand 2 "general_operand" ""))]
2888   "TARGET_HAS_XFLOATING_LIBS"
2889   "alpha_emit_xfloating_arith (DIV, operands); DONE;")
2890
2891 (define_insn "*mulsf3_ieee"
2892   [(set (match_operand:SF 0 "register_operand" "=&f")
2893         (mult:SF (match_operand:SF 1 "reg_or_fp0_operand" "%fG")
2894                  (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2895   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2896   "mul%,%/ %R1,%R2,%0"
2897   [(set_attr "type" "fmul")
2898    (set_attr "trap" "yes")
2899    (set_attr "round_suffix" "normal")
2900    (set_attr "trap_suffix" "u_su_sui")])
2901
2902 (define_insn "mulsf3"
2903   [(set (match_operand:SF 0 "register_operand" "=f")
2904         (mult:SF (match_operand:SF 1 "reg_or_fp0_operand" "%fG")
2905                  (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2906   "TARGET_FP"
2907   "mul%,%/ %R1,%R2,%0"
2908   [(set_attr "type" "fmul")
2909    (set_attr "trap" "yes")
2910    (set_attr "round_suffix" "normal")
2911    (set_attr "trap_suffix" "u_su_sui")])
2912
2913 (define_insn "*muldf3_ieee"
2914   [(set (match_operand:DF 0 "register_operand" "=&f")
2915         (mult:DF (match_operand:DF 1 "reg_or_fp0_operand" "%fG")
2916                  (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2917   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2918   "mul%-%/ %R1,%R2,%0"
2919   [(set_attr "type" "fmul")
2920    (set_attr "trap" "yes")
2921    (set_attr "round_suffix" "normal")
2922    (set_attr "trap_suffix" "u_su_sui")])
2923
2924 (define_insn "muldf3"
2925   [(set (match_operand:DF 0 "register_operand" "=f")
2926         (mult:DF (match_operand:DF 1 "reg_or_fp0_operand" "%fG")
2927                  (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2928   "TARGET_FP"
2929   "mul%-%/ %R1,%R2,%0"
2930   [(set_attr "type" "fmul")
2931    (set_attr "trap" "yes")
2932    (set_attr "round_suffix" "normal")
2933    (set_attr "trap_suffix" "u_su_sui")])
2934
2935 (define_insn "*muldf_ext1"
2936   [(set (match_operand:DF 0 "register_operand" "=f")
2937         (mult:DF (float_extend:DF
2938                   (match_operand:SF 1 "reg_or_fp0_operand" "fG"))
2939                  (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2940   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
2941   "mul%-%/ %R1,%R2,%0"
2942   [(set_attr "type" "fmul")
2943    (set_attr "trap" "yes")
2944    (set_attr "round_suffix" "normal")
2945    (set_attr "trap_suffix" "u_su_sui")])
2946
2947 (define_insn "*muldf_ext2"
2948   [(set (match_operand:DF 0 "register_operand" "=f")
2949         (mult:DF (float_extend:DF
2950                   (match_operand:SF 1 "reg_or_fp0_operand" "%fG"))
2951                  (float_extend:DF
2952                   (match_operand:SF 2 "reg_or_fp0_operand" "fG"))))]
2953   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
2954   "mul%-%/ %R1,%R2,%0"
2955   [(set_attr "type" "fmul")
2956    (set_attr "trap" "yes")
2957    (set_attr "round_suffix" "normal")
2958    (set_attr "trap_suffix" "u_su_sui")])
2959
2960 (define_expand "multf3"
2961   [(use (match_operand 0 "register_operand" ""))
2962    (use (match_operand 1 "general_operand" ""))
2963    (use (match_operand 2 "general_operand" ""))]
2964   "TARGET_HAS_XFLOATING_LIBS"
2965   "alpha_emit_xfloating_arith (MULT, operands); DONE;")
2966
2967 (define_insn "*subsf3_ieee"
2968   [(set (match_operand:SF 0 "register_operand" "=&f")
2969         (minus:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")
2970                   (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2971   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2972   "sub%,%/ %R1,%R2,%0"
2973   [(set_attr "type" "fadd")
2974    (set_attr "trap" "yes")
2975    (set_attr "round_suffix" "normal")
2976    (set_attr "trap_suffix" "u_su_sui")])
2977
2978 (define_insn "subsf3"
2979   [(set (match_operand:SF 0 "register_operand" "=f")
2980         (minus:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")
2981                   (match_operand:SF 2 "reg_or_fp0_operand" "fG")))]
2982   "TARGET_FP"
2983   "sub%,%/ %R1,%R2,%0"
2984   [(set_attr "type" "fadd")
2985    (set_attr "trap" "yes")
2986    (set_attr "round_suffix" "normal")
2987    (set_attr "trap_suffix" "u_su_sui")])
2988
2989 (define_insn "*subdf3_ieee"
2990   [(set (match_operand:DF 0 "register_operand" "=&f")
2991         (minus:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")
2992                   (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
2993   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
2994   "sub%-%/ %R1,%R2,%0"
2995   [(set_attr "type" "fadd")
2996    (set_attr "trap" "yes")
2997    (set_attr "round_suffix" "normal")
2998    (set_attr "trap_suffix" "u_su_sui")])
2999
3000 (define_insn "subdf3"
3001   [(set (match_operand:DF 0 "register_operand" "=f")
3002         (minus:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")
3003                   (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
3004   "TARGET_FP"
3005   "sub%-%/ %R1,%R2,%0"
3006   [(set_attr "type" "fadd")
3007    (set_attr "trap" "yes")
3008    (set_attr "round_suffix" "normal")
3009    (set_attr "trap_suffix" "u_su_sui")])
3010
3011 (define_insn "*subdf_ext1"
3012   [(set (match_operand:DF 0 "register_operand" "=f")
3013         (minus:DF (float_extend:DF
3014                    (match_operand:SF 1 "reg_or_fp0_operand" "fG"))
3015                   (match_operand:DF 2 "reg_or_fp0_operand" "fG")))]
3016   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
3017   "sub%-%/ %R1,%R2,%0"
3018   [(set_attr "type" "fadd")
3019    (set_attr "trap" "yes")
3020    (set_attr "round_suffix" "normal")
3021    (set_attr "trap_suffix" "u_su_sui")])
3022
3023 (define_insn "*subdf_ext2"
3024   [(set (match_operand:DF 0 "register_operand" "=f")
3025         (minus:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")
3026                   (float_extend:DF
3027                    (match_operand:SF 2 "reg_or_fp0_operand" "fG"))))]
3028   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
3029   "sub%-%/ %R1,%R2,%0"
3030   [(set_attr "type" "fadd")
3031    (set_attr "trap" "yes")
3032    (set_attr "round_suffix" "normal")
3033    (set_attr "trap_suffix" "u_su_sui")])
3034
3035 (define_insn "*subdf_ext3"
3036   [(set (match_operand:DF 0 "register_operand" "=f")
3037         (minus:DF (float_extend:DF
3038                    (match_operand:SF 1 "reg_or_fp0_operand" "fG"))
3039                   (float_extend:DF
3040                    (match_operand:SF 2 "reg_or_fp0_operand" "fG"))))]
3041   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
3042   "sub%-%/ %R1,%R2,%0"
3043   [(set_attr "type" "fadd")
3044    (set_attr "trap" "yes")
3045    (set_attr "round_suffix" "normal")
3046    (set_attr "trap_suffix" "u_su_sui")])
3047
3048 (define_expand "subtf3"
3049   [(use (match_operand 0 "register_operand" ""))
3050    (use (match_operand 1 "general_operand" ""))
3051    (use (match_operand 2 "general_operand" ""))]
3052   "TARGET_HAS_XFLOATING_LIBS"
3053   "alpha_emit_xfloating_arith (MINUS, operands); DONE;")
3054
3055 (define_insn "*sqrtsf2_ieee"
3056   [(set (match_operand:SF 0 "register_operand" "=&f")
3057         (sqrt:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")))]
3058   "TARGET_FP && TARGET_FIX && alpha_fptm >= ALPHA_FPTM_SU"
3059   "sqrt%,%/ %R1,%0"
3060   [(set_attr "type" "fsqrt")
3061    (set_attr "opsize" "si")
3062    (set_attr "trap" "yes")
3063    (set_attr "round_suffix" "normal")
3064    (set_attr "trap_suffix" "u_su_sui")])
3065
3066 (define_insn "sqrtsf2"
3067   [(set (match_operand:SF 0 "register_operand" "=f")
3068         (sqrt:SF (match_operand:SF 1 "reg_or_fp0_operand" "fG")))]
3069   "TARGET_FP && TARGET_FIX"
3070   "sqrt%,%/ %R1,%0"
3071   [(set_attr "type" "fsqrt")
3072    (set_attr "opsize" "si")
3073    (set_attr "trap" "yes")
3074    (set_attr "round_suffix" "normal")
3075    (set_attr "trap_suffix" "u_su_sui")])
3076
3077 (define_insn "*sqrtdf2_ieee"
3078   [(set (match_operand:DF 0 "register_operand" "=&f")
3079         (sqrt:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
3080   "TARGET_FP && TARGET_FIX && alpha_fptm >= ALPHA_FPTM_SU"
3081   "sqrt%-%/ %R1,%0"
3082   [(set_attr "type" "fsqrt")
3083    (set_attr "trap" "yes")
3084    (set_attr "round_suffix" "normal")
3085    (set_attr "trap_suffix" "u_su_sui")])
3086
3087 (define_insn "sqrtdf2"
3088   [(set (match_operand:DF 0 "register_operand" "=f")
3089         (sqrt:DF (match_operand:DF 1 "reg_or_fp0_operand" "fG")))]
3090   "TARGET_FP && TARGET_FIX"
3091   "sqrt%-%/ %1,%0"
3092   [(set_attr "type" "fsqrt")
3093    (set_attr "trap" "yes")
3094    (set_attr "round_suffix" "normal")
3095    (set_attr "trap_suffix" "u_su_sui")])
3096 \f
3097 ;; Next are all the integer comparisons, and conditional moves and branches
3098 ;; and some of the related define_expand's and define_split's.
3099
3100 (define_insn "*setcc_internal"
3101   [(set (match_operand 0 "register_operand" "=r")
3102         (match_operator 1 "alpha_comparison_operator"
3103                            [(match_operand:DI 2 "register_operand" "r")
3104                             (match_operand:DI 3 "reg_or_8bit_operand" "rI")]))]
3105   "GET_MODE_CLASS (GET_MODE (operands[0])) == MODE_INT
3106    && GET_MODE_SIZE (GET_MODE (operands[0])) <= 8
3107    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
3108   "cmp%C1 %2,%3,%0"
3109   [(set_attr "type" "icmp")])
3110
3111 ;; Yes, we can technically support reg_or_8bit_operand in operand 2,
3112 ;; but that's non-canonical rtl and allowing that causes inefficiencies
3113 ;; from cse on.
3114 (define_insn "*setcc_swapped_internal"
3115   [(set (match_operand 0 "register_operand" "=r")
3116         (match_operator 1 "alpha_swapped_comparison_operator"
3117                            [(match_operand:DI 2 "register_operand" "r")
3118                             (match_operand:DI 3 "reg_or_0_operand" "rJ")]))]
3119   "GET_MODE_CLASS (GET_MODE (operands[0])) == MODE_INT
3120    && GET_MODE_SIZE (GET_MODE (operands[0])) <= 8
3121    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
3122   "cmp%c1 %r3,%2,%0"
3123   [(set_attr "type" "icmp")])
3124
3125 ;; Use match_operator rather than ne directly so that we can match
3126 ;; multiple integer modes.
3127 (define_insn "*setne_internal"
3128   [(set (match_operand 0 "register_operand" "=r")
3129         (match_operator 1 "signed_comparison_operator"
3130                           [(match_operand:DI 2 "register_operand" "r")
3131                            (const_int 0)]))]
3132   "GET_MODE_CLASS (GET_MODE (operands[0])) == MODE_INT
3133    && GET_MODE_SIZE (GET_MODE (operands[0])) <= 8
3134    && GET_CODE (operands[1]) == NE
3135    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
3136   "cmpult $31,%2,%0"
3137   [(set_attr "type" "icmp")])
3138
3139 ;; The mode folding trick can't be used with const_int operands, since
3140 ;; reload needs to know the proper mode.
3141 ;;
3142 ;; Use add_operand instead of the more seemingly natural reg_or_8bit_operand
3143 ;; in order to create more pairs of constants.  As long as we're allowing
3144 ;; two constants at the same time, and will have to reload one of them...
3145
3146 (define_insn "*movqicc_internal"
3147   [(set (match_operand:QI 0 "register_operand" "=r,r,r,r")
3148         (if_then_else:QI
3149          (match_operator 2 "signed_comparison_operator"
3150                          [(match_operand:DI 3 "reg_or_0_operand" "rJ,rJ,J,J")
3151                           (match_operand:DI 4 "reg_or_0_operand" "J,J,rJ,rJ")])
3152          (match_operand:QI 1 "add_operand" "rI,0,rI,0")
3153          (match_operand:QI 5 "add_operand" "0,rI,0,rI")))]
3154   "(operands[3] == const0_rtx || operands[4] == const0_rtx)"
3155   "@
3156    cmov%C2 %r3,%1,%0
3157    cmov%D2 %r3,%5,%0
3158    cmov%c2 %r4,%1,%0
3159    cmov%d2 %r4,%5,%0"
3160   [(set_attr "type" "icmov")])
3161
3162 (define_insn "*movhicc_internal"
3163   [(set (match_operand:HI 0 "register_operand" "=r,r,r,r")
3164         (if_then_else:HI
3165          (match_operator 2 "signed_comparison_operator"
3166                          [(match_operand:DI 3 "reg_or_0_operand" "rJ,rJ,J,J")
3167                           (match_operand:DI 4 "reg_or_0_operand" "J,J,rJ,rJ")])
3168          (match_operand:HI 1 "add_operand" "rI,0,rI,0")
3169          (match_operand:HI 5 "add_operand" "0,rI,0,rI")))]
3170   "(operands[3] == const0_rtx || operands[4] == const0_rtx)"
3171   "@
3172    cmov%C2 %r3,%1,%0
3173    cmov%D2 %r3,%5,%0
3174    cmov%c2 %r4,%1,%0
3175    cmov%d2 %r4,%5,%0"
3176   [(set_attr "type" "icmov")])
3177
3178 (define_insn "*movsicc_internal"
3179   [(set (match_operand:SI 0 "register_operand" "=r,r,r,r")
3180         (if_then_else:SI
3181          (match_operator 2 "signed_comparison_operator"
3182                          [(match_operand:DI 3 "reg_or_0_operand" "rJ,rJ,J,J")
3183                           (match_operand:DI 4 "reg_or_0_operand" "J,J,rJ,rJ")])
3184          (match_operand:SI 1 "add_operand" "rI,0,rI,0")
3185          (match_operand:SI 5 "add_operand" "0,rI,0,rI")))]
3186   "(operands[3] == const0_rtx || operands[4] == const0_rtx)"
3187   "@
3188    cmov%C2 %r3,%1,%0
3189    cmov%D2 %r3,%5,%0
3190    cmov%c2 %r4,%1,%0
3191    cmov%d2 %r4,%5,%0"
3192   [(set_attr "type" "icmov")])
3193
3194 (define_insn "*movdicc_internal"
3195   [(set (match_operand:DI 0 "register_operand" "=r,r,r,r")
3196         (if_then_else:DI
3197          (match_operator 2 "signed_comparison_operator"
3198                          [(match_operand:DI 3 "reg_or_0_operand" "rJ,rJ,J,J")
3199                           (match_operand:DI 4 "reg_or_0_operand" "J,J,rJ,rJ")])
3200          (match_operand:DI 1 "add_operand" "rI,0,rI,0")
3201          (match_operand:DI 5 "add_operand" "0,rI,0,rI")))]
3202   "(operands[3] == const0_rtx || operands[4] == const0_rtx)"
3203   "@
3204    cmov%C2 %r3,%1,%0
3205    cmov%D2 %r3,%5,%0
3206    cmov%c2 %r4,%1,%0
3207    cmov%d2 %r4,%5,%0"
3208   [(set_attr "type" "icmov")])
3209
3210 (define_insn "*movqicc_lbc"
3211   [(set (match_operand:QI 0 "register_operand" "=r,r")
3212         (if_then_else:QI
3213          (eq (zero_extract:DI (match_operand:DI 2 "reg_or_0_operand" "rJ,rJ")
3214                               (const_int 1)
3215                               (const_int 0))
3216              (const_int 0))
3217          (match_operand:QI 1 "reg_or_8bit_operand" "rI,0")
3218          (match_operand:QI 3 "reg_or_8bit_operand" "0,rI")))]
3219   ""
3220   "@
3221    cmovlbc %r2,%1,%0
3222    cmovlbs %r2,%3,%0"
3223   [(set_attr "type" "icmov")])
3224
3225 (define_insn "*movhicc_lbc"
3226   [(set (match_operand:HI 0 "register_operand" "=r,r")
3227         (if_then_else:HI
3228          (eq (zero_extract:DI (match_operand:DI 2 "reg_or_0_operand" "rJ,rJ")
3229                               (const_int 1)
3230                               (const_int 0))
3231              (const_int 0))
3232          (match_operand:HI 1 "reg_or_8bit_operand" "rI,0")
3233          (match_operand:HI 3 "reg_or_8bit_operand" "0,rI")))]
3234   ""
3235   "@
3236    cmovlbc %r2,%1,%0
3237    cmovlbs %r2,%3,%0"
3238   [(set_attr "type" "icmov")])
3239
3240 (define_insn "*movsicc_lbc"
3241   [(set (match_operand:SI 0 "register_operand" "=r,r")
3242         (if_then_else:SI
3243          (eq (zero_extract:DI (match_operand:DI 2 "reg_or_0_operand" "rJ,rJ")
3244                               (const_int 1)
3245                               (const_int 0))
3246              (const_int 0))
3247          (match_operand:SI 1 "reg_or_8bit_operand" "rI,0")
3248          (match_operand:SI 3 "reg_or_8bit_operand" "0,rI")))]
3249   ""
3250   "@
3251    cmovlbc %r2,%1,%0
3252    cmovlbs %r2,%3,%0"
3253   [(set_attr "type" "icmov")])
3254
3255 (define_insn "*movdicc_lbc"
3256   [(set (match_operand:DI 0 "register_operand" "=r,r")
3257         (if_then_else:DI
3258          (eq (zero_extract:DI (match_operand:DI 2 "reg_or_0_operand" "rJ,rJ")
3259                               (const_int 1)
3260                               (const_int 0))
3261              (const_int 0))
3262          (match_operand:DI 1 "reg_or_8bit_operand" "rI,0")
3263          (match_operand:DI 3 "reg_or_8bit_operand" "0,rI")))]
3264   ""
3265   "@
3266    cmovlbc %r2,%1,%0
3267    cmovlbs %r2,%3,%0"
3268   [(set_attr "type" "icmov")])
3269
3270 (define_insn "*movqicc_lbs"
3271   [(set (match_operand:QI 0 "register_operand" "=r,r")
3272         (if_then_else:QI
3273          (ne (zero_extract:DI (match_operand:DI 2 "reg_or_0_operand" "rJ,rJ")
3274                               (const_int 1)
3275                               (const_int 0))
3276              (const_int 0))
3277          (match_operand:QI 1 "reg_or_8bit_operand" "rI,0")
3278          (match_operand:QI 3 "reg_or_8bit_operand" "0,rI")))]
3279   ""
3280   "@
3281    cmovlbs %r2,%1,%0
3282    cmovlbc %r2,%3,%0"
3283   [(set_attr "type" "icmov")])
3284
3285 (define_insn "*movhicc_lbs"
3286   [(set (match_operand:HI 0 "register_operand" "=r,r")
3287         (if_then_else:HI
3288          (ne (zero_extract:DI (match_operand:DI 2 "reg_or_0_operand" "rJ,rJ")
3289                               (const_int 1)
3290                               (const_int 0))
3291              (const_int 0))
3292          (match_operand:HI 1 "reg_or_8bit_operand" "rI,0")
3293          (match_operand:HI 3 "reg_or_8bit_operand" "0,rI")))]
3294   ""
3295   "@
3296    cmovlbs %r2,%1,%0
3297    cmovlbc %r2,%3,%0"
3298   [(set_attr "type" "icmov")])
3299
3300 (define_insn "*movsicc_lbs"
3301   [(set (match_operand:SI 0 "register_operand" "=r,r")
3302         (if_then_else:SI
3303          (ne (zero_extract:DI (match_operand:DI 2 "reg_or_0_operand" "rJ,rJ")
3304                               (const_int 1)
3305                               (const_int 0))
3306              (const_int 0))
3307          (match_operand:SI 1 "reg_or_8bit_operand" "rI,0")
3308          (match_operand:SI 3 "reg_or_8bit_operand" "0,rI")))]
3309   ""
3310   "@
3311    cmovlbs %r2,%1,%0
3312    cmovlbc %r2,%3,%0"
3313   [(set_attr "type" "icmov")])
3314
3315 (define_insn "*movdicc_lbs"
3316   [(set (match_operand:DI 0 "register_operand" "=r,r")
3317         (if_then_else:DI
3318          (ne (zero_extract:DI (match_operand:DI 2 "reg_or_0_operand" "rJ,rJ")
3319                               (const_int 1)
3320                               (const_int 0))
3321              (const_int 0))
3322          (match_operand:DI 1 "reg_or_8bit_operand" "rI,0")
3323          (match_operand:DI 3 "reg_or_8bit_operand" "0,rI")))]
3324   ""
3325   "@
3326    cmovlbs %r2,%1,%0
3327    cmovlbc %r2,%3,%0"
3328   [(set_attr "type" "icmov")])
3329
3330 ;; For ABS, we have two choices, depending on whether the input and output
3331 ;; registers are the same or not.
3332 (define_expand "absdi2"
3333   [(set (match_operand:DI 0 "register_operand" "")
3334         (abs:DI (match_operand:DI 1 "register_operand" "")))]
3335   ""
3336 {
3337   if (rtx_equal_p (operands[0], operands[1]))
3338     emit_insn (gen_absdi2_same (operands[0], gen_reg_rtx (DImode)));
3339   else
3340     emit_insn (gen_absdi2_diff (operands[0], operands[1]));
3341   DONE;
3342 })
3343
3344 (define_expand "absdi2_same"
3345   [(set (match_operand:DI 1 "register_operand" "")
3346         (neg:DI (match_operand:DI 0 "register_operand" "")))
3347    (set (match_dup 0)
3348         (if_then_else:DI (ge (match_dup 0) (const_int 0))
3349                          (match_dup 0)
3350                          (match_dup 1)))]
3351   ""
3352   "")
3353
3354 (define_expand "absdi2_diff"
3355   [(set (match_operand:DI 0 "register_operand" "")
3356         (neg:DI (match_operand:DI 1 "register_operand" "")))
3357    (set (match_dup 0)
3358         (if_then_else:DI (lt (match_dup 1) (const_int 0))
3359                          (match_dup 0)
3360                          (match_dup 1)))]
3361   ""
3362   "")
3363
3364 (define_split
3365   [(set (match_operand:DI 0 "register_operand" "")
3366         (abs:DI (match_dup 0)))
3367    (clobber (match_operand:DI 1 "register_operand" ""))]
3368   ""
3369   [(set (match_dup 1) (neg:DI (match_dup 0)))
3370    (set (match_dup 0) (if_then_else:DI (ge (match_dup 0) (const_int 0))
3371                                        (match_dup 0) (match_dup 1)))]
3372   "")
3373
3374 (define_split
3375   [(set (match_operand:DI 0 "register_operand" "")
3376         (abs:DI (match_operand:DI 1 "register_operand" "")))]
3377   "! rtx_equal_p (operands[0], operands[1])"
3378   [(set (match_dup 0) (neg:DI (match_dup 1)))
3379    (set (match_dup 0) (if_then_else:DI (lt (match_dup 1) (const_int 0))
3380                                        (match_dup 0) (match_dup 1)))]
3381   "")
3382
3383 (define_split
3384   [(set (match_operand:DI 0 "register_operand" "")
3385         (neg:DI (abs:DI (match_dup 0))))
3386    (clobber (match_operand:DI 1 "register_operand" ""))]
3387   ""
3388   [(set (match_dup 1) (neg:DI (match_dup 0)))
3389    (set (match_dup 0) (if_then_else:DI (le (match_dup 0) (const_int 0))
3390                                        (match_dup 0) (match_dup 1)))]
3391   "")
3392
3393 (define_split
3394   [(set (match_operand:DI 0 "register_operand" "")
3395         (neg:DI (abs:DI (match_operand:DI 1 "register_operand" ""))))]
3396   "! rtx_equal_p (operands[0], operands[1])"
3397   [(set (match_dup 0) (neg:DI (match_dup 1)))
3398    (set (match_dup 0) (if_then_else:DI (gt (match_dup 1) (const_int 0))
3399                                        (match_dup 0) (match_dup 1)))]
3400   "")
3401
3402 (define_insn "sminqi3"
3403   [(set (match_operand:QI 0 "register_operand" "=r")
3404         (smin:QI (match_operand:QI 1 "reg_or_0_operand" "%rJ")
3405                  (match_operand:QI 2 "reg_or_8bit_operand" "rI")))]
3406   "TARGET_MAX"
3407   "minsb8 %r1,%2,%0"
3408   [(set_attr "type" "mvi")])
3409
3410 (define_insn "uminqi3"
3411   [(set (match_operand:QI 0 "register_operand" "=r")
3412         (umin:QI (match_operand:QI 1 "reg_or_0_operand" "%rJ")
3413                  (match_operand:QI 2 "reg_or_8bit_operand" "rI")))]
3414   "TARGET_MAX"
3415   "minub8 %r1,%2,%0"
3416   [(set_attr "type" "mvi")])
3417
3418 (define_insn "smaxqi3"
3419   [(set (match_operand:QI 0 "register_operand" "=r")
3420         (smax:QI (match_operand:QI 1 "reg_or_0_operand" "%rJ")
3421                  (match_operand:QI 2 "reg_or_8bit_operand" "rI")))]
3422   "TARGET_MAX"
3423   "maxsb8 %r1,%2,%0"
3424   [(set_attr "type" "mvi")])
3425
3426 (define_insn "umaxqi3"
3427   [(set (match_operand:QI 0 "register_operand" "=r")
3428         (umax:QI (match_operand:QI 1 "reg_or_0_operand" "%rJ")
3429                  (match_operand:QI 2 "reg_or_8bit_operand" "rI")))]
3430   "TARGET_MAX"
3431   "maxub8 %r1,%2,%0"
3432   [(set_attr "type" "mvi")])
3433
3434 (define_insn "sminhi3"
3435   [(set (match_operand:HI 0 "register_operand" "=r")
3436         (smin:HI (match_operand:HI 1 "reg_or_0_operand" "%rJ")
3437                  (match_operand:HI 2 "reg_or_8bit_operand" "rI")))]
3438   "TARGET_MAX"
3439   "minsw4 %r1,%2,%0"
3440   [(set_attr "type" "mvi")])
3441
3442 (define_insn "uminhi3"
3443   [(set (match_operand:HI 0 "register_operand" "=r")
3444         (umin:HI (match_operand:HI 1 "reg_or_0_operand" "%rJ")
3445                  (match_operand:HI 2 "reg_or_8bit_operand" "rI")))]
3446   "TARGET_MAX"
3447   "minuw4 %r1,%2,%0"
3448   [(set_attr "type" "mvi")])
3449
3450 (define_insn "smaxhi3"
3451   [(set (match_operand:HI 0 "register_operand" "=r")
3452         (smax:HI (match_operand:HI 1 "reg_or_0_operand" "%rJ")
3453                  (match_operand:HI 2 "reg_or_8bit_operand" "rI")))]
3454   "TARGET_MAX"
3455   "maxsw4 %r1,%2,%0"
3456   [(set_attr "type" "mvi")])
3457
3458 (define_insn "umaxhi3"
3459   [(set (match_operand:HI 0 "register_operand" "=r")
3460         (umax:HI (match_operand:HI 1 "reg_or_0_operand" "%rJ")
3461                  (match_operand:HI 2 "reg_or_8bit_operand" "rI")))]
3462   "TARGET_MAX"
3463   "maxuw4 %r1,%2,%0"
3464   [(set_attr "type" "shift")])
3465
3466 (define_expand "smaxdi3"
3467   [(set (match_dup 3)
3468         (le:DI (match_operand:DI 1 "reg_or_0_operand" "")
3469                (match_operand:DI 2 "reg_or_8bit_operand" "")))
3470    (set (match_operand:DI 0 "register_operand" "")
3471         (if_then_else:DI (eq (match_dup 3) (const_int 0))
3472                          (match_dup 1) (match_dup 2)))]
3473   ""
3474   { operands[3] = gen_reg_rtx (DImode); })
3475
3476 (define_split
3477   [(set (match_operand:DI 0 "register_operand" "")
3478         (smax:DI (match_operand:DI 1 "reg_or_0_operand" "")
3479                  (match_operand:DI 2 "reg_or_8bit_operand" "")))
3480    (clobber (match_operand:DI 3 "register_operand" ""))]
3481   "operands[2] != const0_rtx"
3482   [(set (match_dup 3) (le:DI (match_dup 1) (match_dup 2)))
3483    (set (match_dup 0) (if_then_else:DI (eq (match_dup 3) (const_int 0))
3484                                        (match_dup 1) (match_dup 2)))]
3485   "")
3486
3487 (define_insn "*smax_const0"
3488   [(set (match_operand:DI 0 "register_operand" "=r")
3489         (smax:DI (match_operand:DI 1 "register_operand" "0")
3490                  (const_int 0)))]
3491   ""
3492   "cmovlt %0,0,%0"
3493   [(set_attr "type" "icmov")])
3494
3495 (define_expand "smindi3"
3496   [(set (match_dup 3)
3497         (lt:DI (match_operand:DI 1 "reg_or_0_operand" "")
3498                (match_operand:DI 2 "reg_or_8bit_operand" "")))
3499    (set (match_operand:DI 0 "register_operand" "")
3500         (if_then_else:DI (ne (match_dup 3) (const_int 0))
3501                          (match_dup 1) (match_dup 2)))]
3502   ""
3503   { operands[3] = gen_reg_rtx (DImode); })
3504
3505 (define_split
3506   [(set (match_operand:DI 0 "register_operand" "")
3507         (smin:DI (match_operand:DI 1 "reg_or_0_operand" "")
3508                  (match_operand:DI 2 "reg_or_8bit_operand" "")))
3509    (clobber (match_operand:DI 3 "register_operand" ""))]
3510   "operands[2] != const0_rtx"
3511   [(set (match_dup 3) (lt:DI (match_dup 1) (match_dup 2)))
3512    (set (match_dup 0) (if_then_else:DI (ne (match_dup 3) (const_int 0))
3513                                        (match_dup 1) (match_dup 2)))]
3514   "")
3515
3516 (define_insn "*smin_const0"
3517   [(set (match_operand:DI 0 "register_operand" "=r")
3518         (smin:DI (match_operand:DI 1 "register_operand" "0")
3519                  (const_int 0)))]
3520   ""
3521   "cmovgt %0,0,%0"
3522   [(set_attr "type" "icmov")])
3523
3524 (define_expand "umaxdi3"
3525   [(set (match_dup 3)
3526         (leu:DI (match_operand:DI 1 "reg_or_0_operand" "")
3527                 (match_operand:DI 2 "reg_or_8bit_operand" "")))
3528    (set (match_operand:DI 0 "register_operand" "")
3529         (if_then_else:DI (eq (match_dup 3) (const_int 0))
3530                          (match_dup 1) (match_dup 2)))]
3531   ""
3532   "operands[3] = gen_reg_rtx (DImode);")
3533
3534 (define_split
3535   [(set (match_operand:DI 0 "register_operand" "")
3536         (umax:DI (match_operand:DI 1 "reg_or_0_operand" "")
3537                  (match_operand:DI 2 "reg_or_8bit_operand" "")))
3538    (clobber (match_operand:DI 3 "register_operand" ""))]
3539   "operands[2] != const0_rtx"
3540   [(set (match_dup 3) (leu:DI (match_dup 1) (match_dup 2)))
3541    (set (match_dup 0) (if_then_else:DI (eq (match_dup 3) (const_int 0))
3542                                        (match_dup 1) (match_dup 2)))]
3543   "")
3544
3545 (define_expand "umindi3"
3546   [(set (match_dup 3)
3547         (ltu:DI (match_operand:DI 1 "reg_or_0_operand" "")
3548                 (match_operand:DI 2 "reg_or_8bit_operand" "")))
3549    (set (match_operand:DI 0 "register_operand" "")
3550         (if_then_else:DI (ne (match_dup 3) (const_int 0))
3551                          (match_dup 1) (match_dup 2)))]
3552   ""
3553   "operands[3] = gen_reg_rtx (DImode);")
3554
3555 (define_split
3556   [(set (match_operand:DI 0 "register_operand" "")
3557         (umin:DI (match_operand:DI 1 "reg_or_0_operand" "")
3558                  (match_operand:DI 2 "reg_or_8bit_operand" "")))
3559    (clobber (match_operand:DI 3 "register_operand" ""))]
3560   "operands[2] != const0_rtx"
3561   [(set (match_dup 3) (ltu:DI (match_dup 1) (match_dup 2)))
3562    (set (match_dup 0) (if_then_else:DI (ne (match_dup 3) (const_int 0))
3563                                        (match_dup 1) (match_dup 2)))]
3564   "")
3565
3566 (define_insn "*bcc_normal"
3567   [(set (pc)
3568         (if_then_else
3569          (match_operator 1 "signed_comparison_operator"
3570                          [(match_operand:DI 2 "reg_or_0_operand" "rJ")
3571                           (const_int 0)])
3572          (label_ref (match_operand 0 "" ""))
3573          (pc)))]
3574   ""
3575   "b%C1 %r2,%0"
3576   [(set_attr "type" "ibr")])
3577
3578 (define_insn "*bcc_reverse"
3579   [(set (pc)
3580         (if_then_else
3581          (match_operator 1 "signed_comparison_operator"
3582                          [(match_operand:DI 2 "register_operand" "r")
3583                           (const_int 0)])
3584
3585          (pc)
3586          (label_ref (match_operand 0 "" ""))))]
3587   ""
3588   "b%c1 %2,%0"
3589   [(set_attr "type" "ibr")])
3590
3591 (define_insn "*blbs_normal"
3592   [(set (pc)
3593         (if_then_else
3594          (ne (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
3595                               (const_int 1)
3596                               (const_int 0))
3597              (const_int 0))
3598          (label_ref (match_operand 0 "" ""))
3599          (pc)))]
3600   ""
3601   "blbs %r1,%0"
3602   [(set_attr "type" "ibr")])
3603
3604 (define_insn "*blbc_normal"
3605   [(set (pc)
3606         (if_then_else
3607          (eq (zero_extract:DI (match_operand:DI 1 "reg_or_0_operand" "rJ")
3608                               (const_int 1)
3609                               (const_int 0))
3610              (const_int 0))
3611          (label_ref (match_operand 0 "" ""))
3612          (pc)))]
3613   ""
3614   "blbc %r1,%0"
3615   [(set_attr "type" "ibr")])
3616
3617 (define_split
3618   [(parallel
3619     [(set (pc)
3620           (if_then_else
3621            (match_operator 1 "comparison_operator"
3622                            [(zero_extract:DI (match_operand:DI 2 "register_operand" "")
3623                                              (const_int 1)
3624                                              (match_operand:DI 3 "const_int_operand" ""))
3625                             (const_int 0)])
3626            (label_ref (match_operand 0 "" ""))
3627            (pc)))
3628      (clobber (match_operand:DI 4 "register_operand" ""))])]
3629   "INTVAL (operands[3]) != 0"
3630   [(set (match_dup 4)
3631         (lshiftrt:DI (match_dup 2) (match_dup 3)))
3632    (set (pc)
3633         (if_then_else (match_op_dup 1
3634                                     [(zero_extract:DI (match_dup 4)
3635                                                       (const_int 1)
3636                                                       (const_int 0))
3637                                      (const_int 0)])
3638                       (label_ref (match_dup 0))
3639                       (pc)))]
3640   "")
3641 \f
3642 ;; The following are the corresponding floating-point insns.  Recall
3643 ;; we need to have variants that expand the arguments from SFmode
3644 ;; to DFmode.
3645
3646 (define_insn "*cmpdf_ieee"
3647   [(set (match_operand:DF 0 "register_operand" "=&f")
3648         (match_operator:DF 1 "alpha_fp_comparison_operator"
3649                            [(match_operand:DF 2 "reg_or_fp0_operand" "fG")
3650                             (match_operand:DF 3 "reg_or_fp0_operand" "fG")]))]
3651   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
3652   "cmp%-%C1%/ %R2,%R3,%0"
3653   [(set_attr "type" "fadd")
3654    (set_attr "trap" "yes")
3655    (set_attr "trap_suffix" "su")])
3656
3657 (define_insn "*cmpdf_internal"
3658   [(set (match_operand:DF 0 "register_operand" "=f")
3659         (match_operator:DF 1 "alpha_fp_comparison_operator"
3660                            [(match_operand:DF 2 "reg_or_fp0_operand" "fG")
3661                             (match_operand:DF 3 "reg_or_fp0_operand" "fG")]))]
3662   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
3663   "cmp%-%C1%/ %R2,%R3,%0"
3664   [(set_attr "type" "fadd")
3665    (set_attr "trap" "yes")
3666    (set_attr "trap_suffix" "su")])
3667
3668 (define_insn "*cmpdf_ieee_ext1"
3669   [(set (match_operand:DF 0 "register_operand" "=&f")
3670         (match_operator:DF 1 "alpha_fp_comparison_operator"
3671                            [(float_extend:DF
3672                              (match_operand:SF 2 "reg_or_fp0_operand" "fG"))
3673                             (match_operand:DF 3 "reg_or_fp0_operand" "fG")]))]
3674   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
3675   "cmp%-%C1%/ %R2,%R3,%0"
3676   [(set_attr "type" "fadd")
3677    (set_attr "trap" "yes")
3678    (set_attr "trap_suffix" "su")])
3679
3680 (define_insn "*cmpdf_ext1"
3681   [(set (match_operand:DF 0 "register_operand" "=f")
3682         (match_operator:DF 1 "alpha_fp_comparison_operator"
3683                            [(float_extend:DF
3684                              (match_operand:SF 2 "reg_or_fp0_operand" "fG"))
3685                             (match_operand:DF 3 "reg_or_fp0_operand" "fG")]))]
3686   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
3687   "cmp%-%C1%/ %R2,%R3,%0"
3688   [(set_attr "type" "fadd")
3689    (set_attr "trap" "yes")
3690    (set_attr "trap_suffix" "su")])
3691
3692 (define_insn "*cmpdf_ieee_ext2"
3693   [(set (match_operand:DF 0 "register_operand" "=&f")
3694         (match_operator:DF 1 "alpha_fp_comparison_operator"
3695                            [(match_operand:DF 2 "reg_or_fp0_operand" "fG")
3696                             (float_extend:DF
3697                              (match_operand:SF 3 "reg_or_fp0_operand" "fG"))]))]
3698   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
3699   "cmp%-%C1%/ %R2,%R3,%0"
3700   [(set_attr "type" "fadd")
3701    (set_attr "trap" "yes")
3702    (set_attr "trap_suffix" "su")])
3703
3704 (define_insn "*cmpdf_ext2"
3705   [(set (match_operand:DF 0 "register_operand" "=f")
3706         (match_operator:DF 1 "alpha_fp_comparison_operator"
3707                            [(match_operand:DF 2 "reg_or_fp0_operand" "fG")
3708                             (float_extend:DF
3709                              (match_operand:SF 3 "reg_or_fp0_operand" "fG"))]))]
3710   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
3711   "cmp%-%C1%/ %R2,%R3,%0"
3712   [(set_attr "type" "fadd")
3713    (set_attr "trap" "yes")
3714    (set_attr "trap_suffix" "su")])
3715
3716 (define_insn "*cmpdf_ieee_ext3"
3717   [(set (match_operand:DF 0 "register_operand" "=&f")
3718         (match_operator:DF 1 "alpha_fp_comparison_operator"
3719                            [(float_extend:DF
3720                              (match_operand:SF 2 "reg_or_fp0_operand" "fG"))
3721                             (float_extend:DF
3722                              (match_operand:SF 3 "reg_or_fp0_operand" "fG"))]))]
3723   "TARGET_FP && alpha_fptm >= ALPHA_FPTM_SU"
3724   "cmp%-%C1%/ %R2,%R3,%0"
3725   [(set_attr "type" "fadd")
3726    (set_attr "trap" "yes")
3727    (set_attr "trap_suffix" "su")])
3728
3729 (define_insn "*cmpdf_ext3"
3730   [(set (match_operand:DF 0 "register_operand" "=f")
3731         (match_operator:DF 1 "alpha_fp_comparison_operator"
3732                            [(float_extend:DF
3733                              (match_operand:SF 2 "reg_or_fp0_operand" "fG"))
3734                             (float_extend:DF
3735                              (match_operand:SF 3 "reg_or_fp0_operand" "fG"))]))]
3736   "TARGET_FP && alpha_fptm < ALPHA_FPTM_SU"
3737   "cmp%-%C1%/ %R2,%R3,%0"
3738   [(set_attr "type" "fadd")
3739    (set_attr "trap" "yes")
3740    (set_attr "trap_suffix" "su")])
3741
3742 (define_insn "*movdfcc_internal"
3743   [(set (match_operand:DF 0 "register_operand" "=f,f")
3744         (if_then_else:DF
3745          (match_operator 3 "signed_comparison_operator"
3746                          [(match_operand:DF 4 "reg_or_fp0_operand" "fG,fG")
3747                           (match_operand:DF 2 "fp0_operand" "G,G")])
3748          (match_operand:DF 1 "reg_or_fp0_operand" "fG,0")
3749          (match_operand:DF 5 "reg_or_fp0_operand" "0,fG")))]
3750   "TARGET_FP"
3751   "@
3752    fcmov%C3 %R4,%R1,%0
3753    fcmov%D3 %R4,%R5,%0"
3754   [(set_attr "type" "fcmov")])
3755
3756 (define_insn "*movsfcc_internal"
3757   [(set (match_operand:SF 0 "register_operand" "=f,f")
3758         (if_then_else:SF
3759          (match_operator 3 "signed_comparison_operator"
3760                          [(match_operand:DF 4 "reg_or_fp0_operand" "fG,fG")
3761                           (match_operand:DF 2 "fp0_operand" "G,G")])
3762          (match_operand:SF 1 "reg_or_fp0_operand" "fG,0")
3763          (match_operand:SF 5 "reg_or_fp0_operand" "0,fG")))]
3764   "TARGET_FP"
3765   "@
3766    fcmov%C3 %R4,%R1,%0
3767    fcmov%D3 %R4,%R5,%0"
3768   [(set_attr "type" "fcmov")])
3769
3770 (define_insn "*movdfcc_ext1"
3771   [(set (match_operand:DF 0 "register_operand" "=f,f")
3772         (if_then_else:DF
3773          (match_operator 3 "signed_comparison_operator"
3774                          [(match_operand:DF 4 "reg_or_fp0_operand" "fG,fG")
3775                           (match_operand:DF 2 "fp0_operand" "G,G")])
3776          (float_extend:DF (match_operand:SF 1 "reg_or_fp0_operand" "fG,0"))
3777          (match_operand:DF 5 "reg_or_fp0_operand" "0,fG")))]
3778   "TARGET_FP"
3779   "@
3780    fcmov%C3 %R4,%R1,%0
3781    fcmov%D3 %R4,%R5,%0"
3782   [(set_attr "type" "fcmov")])
3783
3784 (define_insn "*movdfcc_ext2"
3785   [(set (match_operand:DF 0 "register_operand" "=f,f")
3786         (if_then_else:DF
3787          (match_operator 3 "signed_comparison_operator"
3788                          [(float_extend:DF
3789                            (match_operand:SF 4 "reg_or_fp0_operand" "fG,fG"))
3790                           (match_operand:DF 2 "fp0_operand" "G,G")])
3791          (match_operand:DF 1 "reg_or_fp0_operand" "fG,0")
3792          (match_operand:DF 5 "reg_or_fp0_operand" "0,fG")))]
3793   "TARGET_FP"
3794   "@
3795    fcmov%C3 %R4,%R1,%0
3796    fcmov%D3 %R4,%R5,%0"
3797   [(set_attr "type" "fcmov")])
3798
3799 (define_insn "*movdfcc_ext3"
3800   [(set (match_operand:SF 0 "register_operand" "=f,f")
3801         (if_then_else:SF
3802          (match_operator 3 "signed_comparison_operator"
3803                          [(float_extend:DF
3804                            (match_operand:SF 4 "reg_or_fp0_operand" "fG,fG"))
3805                           (match_operand:DF 2 "fp0_operand" "G,G")])
3806          (match_operand:SF 1 "reg_or_fp0_operand" "fG,0")
3807          (match_operand:SF 5 "reg_or_fp0_operand" "0,fG")))]
3808   "TARGET_FP"
3809   "@
3810    fcmov%C3 %R4,%R1,%0
3811    fcmov%D3 %R4,%R5,%0"
3812   [(set_attr "type" "fcmov")])
3813
3814 (define_insn "*movdfcc_ext4"
3815   [(set (match_operand:DF 0 "register_operand" "=f,f")
3816         (if_then_else:DF
3817          (match_operator 3 "signed_comparison_operator"
3818                          [(float_extend:DF
3819                            (match_operand:SF 4 "reg_or_fp0_operand" "fG,fG"))
3820                           (match_operand:DF 2 "fp0_operand" "G,G")])
3821          (float_extend:DF (match_operand:SF 1 "reg_or_fp0_operand" "fG,0"))
3822          (match_operand:DF 5 "reg_or_fp0_operand" "0,fG")))]
3823   "TARGET_FP"
3824   "@
3825    fcmov%C3 %R4,%R1,%0
3826    fcmov%D3 %R4,%R5,%0"
3827   [(set_attr "type" "fcmov")])
3828
3829 (define_expand "maxdf3"
3830   [(set (match_dup 3)
3831         (le:DF (match_operand:DF 1 "reg_or_fp0_operand" "")
3832                (match_operand:DF 2 "reg_or_fp0_operand" "")))
3833    (set (match_operand:DF 0 "register_operand" "")
3834         (if_then_else:DF (eq (match_dup 3) (match_dup 4))
3835                          (match_dup 1) (match_dup 2)))]
3836   "TARGET_FP"
3837 {
3838   operands[3] = gen_reg_rtx (DFmode);
3839   operands[4] = CONST0_RTX (DFmode);
3840 })
3841
3842 (define_expand "mindf3"
3843   [(set (match_dup 3)
3844         (lt:DF (match_operand:DF 1 "reg_or_fp0_operand" "")
3845                (match_operand:DF 2 "reg_or_fp0_operand" "")))
3846    (set (match_operand:DF 0 "register_operand" "")
3847         (if_then_else:DF (ne (match_dup 3) (match_dup 4))
3848                          (match_dup 1) (match_dup 2)))]
3849   "TARGET_FP"
3850 {
3851   operands[3] = gen_reg_rtx (DFmode);
3852   operands[4] = CONST0_RTX (DFmode);
3853 })
3854
3855 (define_expand "maxsf3"
3856   [(set (match_dup 3)
3857         (le:DF (float_extend:DF (match_operand:SF 1 "reg_or_fp0_operand" ""))
3858                (float_extend:DF (match_operand:SF 2 "reg_or_fp0_operand" ""))))
3859    (set (match_operand:SF 0 "register_operand" "")
3860         (if_then_else:SF (eq (match_dup 3) (match_dup 4))
3861                          (match_dup 1) (match_dup 2)))]
3862   "TARGET_FP"
3863 {
3864   operands[3] = gen_reg_rtx (DFmode);
3865   operands[4] = CONST0_RTX (DFmode);
3866 })
3867
3868 (define_expand "minsf3"
3869   [(set (match_dup 3)
3870         (lt:DF (float_extend:DF (match_operand:SF 1 "reg_or_fp0_operand" ""))
3871                (float_extend:DF (match_operand:SF 2 "reg_or_fp0_operand" ""))))
3872    (set (match_operand:SF 0 "register_operand" "")
3873         (if_then_else:SF (ne (match_dup 3) (match_dup 4))
3874                       (match_dup 1) (match_dup 2)))]
3875   "TARGET_FP"
3876 {
3877   operands[3] = gen_reg_rtx (DFmode);
3878   operands[4] = CONST0_RTX (DFmode);
3879 })
3880
3881 (define_insn "*fbcc_normal"
3882   [(set (pc)
3883         (if_then_else
3884          (match_operator 1 "signed_comparison_operator"
3885                          [(match_operand:DF 2 "reg_or_fp0_operand" "fG")
3886                           (match_operand:DF 3 "fp0_operand" "G")])
3887          (label_ref (match_operand 0 "" ""))
3888          (pc)))]
3889   "TARGET_FP"
3890   "fb%C1 %R2,%0"
3891   [(set_attr "type" "fbr")])
3892
3893 (define_insn "*fbcc_ext_normal"
3894   [(set (pc)
3895         (if_then_else
3896          (match_operator 1 "signed_comparison_operator"
3897                          [(float_extend:DF
3898                            (match_operand:SF 2 "reg_or_fp0_operand" "fG"))
3899                           (match_operand:DF 3 "fp0_operand" "G")])
3900          (label_ref (match_operand 0 "" ""))
3901          (pc)))]
3902   "TARGET_FP"
3903   "fb%C1 %R2,%0"
3904   [(set_attr "type" "fbr")])
3905 \f
3906 ;; These are the main define_expand's used to make conditional branches
3907 ;; and compares.
3908
3909 (define_expand "cmpdf"
3910   [(set (cc0) (compare (match_operand:DF 0 "reg_or_fp0_operand" "")
3911                        (match_operand:DF 1 "reg_or_fp0_operand" "")))]
3912   "TARGET_FP"
3913 {
3914   alpha_compare.op0 = operands[0];
3915   alpha_compare.op1 = operands[1];
3916   alpha_compare.fp_p = 1;
3917   DONE;
3918 })
3919
3920 (define_expand "cmptf"
3921   [(set (cc0) (compare (match_operand:TF 0 "general_operand" "")
3922                        (match_operand:TF 1 "general_operand" "")))]
3923   "TARGET_HAS_XFLOATING_LIBS"
3924 {
3925   alpha_compare.op0 = operands[0];
3926   alpha_compare.op1 = operands[1];
3927   alpha_compare.fp_p = 1;
3928   DONE;
3929 })
3930
3931 (define_expand "cmpdi"
3932   [(set (cc0) (compare (match_operand:DI 0 "general_operand" "")
3933                        (match_operand:DI 1 "general_operand" "")))]
3934   ""
3935 {
3936   alpha_compare.op0 = operands[0];
3937   alpha_compare.op1 = operands[1];
3938   alpha_compare.fp_p = 0;
3939   DONE;
3940 })
3941
3942 (define_expand "beq"
3943   [(set (pc)
3944         (if_then_else (match_dup 1)
3945                       (label_ref (match_operand 0 "" ""))
3946                       (pc)))]
3947   ""
3948   "{ operands[1] = alpha_emit_conditional_branch (EQ); }")
3949
3950 (define_expand "bne"
3951   [(set (pc)
3952         (if_then_else (match_dup 1)
3953                       (label_ref (match_operand 0 "" ""))
3954                       (pc)))]
3955   ""
3956   "{ operands[1] = alpha_emit_conditional_branch (NE); }")
3957
3958 (define_expand "blt"
3959   [(set (pc)
3960         (if_then_else (match_dup 1)
3961                       (label_ref (match_operand 0 "" ""))
3962                       (pc)))]
3963   ""
3964   "{ operands[1] = alpha_emit_conditional_branch (LT); }")
3965
3966 (define_expand "ble"
3967   [(set (pc)
3968         (if_then_else (match_dup 1)
3969                       (label_ref (match_operand 0 "" ""))
3970                       (pc)))]
3971   ""
3972   "{ operands[1] = alpha_emit_conditional_branch (LE); }")
3973
3974 (define_expand "bgt"
3975   [(set (pc)
3976         (if_then_else (match_dup 1)
3977                       (label_ref (match_operand 0 "" ""))
3978                       (pc)))]
3979   ""
3980   "{ operands[1] = alpha_emit_conditional_branch (GT); }")
3981
3982 (define_expand "bge"
3983   [(set (pc)
3984         (if_then_else (match_dup 1)
3985                       (label_ref (match_operand 0 "" ""))
3986                       (pc)))]
3987   ""
3988   "{ operands[1] = alpha_emit_conditional_branch (GE); }")
3989
3990 (define_expand "bltu"
3991   [(set (pc)
3992         (if_then_else (match_dup 1)
3993                       (label_ref (match_operand 0 "" ""))
3994                       (pc)))]
3995   ""
3996   "{ operands[1] = alpha_emit_conditional_branch (LTU); }")
3997
3998 (define_expand "bleu"
3999   [(set (pc)
4000         (if_then_else (match_dup 1)
4001                       (label_ref (match_operand 0 "" ""))
4002                       (pc)))]
4003   ""
4004   "{ operands[1] = alpha_emit_conditional_branch (LEU); }")
4005
4006 (define_expand "bgtu"
4007   [(set (pc)
4008         (if_then_else (match_dup 1)
4009                       (label_ref (match_operand 0 "" ""))
4010                       (pc)))]
4011   ""
4012   "{ operands[1] = alpha_emit_conditional_branch (GTU); }")
4013
4014 (define_expand "bgeu"
4015   [(set (pc)
4016         (if_then_else (match_dup 1)
4017                       (label_ref (match_operand 0 "" ""))
4018                       (pc)))]
4019   ""
4020   "{ operands[1] = alpha_emit_conditional_branch (GEU); }")
4021
4022 (define_expand "bunordered"
4023   [(set (pc)
4024         (if_then_else (match_dup 1)
4025                       (label_ref (match_operand 0 "" ""))
4026                       (pc)))]
4027   ""
4028   "{ operands[1] = alpha_emit_conditional_branch (UNORDERED); }")
4029
4030 (define_expand "bordered"
4031   [(set (pc)
4032         (if_then_else (match_dup 1)
4033                       (label_ref (match_operand 0 "" ""))
4034                       (pc)))]
4035   ""
4036   "{ operands[1] = alpha_emit_conditional_branch (ORDERED); }")
4037
4038 (define_expand "seq"
4039   [(set (match_operand:DI 0 "register_operand" "")
4040         (match_dup 1))]
4041   ""
4042   "{ if ((operands[1] = alpha_emit_setcc (EQ)) == NULL_RTX) FAIL; }")
4043
4044 (define_expand "sne"
4045   [(set (match_operand:DI 0 "register_operand" "")
4046         (match_dup 1))]
4047   ""
4048   "{ if ((operands[1] = alpha_emit_setcc (NE)) == NULL_RTX) FAIL; }")
4049
4050 (define_expand "slt"
4051   [(set (match_operand:DI 0 "register_operand" "")
4052         (match_dup 1))]
4053   ""
4054   "{ if ((operands[1] = alpha_emit_setcc (LT)) == NULL_RTX) FAIL; }")
4055
4056 (define_expand "sle"
4057   [(set (match_operand:DI 0 "register_operand" "")
4058         (match_dup 1))]
4059   ""
4060   "{ if ((operands[1] = alpha_emit_setcc (LE)) == NULL_RTX) FAIL; }")
4061
4062 (define_expand "sgt"
4063   [(set (match_operand:DI 0 "register_operand" "")
4064         (match_dup 1))]
4065   ""
4066   "{ if ((operands[1] = alpha_emit_setcc (GT)) == NULL_RTX) FAIL; }")
4067
4068 (define_expand "sge"
4069   [(set (match_operand:DI 0 "register_operand" "")
4070         (match_dup 1))]
4071   ""
4072   "{ if ((operands[1] = alpha_emit_setcc (GE)) == NULL_RTX) FAIL; }")
4073
4074 (define_expand "sltu"
4075   [(set (match_operand:DI 0 "register_operand" "")
4076         (match_dup 1))]
4077   ""
4078   "{ if ((operands[1] = alpha_emit_setcc (LTU)) == NULL_RTX) FAIL; }")
4079
4080 (define_expand "sleu"
4081   [(set (match_operand:DI 0 "register_operand" "")
4082         (match_dup 1))]
4083   ""
4084   "{ if ((operands[1] = alpha_emit_setcc (LEU)) == NULL_RTX) FAIL; }")
4085
4086 (define_expand "sgtu"
4087   [(set (match_operand:DI 0 "register_operand" "")
4088         (match_dup 1))]
4089   ""
4090   "{ if ((operands[1] = alpha_emit_setcc (GTU)) == NULL_RTX) FAIL; }")
4091
4092 (define_expand "sgeu"
4093   [(set (match_operand:DI 0 "register_operand" "")
4094         (match_dup 1))]
4095   ""
4096   "{ if ((operands[1] = alpha_emit_setcc (GEU)) == NULL_RTX) FAIL; }")
4097
4098 (define_expand "sunordered"
4099   [(set (match_operand:DI 0 "register_operand" "")
4100         (match_dup 1))]
4101   ""
4102   "{ if ((operands[1] = alpha_emit_setcc (UNORDERED)) == NULL_RTX) FAIL; }")
4103
4104 (define_expand "sordered"
4105   [(set (match_operand:DI 0 "register_operand" "")
4106         (match_dup 1))]
4107   ""
4108   "{ if ((operands[1] = alpha_emit_setcc (ORDERED)) == NULL_RTX) FAIL; }")
4109 \f
4110 ;; These are the main define_expand's used to make conditional moves.
4111
4112 (define_expand "movsicc"
4113   [(set (match_operand:SI 0 "register_operand" "")
4114         (if_then_else:SI (match_operand 1 "comparison_operator" "")
4115                          (match_operand:SI 2 "reg_or_8bit_operand" "")
4116                          (match_operand:SI 3 "reg_or_8bit_operand" "")))]
4117   ""
4118 {
4119   if ((operands[1] = alpha_emit_conditional_move (operands[1], SImode)) == 0)
4120     FAIL;
4121 })
4122
4123 (define_expand "movdicc"
4124   [(set (match_operand:DI 0 "register_operand" "")
4125         (if_then_else:DI (match_operand 1 "comparison_operator" "")
4126                          (match_operand:DI 2 "reg_or_8bit_operand" "")
4127                          (match_operand:DI 3 "reg_or_8bit_operand" "")))]
4128   ""
4129 {
4130   if ((operands[1] = alpha_emit_conditional_move (operands[1], DImode)) == 0)
4131     FAIL;
4132 })
4133
4134 (define_expand "movsfcc"
4135   [(set (match_operand:SF 0 "register_operand" "")
4136         (if_then_else:SF (match_operand 1 "comparison_operator" "")
4137                          (match_operand:SF 2 "reg_or_8bit_operand" "")
4138                          (match_operand:SF 3 "reg_or_8bit_operand" "")))]
4139   ""
4140 {
4141   if ((operands[1] = alpha_emit_conditional_move (operands[1], SFmode)) == 0)
4142     FAIL;
4143 })
4144
4145 (define_expand "movdfcc"
4146   [(set (match_operand:DF 0 "register_operand" "")
4147         (if_then_else:DF (match_operand 1 "comparison_operator" "")
4148                          (match_operand:DF 2 "reg_or_8bit_operand" "")
4149                          (match_operand:DF 3 "reg_or_8bit_operand" "")))]
4150   ""
4151 {
4152   if ((operands[1] = alpha_emit_conditional_move (operands[1], DFmode)) == 0)
4153     FAIL;
4154 })
4155 \f
4156 ;; These define_split definitions are used in cases when comparisons have
4157 ;; not be stated in the correct way and we need to reverse the second
4158 ;; comparison.  For example, x >= 7 has to be done as x < 6 with the
4159 ;; comparison that tests the result being reversed.  We have one define_split
4160 ;; for each use of a comparison.  They do not match valid insns and need
4161 ;; not generate valid insns.
4162 ;;
4163 ;; We can also handle equality comparisons (and inequality comparisons in
4164 ;; cases where the resulting add cannot overflow) by doing an add followed by
4165 ;; a comparison with zero.  This is faster since the addition takes one
4166 ;; less cycle than a compare when feeding into a conditional move.
4167 ;; For this case, we also have an SImode pattern since we can merge the add
4168 ;; and sign extend and the order doesn't matter.
4169 ;;
4170 ;; We do not do this for floating-point, since it isn't clear how the "wrong"
4171 ;; operation could have been generated.
4172
4173 (define_split
4174   [(set (match_operand:DI 0 "register_operand" "")
4175         (if_then_else:DI
4176          (match_operator 1 "comparison_operator"
4177                          [(match_operand:DI 2 "reg_or_0_operand" "")
4178                           (match_operand:DI 3 "reg_or_cint_operand" "")])
4179          (match_operand:DI 4 "reg_or_cint_operand" "")
4180          (match_operand:DI 5 "reg_or_cint_operand" "")))
4181    (clobber (match_operand:DI 6 "register_operand" ""))]
4182   "operands[3] != const0_rtx"
4183   [(set (match_dup 6) (match_dup 7))
4184    (set (match_dup 0)
4185         (if_then_else:DI (match_dup 8) (match_dup 4) (match_dup 5)))]
4186 {
4187   enum rtx_code code = GET_CODE (operands[1]);
4188   int unsignedp = (code == GEU || code == LEU || code == GTU || code == LTU);
4189
4190   /* If we are comparing for equality with a constant and that constant
4191      appears in the arm when the register equals the constant, use the
4192      register since that is more likely to match (and to produce better code
4193      if both would).  */
4194
4195   if (code == EQ && GET_CODE (operands[3]) == CONST_INT
4196       && rtx_equal_p (operands[4], operands[3]))
4197     operands[4] = operands[2];
4198
4199   else if (code == NE && GET_CODE (operands[3]) == CONST_INT
4200            && rtx_equal_p (operands[5], operands[3]))
4201     operands[5] = operands[2];
4202
4203   if (code == NE || code == EQ
4204       || (extended_count (operands[2], DImode, unsignedp) >= 1
4205           && extended_count (operands[3], DImode, unsignedp) >= 1))
4206     {
4207       if (GET_CODE (operands[3]) == CONST_INT)
4208         operands[7] = gen_rtx_PLUS (DImode, operands[2],
4209                                     GEN_INT (- INTVAL (operands[3])));
4210       else
4211         operands[7] = gen_rtx_MINUS (DImode, operands[2], operands[3]);
4212
4213       operands[8] = gen_rtx_fmt_ee (code, VOIDmode, operands[6], const0_rtx);
4214     }
4215
4216   else if (code == EQ || code == LE || code == LT
4217            || code == LEU || code == LTU)
4218     {
4219       operands[7] = gen_rtx_fmt_ee (code, DImode, operands[2], operands[3]);
4220       operands[8] = gen_rtx_NE (VOIDmode, operands[6], const0_rtx);
4221     }
4222   else
4223     {
4224       operands[7] = gen_rtx_fmt_ee (reverse_condition (code), DImode,
4225                                     operands[2], operands[3]);
4226       operands[8] = gen_rtx_EQ (VOIDmode, operands[6], const0_rtx);
4227     }
4228 })
4229
4230 (define_split
4231   [(set (match_operand:DI 0 "register_operand" "")
4232         (if_then_else:DI
4233          (match_operator 1 "comparison_operator"
4234                          [(match_operand:SI 2 "reg_or_0_operand" "")
4235                           (match_operand:SI 3 "reg_or_cint_operand" "")])
4236          (match_operand:DI 4 "reg_or_8bit_operand" "")
4237          (match_operand:DI 5 "reg_or_8bit_operand" "")))
4238    (clobber (match_operand:DI 6 "register_operand" ""))]
4239   "operands[3] != const0_rtx
4240    && (GET_CODE (operands[1]) == EQ || GET_CODE (operands[1]) == NE)"
4241   [(set (match_dup 6) (match_dup 7))
4242    (set (match_dup 0)
4243         (if_then_else:DI (match_dup 8) (match_dup 4) (match_dup 5)))]
4244 {
4245   enum rtx_code code = GET_CODE (operands[1]);
4246   int unsignedp = (code == GEU || code == LEU || code == GTU || code == LTU);
4247   rtx tem;
4248
4249   if ((code != NE && code != EQ
4250        && ! (extended_count (operands[2], DImode, unsignedp) >= 1
4251              && extended_count (operands[3], DImode, unsignedp) >= 1)))
4252     FAIL;
4253
4254   if (GET_CODE (operands[3]) == CONST_INT)
4255     tem = gen_rtx_PLUS (SImode, operands[2],
4256                         GEN_INT (- INTVAL (operands[3])));
4257   else
4258     tem = gen_rtx_MINUS (SImode, operands[2], operands[3]);
4259
4260   operands[7] = gen_rtx_SIGN_EXTEND (DImode, tem);
4261   operands[8] = gen_rtx_fmt_ee (GET_CODE (operands[1]), VOIDmode,
4262                                 operands[6], const0_rtx);
4263 })
4264
4265 (define_split
4266   [(set (pc)
4267         (if_then_else
4268          (match_operator 1 "comparison_operator"
4269                          [(match_operand:DI 2 "reg_or_0_operand" "")
4270                           (match_operand:DI 3 "reg_or_cint_operand" "")])
4271          (label_ref (match_operand 0 "" ""))
4272          (pc)))
4273    (clobber (match_operand:DI 4 "register_operand" ""))]
4274   "operands[3] != const0_rtx"
4275   [(set (match_dup 4) (match_dup 5))
4276    (set (pc) (if_then_else (match_dup 6) (label_ref (match_dup 0)) (pc)))]
4277 {
4278   enum rtx_code code = GET_CODE (operands[1]);
4279   int unsignedp = (code == GEU || code == LEU || code == GTU || code == LTU);
4280
4281   if (code == NE || code == EQ
4282       || (extended_count (operands[2], DImode, unsignedp) >= 1
4283           && extended_count (operands[3], DImode, unsignedp) >= 1))
4284     {
4285       if (GET_CODE (operands[3]) == CONST_INT)
4286         operands[5] = gen_rtx_PLUS (DImode, operands[2],
4287                                     GEN_INT (- INTVAL (operands[3])));
4288       else
4289         operands[5] = gen_rtx_MINUS (DImode, operands[2], operands[3]);
4290
4291       operands[6] = gen_rtx_fmt_ee (code, VOIDmode, operands[4], const0_rtx);
4292     }
4293
4294   else if (code == EQ || code == LE || code == LT
4295            || code == LEU || code == LTU)
4296     {
4297       operands[5] = gen_rtx_fmt_ee (code, DImode, operands[2], operands[3]);
4298       operands[6] = gen_rtx_NE (VOIDmode, operands[4], const0_rtx);
4299     }
4300   else
4301     {
4302       operands[5] = gen_rtx_fmt_ee (reverse_condition (code), DImode,
4303                                     operands[2], operands[3]);
4304       operands[6] = gen_rtx_EQ (VOIDmode, operands[4], const0_rtx);
4305     }
4306 })
4307
4308 (define_split
4309   [(set (pc)
4310         (if_then_else
4311          (match_operator 1 "comparison_operator"
4312                          [(match_operand:SI 2 "reg_or_0_operand" "")
4313                           (match_operand:SI 3 "const_int_operand" "")])
4314          (label_ref (match_operand 0 "" ""))
4315          (pc)))
4316    (clobber (match_operand:DI 4 "register_operand" ""))]
4317   "operands[3] != const0_rtx
4318    && (GET_CODE (operands[1]) == EQ || GET_CODE (operands[1]) == NE)"
4319   [(set (match_dup 4) (match_dup 5))
4320    (set (pc) (if_then_else (match_dup 6) (label_ref (match_dup 0)) (pc)))]
4321 {
4322   rtx tem;
4323
4324   if (GET_CODE (operands[3]) == CONST_INT)
4325     tem = gen_rtx_PLUS (SImode, operands[2],
4326                         GEN_INT (- INTVAL (operands[3])));
4327   else
4328     tem = gen_rtx_MINUS (SImode, operands[2], operands[3]);
4329
4330   operands[5] = gen_rtx_SIGN_EXTEND (DImode, tem);
4331   operands[6] = gen_rtx_fmt_ee (GET_CODE (operands[1]), VOIDmode,
4332                                 operands[4], const0_rtx);
4333 })
4334
4335 ;; We can convert such things as "a > 0xffff" to "t = a & ~ 0xffff; t != 0".
4336 ;; This eliminates one, and sometimes two, insns when the AND can be done
4337 ;; with a ZAP.
4338 (define_split
4339   [(set (match_operand:DI 0 "register_operand" "")
4340         (match_operator:DI 1 "comparison_operator"
4341                         [(match_operand:DI 2 "register_operand" "")
4342                          (match_operand:DI 3 "const_int_operand" "")]))
4343    (clobber (match_operand:DI 4 "register_operand" ""))]
4344   "exact_log2 (INTVAL (operands[3]) + 1) >= 0
4345    && (GET_CODE (operands[1]) == GTU
4346        || GET_CODE (operands[1]) == LEU
4347        || ((GET_CODE (operands[1]) == GT || GET_CODE (operands[1]) == LE)
4348            && extended_count (operands[2], DImode, 1) > 0))"
4349   [(set (match_dup 4) (and:DI (match_dup 2) (match_dup 5)))
4350    (set (match_dup 0) (match_dup 6))]
4351 {
4352   operands[5] = GEN_INT (~ INTVAL (operands[3]));
4353   operands[6] = gen_rtx_fmt_ee (((GET_CODE (operands[1]) == GTU
4354                                   || GET_CODE (operands[1]) == GT)
4355                                  ? NE : EQ),
4356                                 DImode, operands[4], const0_rtx);
4357 })
4358
4359 ;; Prefer to use cmp and arithmetic when possible instead of a cmove.
4360
4361 (define_split
4362   [(set (match_operand 0 "register_operand" "")
4363         (if_then_else (match_operator 1 "signed_comparison_operator"
4364                            [(match_operand:DI 2 "reg_or_0_operand" "")
4365                             (const_int 0)])
4366           (match_operand 3 "const_int_operand" "")
4367           (match_operand 4 "const_int_operand" "")))]
4368   ""
4369   [(const_int 0)]
4370 {
4371   if (alpha_split_conditional_move (GET_CODE (operands[1]), operands[0],
4372                                     operands[2], operands[3], operands[4]))
4373     DONE;
4374   else
4375     FAIL;
4376 })
4377
4378 ;; ??? Why combine is allowed to create such non-canonical rtl, I don't know.
4379 ;; Oh well, we match it in movcc, so it must be partially our fault.
4380 (define_split
4381   [(set (match_operand 0 "register_operand" "")
4382         (if_then_else (match_operator 1 "signed_comparison_operator"
4383                            [(const_int 0)
4384                             (match_operand:DI 2 "reg_or_0_operand" "")])
4385           (match_operand 3 "const_int_operand" "")
4386           (match_operand 4 "const_int_operand" "")))]
4387   ""
4388   [(const_int 0)]
4389 {
4390   if (alpha_split_conditional_move (swap_condition (GET_CODE (operands[1])),
4391                                     operands[0], operands[2], operands[3],
4392                                     operands[4]))
4393     DONE;
4394   else
4395     FAIL;
4396 })
4397
4398 (define_insn_and_split "*cmp_sadd_di"
4399   [(set (match_operand:DI 0 "register_operand" "=r")
4400         (plus:DI (if_then_else:DI
4401                    (match_operator 1 "alpha_zero_comparison_operator"
4402                      [(match_operand:DI 2 "reg_or_0_operand" "rJ")
4403                       (const_int 0)])
4404                    (match_operand:DI 3 "const48_operand" "I")
4405                    (const_int 0))
4406                  (match_operand:DI 4 "sext_add_operand" "rIO")))
4407    (clobber (match_scratch:DI 5 "=r"))]
4408   ""
4409   "#"
4410   "! no_new_pseudos || reload_completed"
4411   [(set (match_dup 5)
4412         (match_op_dup:DI 1 [(match_dup 2) (const_int 0)]))
4413    (set (match_dup 0)
4414         (plus:DI (mult:DI (match_dup 5) (match_dup 3))
4415                  (match_dup 4)))]
4416 {
4417   if (! no_new_pseudos)
4418     operands[5] = gen_reg_rtx (DImode);
4419   else if (reg_overlap_mentioned_p (operands[5], operands[4]))
4420     operands[5] = operands[0];
4421 })
4422
4423 (define_insn_and_split "*cmp_sadd_si"
4424   [(set (match_operand:SI 0 "register_operand" "=r")
4425         (plus:SI (if_then_else:SI
4426                    (match_operator 1 "alpha_zero_comparison_operator"
4427                      [(match_operand:DI 2 "reg_or_0_operand" "rJ")
4428                       (const_int 0)])
4429                    (match_operand:SI 3 "const48_operand" "I")
4430                    (const_int 0))
4431                  (match_operand:SI 4 "sext_add_operand" "rIO")))
4432    (clobber (match_scratch:SI 5 "=r"))]
4433   ""
4434   "#"
4435   "! no_new_pseudos || reload_completed"
4436   [(set (match_dup 5)
4437         (match_op_dup:SI 1 [(match_dup 2) (const_int 0)]))
4438    (set (match_dup 0)
4439         (plus:SI (mult:SI (match_dup 5) (match_dup 3))
4440                  (match_dup 4)))]
4441 {
4442   if (! no_new_pseudos)
4443     operands[5] = gen_reg_rtx (DImode);
4444   else if (reg_overlap_mentioned_p (operands[5], operands[4]))
4445     operands[5] = operands[0];
4446 })
4447
4448 (define_insn_and_split "*cmp_sadd_sidi"
4449   [(set (match_operand:DI 0 "register_operand" "=r")
4450         (sign_extend:DI
4451           (plus:SI (if_then_else:SI
4452                      (match_operator 1 "alpha_zero_comparison_operator"
4453                        [(match_operand:DI 2 "reg_or_0_operand" "rJ")
4454                         (const_int 0)])
4455                      (match_operand:SI 3 "const48_operand" "I")
4456                      (const_int 0))
4457                    (match_operand:SI 4 "sext_add_operand" "rIO"))))
4458    (clobber (match_scratch:SI 5 "=r"))]
4459   ""
4460   "#"
4461   "! no_new_pseudos || reload_completed"
4462   [(set (match_dup 5)
4463         (match_op_dup:SI 1 [(match_dup 2) (const_int 0)]))
4464    (set (match_dup 0)
4465         (sign_extend:DI (plus:SI (mult:SI (match_dup 5) (match_dup 3))
4466                                  (match_dup 4))))]
4467 {
4468   if (! no_new_pseudos)
4469     operands[5] = gen_reg_rtx (DImode);
4470   else if (reg_overlap_mentioned_p (operands[5], operands[4]))
4471     operands[5] = operands[0];
4472 })
4473
4474 (define_insn_and_split "*cmp_ssub_di"
4475   [(set (match_operand:DI 0 "register_operand" "=r")
4476         (minus:DI (if_then_else:DI
4477                     (match_operator 1 "alpha_zero_comparison_operator"
4478                       [(match_operand:DI 2 "reg_or_0_operand" "rJ")
4479                        (const_int 0)])
4480                     (match_operand:DI 3 "const48_operand" "I")
4481                     (const_int 0))
4482                   (match_operand:DI 4 "reg_or_8bit_operand" "rI")))
4483    (clobber (match_scratch:DI 5 "=r"))]
4484   ""
4485   "#"
4486   "! no_new_pseudos || reload_completed"
4487   [(set (match_dup 5)
4488         (match_op_dup:DI 1 [(match_dup 2) (const_int 0)]))
4489    (set (match_dup 0)
4490         (minus:DI (mult:DI (match_dup 5) (match_dup 3))
4491                   (match_dup 4)))]
4492 {
4493   if (! no_new_pseudos)
4494     operands[5] = gen_reg_rtx (DImode);
4495   else if (reg_overlap_mentioned_p (operands[5], operands[4]))
4496     operands[5] = operands[0];
4497 })
4498
4499 (define_insn_and_split "*cmp_ssub_si"
4500   [(set (match_operand:SI 0 "register_operand" "=r")
4501         (minus:SI (if_then_else:SI
4502                     (match_operator 1 "alpha_zero_comparison_operator"
4503                       [(match_operand:DI 2 "reg_or_0_operand" "rJ")
4504                        (const_int 0)])
4505                     (match_operand:SI 3 "const48_operand" "I")
4506                     (const_int 0))
4507                   (match_operand:SI 4 "reg_or_8bit_operand" "rI")))
4508    (clobber (match_scratch:SI 5 "=r"))]
4509   ""
4510   "#"
4511   "! no_new_pseudos || reload_completed"
4512   [(set (match_dup 5)
4513         (match_op_dup:SI 1 [(match_dup 2) (const_int 0)]))
4514    (set (match_dup 0)
4515         (minus:SI (mult:SI (match_dup 5) (match_dup 3))
4516                  (match_dup 4)))]
4517 {
4518   if (! no_new_pseudos)
4519     operands[5] = gen_reg_rtx (DImode);
4520   else if (reg_overlap_mentioned_p (operands[5], operands[4]))
4521     operands[5] = operands[0];
4522 })
4523
4524 (define_insn_and_split "*cmp_ssub_sidi"
4525   [(set (match_operand:DI 0 "register_operand" "=r")
4526         (sign_extend:DI
4527           (minus:SI (if_then_else:SI
4528                       (match_operator 1 "alpha_zero_comparison_operator"
4529                         [(match_operand:DI 2 "reg_or_0_operand" "rJ")
4530                          (const_int 0)])
4531                       (match_operand:SI 3 "const48_operand" "I")
4532                       (const_int 0))
4533                     (match_operand:SI 4 "reg_or_8bit_operand" "rI"))))
4534    (clobber (match_scratch:SI 5 "=r"))]
4535   ""
4536   "#"
4537   "! no_new_pseudos || reload_completed"
4538   [(set (match_dup 5)
4539         (match_op_dup:SI 1 [(match_dup 2) (const_int 0)]))
4540    (set (match_dup 0)
4541         (sign_extend:DI (minus:SI (mult:SI (match_dup 5) (match_dup 3))
4542                                   (match_dup 4))))]
4543 {
4544   if (! no_new_pseudos)
4545     operands[5] = gen_reg_rtx (DImode);
4546   else if (reg_overlap_mentioned_p (operands[5], operands[4]))
4547     operands[5] = operands[0];
4548 })
4549 \f
4550 ;; Here are the CALL and unconditional branch insns.  Calls on NT and OSF
4551 ;; work differently, so we have different patterns for each.
4552
4553 ;; On Unicos/Mk a call information word (CIW) must be generated for each
4554 ;; call. The CIW contains information about arguments passed in registers
4555 ;; and is stored in the caller's SSIB. Its offset relative to the beginning
4556 ;; of the SSIB is passed in $25. Handling this properly is quite complicated
4557 ;; in the presence of inlining since the CIWs for calls performed by the
4558 ;; inlined function must be stored in the SSIB of the function it is inlined
4559 ;; into as well. We encode the CIW in an unspec and append it to the list
4560 ;; of the CIWs for the current function only when the instruction for loading
4561 ;; $25 is generated.
4562
4563 (define_expand "call"
4564   [(use (match_operand:DI 0 "" ""))
4565    (use (match_operand 1 "" ""))
4566    (use (match_operand 2 "" ""))
4567    (use (match_operand 3 "" ""))]
4568   ""
4569 {
4570   if (TARGET_ABI_WINDOWS_NT)
4571     emit_call_insn (gen_call_nt (operands[0], operands[1]));
4572   else if (TARGET_ABI_OPEN_VMS)
4573     emit_call_insn (gen_call_vms (operands[0], operands[2]));
4574   else if (TARGET_ABI_UNICOSMK)
4575     emit_call_insn (gen_call_umk (operands[0], operands[2]));
4576   else
4577     emit_call_insn (gen_call_osf (operands[0], operands[1]));
4578   DONE;
4579 })
4580
4581 (define_expand "sibcall"
4582   [(parallel [(call (mem:DI (match_operand 0 "" ""))
4583                             (match_operand 1 "" ""))
4584               (unspec [(reg:DI 29)] UNSPEC_SIBCALL)])]
4585   "TARGET_ABI_OSF"
4586 {
4587   if (GET_CODE (operands[0]) != MEM)
4588     abort ();
4589   operands[0] = XEXP (operands[0], 0);
4590 })
4591
4592 (define_expand "call_osf"
4593   [(parallel [(call (mem:DI (match_operand 0 "" ""))
4594                     (match_operand 1 "" ""))
4595               (use (reg:DI 29))
4596               (clobber (reg:DI 26))])]
4597   ""
4598 {
4599   if (GET_CODE (operands[0]) != MEM)
4600     abort ();
4601
4602   operands[0] = XEXP (operands[0], 0);
4603   if (! call_operand (operands[0], Pmode))
4604     operands[0] = copy_to_mode_reg (Pmode, operands[0]);
4605 })
4606
4607 (define_expand "call_nt"
4608   [(parallel [(call (mem:DI (match_operand 0 "" ""))
4609                     (match_operand 1 "" ""))
4610               (clobber (reg:DI 26))])]
4611   ""
4612 {
4613   if (GET_CODE (operands[0]) != MEM)
4614     abort ();
4615
4616   operands[0] = XEXP (operands[0], 0);
4617   if (GET_CODE (operands[0]) != SYMBOL_REF && GET_CODE (operands[0]) != REG)
4618     operands[0] = force_reg (DImode, operands[0]);
4619 })
4620
4621 ;; Calls on Unicos/Mk are always indirect.
4622 ;; op 0: symbol ref for called function
4623 ;; op 1: CIW for $25 represented by an unspec
4624
4625 (define_expand "call_umk"
4626    [(parallel [(call (mem:DI (match_operand 0 "" ""))
4627                      (match_operand 1 "" ""))
4628                (use (reg:DI 25))
4629                (clobber (reg:DI 26))])]
4630    ""
4631 {
4632   if (GET_CODE (operands[0]) != MEM)
4633     abort ();
4634
4635   /* Always load the address of the called function into a register;
4636      load the CIW in $25.  */
4637
4638   operands[0] = XEXP (operands[0], 0);
4639   if (GET_CODE (operands[0]) != REG)
4640     operands[0] = force_reg (DImode, operands[0]);
4641
4642   emit_move_insn (gen_rtx_REG (DImode, 25), operands[1]);
4643 })
4644
4645 ;;
4646 ;; call openvms/alpha
4647 ;; op 0: symbol ref for called function
4648 ;; op 1: next_arg_reg (argument information value for R25)
4649 ;;
4650 (define_expand "call_vms"
4651   [(parallel [(call (mem:DI (match_operand 0 "" ""))
4652                     (match_operand 1 "" ""))
4653               (use (match_dup 2))
4654               (use (reg:DI 25))
4655               (use (reg:DI 26))
4656               (clobber (reg:DI 27))])]
4657   ""
4658 {
4659   if (GET_CODE (operands[0]) != MEM)
4660     abort ();
4661
4662   operands[0] = XEXP (operands[0], 0);
4663
4664   /* Always load AI with argument information, then handle symbolic and
4665      indirect call differently.  Load RA and set operands[2] to PV in
4666      both cases.  */
4667
4668   emit_move_insn (gen_rtx_REG (DImode, 25), operands[1]);
4669   if (GET_CODE (operands[0]) == SYMBOL_REF)
4670     {
4671       rtx linkage = alpha_need_linkage (XSTR (operands[0], 0), 0);
4672
4673       emit_move_insn (gen_rtx_REG (Pmode, 26), gen_rtx_MEM (Pmode, linkage));
4674       operands[2]
4675         = validize_mem (gen_rtx_MEM (Pmode, plus_constant (linkage, 8)));
4676     }
4677   else
4678     {
4679       emit_move_insn (gen_rtx_REG (Pmode, 26),
4680                       gen_rtx_MEM (Pmode, plus_constant (operands[0], 8)));
4681       operands[2] = operands[0];
4682     }
4683
4684 })
4685
4686 (define_expand "call_value"
4687   [(use (match_operand 0 "" ""))
4688    (use (match_operand:DI 1 "" ""))
4689    (use (match_operand 2 "" ""))
4690    (use (match_operand 3 "" ""))
4691    (use (match_operand 4 "" ""))]
4692   ""
4693 {
4694   if (TARGET_ABI_WINDOWS_NT)
4695     emit_call_insn (gen_call_value_nt (operands[0], operands[1], operands[2]));
4696   else if (TARGET_ABI_OPEN_VMS)
4697     emit_call_insn (gen_call_value_vms (operands[0], operands[1],
4698                                         operands[3]));
4699   else if (TARGET_ABI_UNICOSMK)
4700     emit_call_insn (gen_call_value_umk (operands[0], operands[1],
4701                                         operands[3]));
4702   else
4703     emit_call_insn (gen_call_value_osf (operands[0], operands[1],
4704                                         operands[2]));
4705   DONE;
4706 })
4707
4708 (define_expand "sibcall_value"
4709   [(parallel [(set (match_operand 0 "" "")
4710                    (call (mem:DI (match_operand 1 "" ""))
4711                          (match_operand 2 "" "")))
4712               (unspec [(reg:DI 29)] UNSPEC_SIBCALL)])]
4713   "TARGET_ABI_OSF"
4714 {
4715   if (GET_CODE (operands[1]) != MEM)
4716     abort ();
4717   operands[1] = XEXP (operands[1], 0);
4718 })
4719
4720 (define_expand "call_value_osf"
4721   [(parallel [(set (match_operand 0 "" "")
4722                    (call (mem:DI (match_operand 1 "" ""))
4723                          (match_operand 2 "" "")))
4724               (use (reg:DI 29))
4725               (clobber (reg:DI 26))])]
4726   ""
4727 {
4728   if (GET_CODE (operands[1]) != MEM)
4729     abort ();
4730
4731   operands[1] = XEXP (operands[1], 0);
4732   if (! call_operand (operands[1], Pmode))
4733     operands[1] = copy_to_mode_reg (Pmode, operands[1]);
4734 })
4735
4736 (define_expand "call_value_nt"
4737   [(parallel [(set (match_operand 0 "" "")
4738                    (call (mem:DI (match_operand 1 "" ""))
4739                          (match_operand 2 "" "")))
4740               (clobber (reg:DI 26))])]
4741   ""
4742 {
4743   if (GET_CODE (operands[1]) != MEM)
4744     abort ();
4745
4746   operands[1] = XEXP (operands[1], 0);
4747   if (GET_CODE (operands[1]) != SYMBOL_REF && GET_CODE (operands[1]) != REG)
4748     operands[1] = force_reg (DImode, operands[1]);
4749 })
4750
4751 (define_expand "call_value_vms"
4752   [(parallel [(set (match_operand 0 "" "")
4753                    (call (mem:DI (match_operand:DI 1 "" ""))
4754                          (match_operand 2 "" "")))
4755               (use (match_dup 3))
4756               (use (reg:DI 25))
4757               (use (reg:DI 26))
4758               (clobber (reg:DI 27))])]
4759   ""
4760 {
4761   if (GET_CODE (operands[1]) != MEM)
4762     abort ();
4763
4764   operands[1] = XEXP (operands[1], 0);
4765
4766   /* Always load AI with argument information, then handle symbolic and
4767      indirect call differently.  Load RA and set operands[3] to PV in
4768      both cases.  */
4769
4770   emit_move_insn (gen_rtx_REG (DImode, 25), operands[2]);
4771   if (GET_CODE (operands[1]) == SYMBOL_REF)
4772     {
4773       rtx linkage = alpha_need_linkage (XSTR (operands[1], 0), 0);
4774
4775       emit_move_insn (gen_rtx_REG (Pmode, 26), gen_rtx_MEM (Pmode, linkage));
4776       operands[3]
4777         = validize_mem (gen_rtx_MEM (Pmode, plus_constant (linkage, 8)));
4778     }
4779   else
4780     {
4781       emit_move_insn (gen_rtx_REG (Pmode, 26),
4782                       gen_rtx_MEM (Pmode, plus_constant (operands[1], 8)));
4783       operands[3] = operands[1];
4784     }
4785 })
4786
4787 (define_expand "call_value_umk"
4788   [(parallel [(set (match_operand 0 "" "")
4789                    (call (mem:DI (match_operand 1 "" ""))
4790                          (match_operand 2 "" "")))
4791               (use (reg:DI 25))
4792               (clobber (reg:DI 26))])]
4793   ""
4794 {
4795   if (GET_CODE (operands[1]) != MEM)
4796     abort ();
4797
4798   operands[1] = XEXP (operands[1], 0);
4799   if (GET_CODE (operands[1]) != REG)
4800     operands[1] = force_reg (DImode, operands[1]);
4801
4802   emit_move_insn (gen_rtx_REG (DImode, 25), operands[2]);
4803 })
4804
4805 (define_insn "*call_osf_1_er"
4806   [(call (mem:DI (match_operand:DI 0 "call_operand" "c,R,s"))
4807          (match_operand 1 "" ""))
4808    (use (reg:DI 29))
4809    (clobber (reg:DI 26))]
4810   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
4811   "@
4812    jsr $26,(%0),0\;ldah $29,0($26)\t\t!gpdisp!%*\;lda $29,0($29)\t\t!gpdisp!%*
4813    bsr $26,$%0..ng
4814    ldq $27,%0($29)\t\t!literal!%#\;jsr $26,($27),%0\t\t!lituse_jsr!%#\;ldah $29,0($26)\t\t!gpdisp!%*\;lda $29,0($29)\t\t!gpdisp!%*"
4815   [(set_attr "type" "jsr")
4816    (set_attr "length" "12,*,16")])
4817
4818 ;; We must use peep2 instead of a split because we need accurate life
4819 ;; information for $gp.  Consider the case of { bar(); while (1); }.
4820 (define_peephole2
4821   [(parallel [(call (mem:DI (match_operand:DI 0 "call_operand" ""))
4822                     (match_operand 1 "" ""))
4823               (use (reg:DI 29))
4824               (clobber (reg:DI 26))])]
4825   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF && reload_completed
4826    && ! current_file_function_operand (operands[0], Pmode)
4827    && peep2_regno_dead_p (1, 29)"
4828   [(parallel [(call (mem:DI (match_dup 2))
4829                     (match_dup 1))
4830               (set (reg:DI 26) (plus:DI (pc) (const_int 4)))
4831               (unspec_volatile [(reg:DI 29)] UNSPECV_BLOCKAGE)
4832               (use (match_dup 0))
4833               (use (match_dup 3))])]
4834 {
4835   if (CONSTANT_P (operands[0]))
4836     {
4837       operands[2] = gen_rtx_REG (Pmode, 27);
4838       operands[3] = GEN_INT (alpha_next_sequence_number++);
4839       emit_insn (gen_movdi_er_high_g (operands[2], pic_offset_table_rtx,
4840                                       operands[0], operands[3]));
4841     }
4842   else
4843     {
4844       operands[2] = operands[0];
4845       operands[0] = const0_rtx;
4846       operands[3] = const0_rtx;
4847     }
4848 })
4849
4850 (define_peephole2
4851   [(parallel [(call (mem:DI (match_operand:DI 0 "call_operand" ""))
4852                     (match_operand 1 "" ""))
4853               (use (reg:DI 29))
4854               (clobber (reg:DI 26))])]
4855   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF && reload_completed
4856    && ! current_file_function_operand (operands[0], Pmode)
4857    && ! peep2_regno_dead_p (1, 29)"
4858   [(parallel [(call (mem:DI (match_dup 2))
4859                     (match_dup 1))
4860               (set (reg:DI 26) (plus:DI (pc) (const_int 4)))
4861               (unspec_volatile [(reg:DI 29)] UNSPECV_BLOCKAGE)
4862               (use (match_dup 0))
4863               (use (match_dup 4))])
4864    (set (reg:DI 29)
4865         (unspec_volatile:DI [(reg:DI 26) (match_dup 3)] UNSPECV_LDGP1))
4866    (set (reg:DI 29)
4867         (unspec:DI [(reg:DI 29) (match_dup 3)] UNSPEC_LDGP2))]
4868 {
4869   if (CONSTANT_P (operands[0]))
4870     {
4871       operands[2] = gen_rtx_REG (Pmode, 27);
4872       operands[4] = GEN_INT (alpha_next_sequence_number++);
4873       emit_insn (gen_movdi_er_high_g (operands[2], pic_offset_table_rtx,
4874                                       operands[0], operands[4]));
4875     }
4876   else
4877     {
4878       operands[2] = operands[0];
4879       operands[0] = const0_rtx;
4880       operands[4] = const0_rtx;
4881     }
4882   operands[3] = GEN_INT (alpha_next_sequence_number++);
4883 })
4884
4885 ;; We add a blockage unspec_volatile to prevent insns from moving down
4886 ;; from above the call to in between the call and the ldah gpdisp.
4887
4888 (define_insn "*call_osf_2_er"
4889   [(call (mem:DI (match_operand:DI 0 "register_operand" "c"))
4890          (match_operand 1 "" ""))
4891    (set (reg:DI 26) (plus:DI (pc) (const_int 4)))
4892    (unspec_volatile [(reg:DI 29)] UNSPECV_BLOCKAGE)
4893    (use (match_operand 2 "" ""))
4894    (use (match_operand 3 "const_int_operand" ""))]
4895   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
4896   "jsr $26,(%0),%2%J3"
4897   [(set_attr "type" "jsr")])
4898
4899 (define_insn "*call_osf_1_noreturn"
4900   [(call (mem:DI (match_operand:DI 0 "call_operand" "c,R,s"))
4901          (match_operand 1 "" ""))
4902    (use (reg:DI 29))
4903    (clobber (reg:DI 26))]
4904   "! TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF
4905    && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
4906   "@
4907    jsr $26,($27),0
4908    bsr $26,$%0..ng
4909    jsr $26,%0"
4910   [(set_attr "type" "jsr")
4911    (set_attr "length" "*,*,8")])
4912
4913 (define_insn "*call_osf_1"
4914   [(call (mem:DI (match_operand:DI 0 "call_operand" "c,R,s"))
4915          (match_operand 1 "" ""))
4916    (use (reg:DI 29))
4917    (clobber (reg:DI 26))]
4918   "! TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
4919   "@
4920    jsr $26,($27),0\;ldgp $29,0($26)
4921    bsr $26,$%0..ng
4922    jsr $26,%0\;ldgp $29,0($26)"
4923   [(set_attr "type" "jsr")
4924    (set_attr "length" "12,*,16")])
4925
4926 ;; Note that the DEC assembler expands "jmp foo" with $at, which
4927 ;; doesn't do what we want.
4928 (define_insn "*sibcall_osf_1_er"
4929   [(call (mem:DI (match_operand:DI 0 "symbolic_operand" "R,s"))
4930          (match_operand 1 "" ""))
4931    (unspec [(reg:DI 29)] UNSPEC_SIBCALL)]
4932   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
4933   "@
4934    br $31,$%0..ng
4935    ldq $27,%0($29)\t\t!literal!%#\;jmp $31,($27),%0\t\t!lituse_jsr!%#"
4936   [(set_attr "type" "jsr")
4937    (set_attr "length" "*,8")])
4938
4939 (define_insn "*sibcall_osf_1"
4940   [(call (mem:DI (match_operand:DI 0 "symbolic_operand" "R,s"))
4941          (match_operand 1 "" ""))
4942    (unspec [(reg:DI 29)] UNSPEC_SIBCALL)]
4943   "! TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
4944   "@
4945    br $31,$%0..ng
4946    lda $27,%0\;jmp $31,($27),%0"
4947   [(set_attr "type" "jsr")
4948    (set_attr "length" "*,8")])
4949
4950 (define_insn "*call_nt_1"
4951   [(call (mem:DI (match_operand:DI 0 "call_operand" "r,R,s"))
4952          (match_operand 1 "" ""))
4953    (clobber (reg:DI 26))]
4954   "TARGET_ABI_WINDOWS_NT"
4955   "@
4956    jsr $26,(%0)
4957    bsr $26,%0
4958    jsr $26,%0"
4959   [(set_attr "type" "jsr")
4960    (set_attr "length" "*,*,12")])
4961
4962 (define_insn "*call_vms_1"
4963   [(call (mem:DI (match_operand:DI 0 "call_operand" "r,s"))
4964          (match_operand 1 "" ""))
4965    (use (match_operand:DI 2 "nonimmediate_operand" "r,m"))
4966    (use (reg:DI 25))
4967    (use (reg:DI 26))
4968    (clobber (reg:DI 27))]
4969   "TARGET_ABI_OPEN_VMS"
4970   "@
4971    mov %2,$27\;jsr $26,0\;ldq $27,0($29)
4972    ldq $27,%2\;jsr $26,%0\;ldq $27,0($29)"
4973   [(set_attr "type" "jsr")
4974    (set_attr "length" "12,16")])
4975
4976 (define_insn "*call_umk_1"
4977   [(call (mem:DI (match_operand:DI 0 "call_operand" "r"))
4978          (match_operand 1 "" ""))
4979    (use (reg:DI 25))
4980    (clobber (reg:DI 26))]
4981   "TARGET_ABI_UNICOSMK"
4982   "jsr $26,(%0)"
4983   [(set_attr "type" "jsr")])
4984
4985 ;; Call subroutine returning any type.
4986
4987 (define_expand "untyped_call"
4988   [(parallel [(call (match_operand 0 "" "")
4989                     (const_int 0))
4990               (match_operand 1 "" "")
4991               (match_operand 2 "" "")])]
4992   ""
4993 {
4994   int i;
4995
4996   emit_call_insn (GEN_CALL (operands[0], const0_rtx, NULL, const0_rtx));
4997
4998   for (i = 0; i < XVECLEN (operands[2], 0); i++)
4999     {
5000       rtx set = XVECEXP (operands[2], 0, i);
5001       emit_move_insn (SET_DEST (set), SET_SRC (set));
5002     }
5003
5004   /* The optimizer does not know that the call sets the function value
5005      registers we stored in the result block.  We avoid problems by
5006      claiming that all hard registers are used and clobbered at this
5007      point.  */
5008   emit_insn (gen_blockage ());
5009
5010   DONE;
5011 })
5012
5013 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
5014 ;; all of memory.  This blocks insns from being moved across this point.
5015
5016 (define_insn "blockage"
5017   [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
5018   ""
5019   ""
5020   [(set_attr "length" "0")])
5021
5022 (define_insn "jump"
5023   [(set (pc)
5024         (label_ref (match_operand 0 "" "")))]
5025   ""
5026   "br $31,%l0"
5027   [(set_attr "type" "ibr")])
5028
5029 (define_expand "return"
5030   [(return)]
5031   "direct_return ()"
5032   "")
5033
5034 (define_insn "*return_internal"
5035   [(return)]
5036   "reload_completed"
5037   "ret $31,($26),1"
5038   [(set_attr "type" "ibr")])
5039
5040 (define_insn "indirect_jump"
5041   [(set (pc) (match_operand:DI 0 "register_operand" "r"))]
5042   ""
5043   "jmp $31,(%0),0"
5044   [(set_attr "type" "ibr")])
5045
5046 (define_expand "tablejump"
5047   [(parallel [(set (pc)
5048                    (match_operand 0 "register_operand" ""))
5049               (use (label_ref:DI (match_operand 1 "" "")))])]
5050   ""
5051 {
5052   if (TARGET_ABI_WINDOWS_NT)
5053     {
5054       rtx dest = gen_reg_rtx (DImode);
5055       emit_insn (gen_extendsidi2 (dest, operands[0]));
5056       operands[0] = dest;
5057     }
5058   else if (TARGET_ABI_OSF)
5059     {
5060       rtx dest = gen_reg_rtx (DImode);
5061       emit_insn (gen_extendsidi2 (dest, operands[0]));
5062       emit_insn (gen_adddi3 (dest, pic_offset_table_rtx, dest));        
5063       operands[0] = dest;
5064     }
5065 })
5066
5067 (define_insn "*tablejump_osf_nt_internal"
5068   [(set (pc)
5069         (match_operand:DI 0 "register_operand" "r"))
5070    (use (label_ref:DI (match_operand 1 "" "")))]
5071   "(TARGET_ABI_OSF || TARGET_ABI_WINDOWS_NT)
5072    && alpha_tablejump_addr_vec (insn)"
5073 {
5074   operands[2] = alpha_tablejump_best_label (insn);
5075   return "jmp $31,(%0),%2";
5076 }
5077   [(set_attr "type" "ibr")])
5078
5079 (define_insn "*tablejump_internal"
5080   [(set (pc)
5081         (match_operand:DI 0 "register_operand" "r"))
5082    (use (label_ref (match_operand 1 "" "")))]
5083   ""
5084   "jmp $31,(%0),0"
5085   [(set_attr "type" "ibr")])
5086
5087 ;; Cache flush.  Used by INITIALIZE_TRAMPOLINE.  0x86 is PAL_imb, but we don't
5088 ;; want to have to include pal.h in our .s file.
5089 ;;
5090 ;; Technically the type for call_pal is jsr, but we use that for determining
5091 ;; if we need a GP.  Use ibr instead since it has the same EV5 scheduling
5092 ;; characteristics.
5093 (define_insn "imb"
5094   [(unspec_volatile [(const_int 0)] UNSPECV_IMB)]
5095   ""
5096   "call_pal 0x86"
5097   [(set_attr "type" "ibr")])
5098
5099 ;; BUGCHK is documented common to OSF/1 and VMS PALcode.
5100 ;; NT does not document anything at 0x81 -- presumably it would generate
5101 ;; the equivalent of SIGILL, but this isn't that important.
5102 ;; ??? Presuming unicosmk uses either OSF/1 or VMS PALcode.
5103 (define_insn "trap"
5104   [(trap_if (const_int 1) (const_int 0))]
5105   "!TARGET_ABI_WINDOWS_NT"
5106   "call_pal 0x81"
5107   [(set_attr "type" "ibr")])
5108 \f
5109 ;; Finally, we have the basic data motion insns.  The byte and word insns
5110 ;; are done via define_expand.  Start with the floating-point insns, since
5111 ;; they are simpler.
5112
5113 (define_insn "*movsf_nofix"
5114   [(set (match_operand:SF 0 "nonimmediate_operand" "=f,f,*r,*r,m,m")
5115         (match_operand:SF 1 "input_operand" "fG,m,*rG,m,fG,*r"))]
5116   "TARGET_FPREGS && ! TARGET_FIX
5117    && (register_operand (operands[0], SFmode)
5118        || reg_or_fp0_operand (operands[1], SFmode))"
5119   "@
5120    cpys %R1,%R1,%0
5121    ld%, %0,%1
5122    bis $31,%r1,%0
5123    ldl %0,%1
5124    st%, %R1,%0
5125    stl %r1,%0"
5126   [(set_attr "type" "fcpys,fld,ilog,ild,fst,ist")])
5127
5128 (define_insn "*movsf_fix"
5129   [(set (match_operand:SF 0 "nonimmediate_operand" "=f,f,*r,*r,m,m,f,*r")
5130         (match_operand:SF 1 "input_operand" "fG,m,*rG,m,fG,*r,*r,f"))]
5131   "TARGET_FPREGS && TARGET_FIX
5132    && (register_operand (operands[0], SFmode)
5133        || reg_or_fp0_operand (operands[1], SFmode))"
5134   "@
5135    cpys %R1,%R1,%0
5136    ld%, %0,%1
5137    bis $31,%r1,%0
5138    ldl %0,%1
5139    st%, %R1,%0
5140    stl %r1,%0
5141    itofs %1,%0
5142    ftois %1,%0"
5143   [(set_attr "type" "fcpys,fld,ilog,ild,fst,ist,itof,ftoi")])
5144
5145 (define_insn "*movsf_nofp"
5146   [(set (match_operand:SF 0 "nonimmediate_operand" "=r,r,m")
5147         (match_operand:SF 1 "input_operand" "rG,m,r"))]
5148   "! TARGET_FPREGS
5149    && (register_operand (operands[0], SFmode)
5150        || reg_or_fp0_operand (operands[1], SFmode))"
5151   "@
5152    bis $31,%r1,%0
5153    ldl %0,%1
5154    stl %r1,%0"
5155   [(set_attr "type" "ilog,ild,ist")])
5156
5157 (define_insn "*movdf_nofix"
5158   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,f,*r,*r,m,m")
5159         (match_operand:DF 1 "input_operand" "fG,m,*rG,m,fG,*r"))]
5160   "TARGET_FPREGS && ! TARGET_FIX
5161    && (register_operand (operands[0], DFmode)
5162        || reg_or_fp0_operand (operands[1], DFmode))"
5163   "@
5164    cpys %R1,%R1,%0
5165    ld%- %0,%1
5166    bis $31,%r1,%0
5167    ldq %0,%1
5168    st%- %R1,%0
5169    stq %r1,%0"
5170   [(set_attr "type" "fcpys,fld,ilog,ild,fst,ist")])
5171
5172 (define_insn "*movdf_fix"
5173   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,f,*r,*r,m,m,f,*r")
5174         (match_operand:DF 1 "input_operand" "fG,m,*rG,m,fG,*r,*r,f"))]
5175   "TARGET_FPREGS && TARGET_FIX
5176    && (register_operand (operands[0], DFmode)
5177        || reg_or_fp0_operand (operands[1], DFmode))"
5178   "@
5179    cpys %R1,%R1,%0
5180    ld%- %0,%1
5181    bis $31,%r1,%0
5182    ldq %0,%1
5183    st%- %R1,%0
5184    stq %r1,%0
5185    itoft %1,%0
5186    ftoit %1,%0"
5187   [(set_attr "type" "fcpys,fld,ilog,ild,fst,ist,itof,ftoi")])
5188
5189 (define_insn "*movdf_nofp"
5190   [(set (match_operand:DF 0 "nonimmediate_operand" "=r,r,m")
5191         (match_operand:DF 1 "input_operand" "rG,m,r"))]
5192   "! TARGET_FPREGS
5193    && (register_operand (operands[0], DFmode)
5194        || reg_or_fp0_operand (operands[1], DFmode))"
5195   "@
5196    bis $31,%r1,%0
5197    ldq %0,%1
5198    stq %r1,%0"
5199   [(set_attr "type" "ilog,ild,ist")])
5200
5201 ;; Subregs suck for register allocation.  Pretend we can move TFmode
5202 ;; data between general registers until after reload.
5203
5204 (define_insn_and_split "*movtf_internal"
5205   [(set (match_operand:TF 0 "nonimmediate_operand" "=r,o")
5206         (match_operand:TF 1 "input_operand" "roG,rG"))]
5207   "register_operand (operands[0], TFmode)
5208    || reg_or_fp0_operand (operands[1], TFmode)"
5209   "#"
5210   "reload_completed"
5211   [(set (match_dup 0) (match_dup 2))
5212    (set (match_dup 1) (match_dup 3))]
5213 {
5214   alpha_split_tfmode_pair (operands);
5215   if (reg_overlap_mentioned_p (operands[0], operands[3]))
5216     {
5217       rtx tmp;
5218       tmp = operands[0], operands[0] = operands[1], operands[1] = tmp;
5219       tmp = operands[2], operands[2] = operands[3], operands[3] = tmp;
5220     }
5221 })
5222
5223 (define_expand "movsf"
5224   [(set (match_operand:SF 0 "nonimmediate_operand" "")
5225         (match_operand:SF 1 "general_operand" ""))]
5226   ""
5227 {
5228   if (GET_CODE (operands[0]) == MEM
5229       && ! reg_or_fp0_operand (operands[1], SFmode))
5230     operands[1] = force_reg (SFmode, operands[1]);
5231 })
5232
5233 (define_expand "movdf"
5234   [(set (match_operand:DF 0 "nonimmediate_operand" "")
5235         (match_operand:DF 1 "general_operand" ""))]
5236   ""
5237 {
5238   if (GET_CODE (operands[0]) == MEM
5239       && ! reg_or_fp0_operand (operands[1], DFmode))
5240     operands[1] = force_reg (DFmode, operands[1]);
5241 })
5242
5243 (define_expand "movtf"
5244   [(set (match_operand:TF 0 "nonimmediate_operand" "")
5245         (match_operand:TF 1 "general_operand" ""))]
5246   ""
5247 {
5248   if (GET_CODE (operands[0]) == MEM
5249       && ! reg_or_fp0_operand (operands[1], TFmode))
5250     operands[1] = force_reg (TFmode, operands[1]);
5251 })
5252
5253 (define_insn "*movsi_nofix"
5254   [(set (match_operand:SI 0 "nonimmediate_operand" "=r,r,r,r,m,*f,*f,m")
5255         (match_operand:SI 1 "input_operand" "rJ,K,L,m,rJ,*fJ,m,*f"))]
5256   "(TARGET_ABI_OSF || TARGET_ABI_UNICOSMK) && ! TARGET_FIX
5257    && (register_operand (operands[0], SImode)
5258        || reg_or_0_operand (operands[1], SImode))"
5259   "@
5260    bis $31,%r1,%0
5261    lda %0,%1($31)
5262    ldah %0,%h1($31)
5263    ldl %0,%1
5264    stl %r1,%0
5265    cpys %R1,%R1,%0
5266    ld%, %0,%1
5267    st%, %R1,%0"
5268   [(set_attr "type" "ilog,iadd,iadd,ild,ist,fcpys,fld,fst")])
5269
5270 (define_insn "*movsi_fix"
5271   [(set (match_operand:SI 0 "nonimmediate_operand" "=r,r,r,r,m,*f,*f,m,r,*f")
5272         (match_operand:SI 1 "input_operand" "rJ,K,L,m,rJ,*fJ,m,*f,*f,r"))]
5273   "TARGET_ABI_OSF && TARGET_FIX
5274    && (register_operand (operands[0], SImode)
5275        || reg_or_0_operand (operands[1], SImode))"
5276   "@
5277    bis $31,%r1,%0
5278    lda %0,%1($31)
5279    ldah %0,%h1($31)
5280    ldl %0,%1
5281    stl %r1,%0
5282    cpys %R1,%R1,%0
5283    ld%, %0,%1
5284    st%, %R1,%0
5285    ftois %1,%0
5286    itofs %1,%0"
5287   [(set_attr "type" "ilog,iadd,iadd,ild,ist,fcpys,fld,fst,ftoi,itof")])
5288
5289 (define_insn "*movsi_nt_vms_nofix"
5290   [(set (match_operand:SI 0 "nonimmediate_operand" "=r,r,r,r,r,m,*f,*f,m")
5291         (match_operand:SI 1 "input_operand" "rJ,K,L,s,m,rJ,*fJ,m,*f"))]
5292   "(TARGET_ABI_WINDOWS_NT || TARGET_ABI_OPEN_VMS)
5293     && !TARGET_FIX
5294     && (register_operand (operands[0], SImode)
5295         || reg_or_0_operand (operands[1], SImode))"
5296   "@
5297    bis $31,%1,%0
5298    lda %0,%1
5299    ldah %0,%h1
5300    lda %0,%1
5301    ldl %0,%1
5302    stl %r1,%0
5303    cpys %R1,%R1,%0
5304    ld%, %0,%1
5305    st%, %R1,%0"
5306   [(set_attr "type" "ilog,iadd,iadd,ldsym,ild,ist,fcpys,fld,fst")])
5307
5308 (define_insn "*movsi_nt_vms_fix"
5309   [(set (match_operand:SI 0 "nonimmediate_operand" "=r,r,r,r,r,m,*f,*f,m,r,*f")
5310         (match_operand:SI 1 "input_operand" "rJ,K,L,s,m,rJ,*fJ,m,*f,*f,r"))]
5311   "(TARGET_ABI_WINDOWS_NT || TARGET_ABI_OPEN_VMS)
5312     && TARGET_FIX
5313     && (register_operand (operands[0], SImode)
5314         || reg_or_0_operand (operands[1], SImode))"
5315   "@
5316    bis $31,%1,%0
5317    lda %0,%1
5318    ldah %0,%h1
5319    lda %0,%1
5320    ldl %0,%1
5321    stl %r1,%0
5322    cpys %R1,%R1,%0
5323    ld%, %0,%1
5324    st%, %R1,%0
5325    ftois %1,%0
5326    itofs %1,%0"
5327   [(set_attr "type" "ilog,iadd,iadd,ldsym,ild,ist,fcpys,fld,fst,ftoi,itof")])
5328
5329 (define_insn "*movhi_nobwx"
5330   [(set (match_operand:HI 0 "register_operand" "=r,r")
5331         (match_operand:HI 1 "input_operand" "rJ,n"))]
5332   "! TARGET_BWX
5333    && (register_operand (operands[0], HImode)
5334        || register_operand (operands[1], HImode))"
5335   "@
5336    bis $31,%r1,%0
5337    lda %0,%L1($31)"
5338   [(set_attr "type" "ilog,iadd")])
5339
5340 (define_insn "*movhi_bwx"
5341   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
5342         (match_operand:HI 1 "input_operand" "rJ,n,m,rJ"))]
5343   "TARGET_BWX
5344    && (register_operand (operands[0], HImode)
5345        || reg_or_0_operand (operands[1], HImode))"
5346   "@
5347    bis $31,%r1,%0
5348    lda %0,%L1($31)
5349    ldwu %0,%1
5350    stw %r1,%0"
5351   [(set_attr "type" "ilog,iadd,ild,ist")])
5352
5353 (define_insn "*movqi_nobwx"
5354   [(set (match_operand:QI 0 "register_operand" "=r,r")
5355         (match_operand:QI 1 "input_operand" "rJ,n"))]
5356   "! TARGET_BWX
5357    && (register_operand (operands[0], QImode)
5358        || register_operand (operands[1], QImode))"
5359   "@
5360    bis $31,%r1,%0
5361    lda %0,%L1($31)"
5362   [(set_attr "type" "ilog,iadd")])
5363
5364 (define_insn "*movqi_bwx"
5365   [(set (match_operand:QI 0 "nonimmediate_operand" "=r,r,r,m")
5366         (match_operand:QI 1 "input_operand" "rJ,n,m,rJ"))]
5367   "TARGET_BWX
5368    && (register_operand (operands[0], QImode)
5369        || reg_or_0_operand (operands[1], QImode))"
5370   "@
5371    bis $31,%r1,%0
5372    lda %0,%L1($31)
5373    ldbu %0,%1
5374    stb %r1,%0"
5375   [(set_attr "type" "ilog,iadd,ild,ist")])
5376
5377 ;; We do two major things here: handle mem->mem and construct long
5378 ;; constants.
5379
5380 (define_expand "movsi"
5381   [(set (match_operand:SI 0 "nonimmediate_operand" "")
5382         (match_operand:SI 1 "general_operand" ""))]
5383   ""
5384 {
5385   if (alpha_expand_mov (SImode, operands))
5386     DONE;
5387 })
5388
5389 ;; Split a load of a large constant into the appropriate two-insn
5390 ;; sequence.
5391
5392 (define_split
5393   [(set (match_operand:SI 0 "register_operand" "")
5394         (match_operand:SI 1 "const_int_operand" ""))]
5395   "! add_operand (operands[1], SImode)"
5396   [(set (match_dup 0) (match_dup 2))
5397    (set (match_dup 0) (plus:SI (match_dup 0) (match_dup 3)))]
5398 {
5399   rtx tem
5400     = alpha_emit_set_const (operands[0], SImode, INTVAL (operands[1]), 2);
5401
5402   if (tem == operands[0])
5403     DONE;
5404   else
5405     FAIL;
5406 })
5407
5408 ;; Split the load of an address into a four-insn sequence on Unicos/Mk.
5409 ;; Always generate a REG_EQUAL note for the last instruction to facilitate
5410 ;; optimisations. If the symbolic operand is a label_ref, generate REG_LABEL
5411 ;; notes and update LABEL_NUSES because this is not done automatically.
5412 ;; Labels may be incorrectly deleted if we don't do this.
5413 ;;
5414 ;; Describing what the individual instructions do correctly is too complicated
5415 ;; so use UNSPECs for each of the three parts of an address.
5416
5417 (define_split
5418   [(set (match_operand:DI 0 "register_operand" "")
5419         (match_operand:DI 1 "symbolic_operand" ""))]
5420   "TARGET_ABI_UNICOSMK && reload_completed"
5421   [(const_int 0)]
5422 {
5423   rtx insn1, insn2, insn3;
5424
5425   insn1 = emit_insn (gen_umk_laum (operands[0], operands[1]));
5426   emit_insn (gen_ashldi3 (operands[0], operands[0], GEN_INT (32)));
5427   insn2 = emit_insn (gen_umk_lalm (operands[0], operands[0], operands[1]));
5428   insn3 = emit_insn (gen_umk_lal (operands[0], operands[0], operands[1]));
5429   REG_NOTES (insn3) = gen_rtx_EXPR_LIST (REG_EQUAL, operands[1],
5430                                          REG_NOTES (insn3));
5431   if (GET_CODE (operands[1]) == LABEL_REF)
5432     {
5433       rtx label;
5434
5435       label = XEXP (operands[1], 0);
5436       REG_NOTES (insn1) = gen_rtx_EXPR_LIST (REG_LABEL, label,
5437                                              REG_NOTES (insn1));
5438       REG_NOTES (insn2) = gen_rtx_EXPR_LIST (REG_LABEL, label,
5439                                              REG_NOTES (insn2));
5440       REG_NOTES (insn3) = gen_rtx_EXPR_LIST (REG_LABEL, label,
5441                                              REG_NOTES (insn3));
5442       LABEL_NUSES (label) += 3;
5443     }
5444   DONE;
5445 })
5446
5447 ;; Instructions for loading the three parts of an address on Unicos/Mk.
5448
5449 (define_insn "umk_laum"
5450   [(set (match_operand:DI 0 "register_operand" "=r")
5451         (unspec:DI [(match_operand:DI 1 "symbolic_operand" "")]
5452                    UNSPEC_UMK_LAUM))]
5453   "TARGET_ABI_UNICOSMK"
5454   "laum %r0,%t1($31)"
5455   [(set_attr "type" "iadd")])
5456
5457 (define_insn "umk_lalm"
5458   [(set (match_operand:DI 0 "register_operand" "=r")
5459         (plus:DI (match_operand:DI 1 "register_operand" "r")
5460                  (unspec:DI [(match_operand:DI 2 "symbolic_operand" "")]
5461                             UNSPEC_UMK_LALM)))] 
5462   "TARGET_ABI_UNICOSMK"
5463   "lalm %r0,%t2(%r1)"
5464   [(set_attr "type" "iadd")])
5465
5466 (define_insn "umk_lal"
5467   [(set (match_operand:DI 0 "register_operand" "=r")
5468         (plus:DI (match_operand:DI 1 "register_operand" "r")
5469                  (unspec:DI [(match_operand:DI 2 "symbolic_operand" "")]
5470                             UNSPEC_UMK_LAL)))]
5471   "TARGET_ABI_UNICOSMK"
5472   "lal %r0,%t2(%r1)"
5473   [(set_attr "type" "iadd")])
5474
5475 ;; Add a new call information word to the current function's list of CIWs
5476 ;; and load its index into $25. Doing it here ensures that the CIW will be
5477 ;; associated with the correct function even in the presence of inlining.
5478
5479 (define_insn "*umk_load_ciw"
5480   [(set (reg:DI 25)
5481         (unspec:DI [(match_operand 0 "" "")] UNSPEC_UMK_LOAD_CIW))]
5482   "TARGET_ABI_UNICOSMK"
5483 {
5484   operands[0] = unicosmk_add_call_info_word (operands[0]);
5485   return "lda $25,%0";
5486 }
5487   [(set_attr "type" "iadd")])
5488
5489 (define_insn "*movdi_er_low_l"
5490   [(set (match_operand:DI 0 "register_operand" "=r")
5491         (lo_sum:DI (match_operand:DI 1 "register_operand" "r")
5492                    (match_operand:DI 2 "local_symbolic_operand" "")))]
5493   "TARGET_EXPLICIT_RELOCS"
5494 {
5495   if (true_regnum (operands[1]) == 29)
5496     return "lda %0,%2(%1)\t\t!gprel";
5497   else
5498     return "lda %0,%2(%1)\t\t!gprellow";
5499 })
5500
5501 (define_split
5502   [(set (match_operand:DI 0 "register_operand" "")
5503         (match_operand:DI 1 "small_symbolic_operand" ""))]
5504   "TARGET_EXPLICIT_RELOCS && reload_completed"
5505   [(set (match_dup 0)
5506         (lo_sum:DI (match_dup 2) (match_dup 1)))]
5507   "operands[2] = pic_offset_table_rtx;")
5508
5509 (define_split
5510   [(set (match_operand:DI 0 "register_operand" "")
5511         (match_operand:DI 1 "local_symbolic_operand" ""))]
5512   "TARGET_EXPLICIT_RELOCS && reload_completed"
5513   [(set (match_dup 0)
5514         (plus:DI (match_dup 2) (high:DI (match_dup 1))))
5515    (set (match_dup 0)
5516         (lo_sum:DI (match_dup 0) (match_dup 1)))]
5517   "operands[2] = pic_offset_table_rtx;")
5518
5519 (define_split
5520   [(match_operand 0 "some_small_symbolic_operand" "")]
5521   "TARGET_EXPLICIT_RELOCS && reload_completed"
5522   [(match_dup 0)]
5523   "operands[0] = split_small_symbolic_operand (operands[0]);")
5524
5525 (define_insn "movdi_er_high_g"
5526   [(set (match_operand:DI 0 "register_operand" "=r")
5527         (unspec:DI [(match_operand:DI 1 "register_operand" "r")
5528                     (match_operand:DI 2 "global_symbolic_operand" "")
5529                     (match_operand 3 "const_int_operand" "")]
5530                    UNSPEC_LITERAL))]
5531   "TARGET_EXPLICIT_RELOCS"
5532 {
5533   if (INTVAL (operands[3]) == 0)
5534     return "ldq %0,%2(%1)\t\t!literal";
5535   else
5536     return "ldq %0,%2(%1)\t\t!literal!%3";
5537 }
5538   [(set_attr "type" "ldsym")])
5539
5540 (define_split
5541   [(set (match_operand:DI 0 "register_operand" "")
5542         (match_operand:DI 1 "global_symbolic_operand" ""))]
5543   "TARGET_EXPLICIT_RELOCS && reload_completed"
5544   [(set (match_dup 0)
5545         (unspec:DI [(match_dup 2)
5546                     (match_dup 1)
5547                     (const_int 0)] UNSPEC_LITERAL))]
5548   "operands[2] = pic_offset_table_rtx;")
5549
5550 (define_insn "*movdi_er_nofix"
5551   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,r,r,r,r,m,*f,*f,Q")
5552         (match_operand:DI 1 "input_operand" "rJ,K,L,T,s,m,rJ,*fJ,Q,*f"))]
5553   "TARGET_EXPLICIT_RELOCS && ! TARGET_FIX
5554    && (register_operand (operands[0], DImode)
5555        || reg_or_0_operand (operands[1], DImode))"
5556   "@
5557    mov %r1,%0
5558    lda %0,%1($31)
5559    ldah %0,%h1($31)
5560    #
5561    #
5562    ldq%A1 %0,%1
5563    stq%A0 %r1,%0
5564    fmov %R1,%0
5565    ldt %0,%1
5566    stt %R1,%0"
5567   [(set_attr "type" "ilog,iadd,iadd,iadd,ldsym,ild,ist,fcpys,fld,fst")])
5568
5569 ;; The 'U' constraint matches symbolic operands on Unicos/Mk. Those should
5570 ;; have been split up by the rules above but we shouldn't reject the
5571 ;; possibility of them getting through.
5572
5573 (define_insn "*movdi_nofix"
5574   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,r,r,r,r,m,*f,*f,Q")
5575         (match_operand:DI 1 "input_operand" "rJ,K,L,U,s,m,rJ,*fJ,Q,*f"))]
5576   "! TARGET_FIX
5577    && (register_operand (operands[0], DImode)
5578        || reg_or_0_operand (operands[1], DImode))"
5579   "@
5580    bis $31,%r1,%0
5581    lda %0,%1($31)
5582    ldah %0,%h1($31)
5583    laum %0,%t1($31)\;sll %0,32,%0\;lalm %0,%t1(%0)\;lal %0,%t1(%0)
5584    lda %0,%1
5585    ldq%A1 %0,%1
5586    stq%A0 %r1,%0
5587    cpys %R1,%R1,%0
5588    ldt %0,%1
5589    stt %R1,%0"
5590   [(set_attr "type" "ilog,iadd,iadd,ldsym,ldsym,ild,ist,fcpys,fld,fst")
5591    (set_attr "length" "*,*,*,16,*,*,*,*,*,*")])
5592
5593 (define_insn "*movdi_er_fix"
5594   [(set (match_operand:DI 0 "nonimmediate_operand"
5595                                 "=r,r,r,r,r,r, m, *f,*f, Q, r,*f")
5596         (match_operand:DI 1 "input_operand"
5597                                 "rJ,K,L,T,s,m,rJ,*fJ, Q,*f,*f, r"))]
5598   "TARGET_EXPLICIT_RELOCS && TARGET_FIX
5599    && (register_operand (operands[0], DImode)
5600        || reg_or_0_operand (operands[1], DImode))"
5601   "@
5602    mov %r1,%0
5603    lda %0,%1($31)
5604    ldah %0,%h1($31)
5605    #
5606    #
5607    ldq%A1 %0,%1
5608    stq%A0 %r1,%0
5609    fmov %R1,%0
5610    ldt %0,%1
5611    stt %R1,%0
5612    ftoit %1,%0
5613    itoft %1,%0"
5614   [(set_attr "type" "ilog,iadd,iadd,iadd,ldsym,ild,ist,fcpys,fld,fst,ftoi,itof")])
5615
5616 (define_insn "*movdi_fix"
5617   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,r,r,r,m,*f,*f,Q,r,*f")
5618         (match_operand:DI 1 "input_operand" "rJ,K,L,s,m,rJ,*fJ,Q,*f,*f,r"))]
5619   "! TARGET_EXPLICIT_RELOCS && TARGET_FIX
5620    && (register_operand (operands[0], DImode)
5621        || reg_or_0_operand (operands[1], DImode))"
5622   "@
5623    bis $31,%r1,%0
5624    lda %0,%1($31)
5625    ldah %0,%h1($31)
5626    lda %0,%1
5627    ldq%A1 %0,%1
5628    stq%A0 %r1,%0
5629    cpys %R1,%R1,%0
5630    ldt %0,%1
5631    stt %R1,%0
5632    ftoit %1,%0
5633    itoft %1,%0"
5634   [(set_attr "type" "ilog,iadd,iadd,ldsym,ild,ist,fcpys,fld,fst,ftoi,itof")])
5635
5636 ;; VMS needs to set up "vms_base_regno" for unwinding.  This move
5637 ;; often appears dead to the life analysis code, at which point we
5638 ;; abort for emitting dead prologue instructions.  Force this live.
5639
5640 (define_insn "force_movdi"
5641   [(set (match_operand:DI 0 "register_operand" "=r")
5642         (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "r")]
5643                             UNSPECV_FORCE_MOV))]
5644   ""
5645   "mov %1,%0"
5646   [(set_attr "type" "ilog")])
5647
5648 ;; We do three major things here: handle mem->mem, put 64-bit constants in
5649 ;; memory, and construct long 32-bit constants.
5650
5651 (define_expand "movdi"
5652   [(set (match_operand:DI 0 "nonimmediate_operand" "")
5653         (match_operand:DI 1 "general_operand" ""))]
5654   ""
5655 {
5656   if (alpha_expand_mov (DImode, operands))
5657     DONE;
5658 })
5659
5660 ;; Split a load of a large constant into the appropriate two-insn
5661 ;; sequence.
5662
5663 (define_split
5664   [(set (match_operand:DI 0 "register_operand" "")
5665         (match_operand:DI 1 "const_int_operand" ""))]
5666   "! add_operand (operands[1], DImode)"
5667   [(set (match_dup 0) (match_dup 2))
5668    (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 3)))]
5669 {
5670   rtx tem
5671     = alpha_emit_set_const (operands[0], DImode, INTVAL (operands[1]), 2);
5672
5673   if (tem == operands[0])
5674     DONE;
5675   else
5676     FAIL;
5677 })
5678
5679 ;; These are the partial-word cases.
5680 ;;
5681 ;; First we have the code to load an aligned word.  Operand 0 is the register
5682 ;; in which to place the result.  It's mode is QImode or HImode.  Operand 1
5683 ;; is an SImode MEM at the low-order byte of the proper word.  Operand 2 is the
5684 ;; number of bits within the word that the value is.  Operand 3 is an SImode
5685 ;; scratch register.  If operand 0 is a hard register, operand 3 may be the
5686 ;; same register.  It is allowed to conflict with operand 1 as well.
5687
5688 (define_expand "aligned_loadqi"
5689   [(set (match_operand:SI 3 "register_operand" "")
5690         (match_operand:SI 1 "memory_operand" ""))
5691    (set (subreg:DI (match_operand:QI 0 "register_operand" "") 0)
5692         (zero_extract:DI (subreg:DI (match_dup 3) 0)
5693                          (const_int 8)
5694                          (match_operand:DI 2 "const_int_operand" "")))]
5695
5696   ""
5697   "")
5698
5699 (define_expand "aligned_loadhi"
5700   [(set (match_operand:SI 3 "register_operand" "")
5701         (match_operand:SI 1 "memory_operand" ""))
5702    (set (subreg:DI (match_operand:HI 0 "register_operand" "") 0)
5703         (zero_extract:DI (subreg:DI (match_dup 3) 0)
5704                          (const_int 16)
5705                          (match_operand:DI 2 "const_int_operand" "")))]
5706
5707   ""
5708   "")
5709
5710 ;; Similar for unaligned loads, where we use the sequence from the
5711 ;; Alpha Architecture manual. We have to distinguish between little-endian
5712 ;; and big-endian systems as the sequences are different.
5713 ;;
5714 ;; Operand 1 is the address.  Operands 2 and 3 are temporaries, where
5715 ;; operand 3 can overlap the input and output registers.
5716
5717 (define_expand "unaligned_loadqi"
5718   [(use (match_operand:QI 0 "register_operand" ""))
5719    (use (match_operand:DI 1 "address_operand" ""))
5720    (use (match_operand:DI 2 "register_operand" ""))
5721    (use (match_operand:DI 3 "register_operand" ""))]
5722   ""
5723 {
5724   if (WORDS_BIG_ENDIAN)
5725     emit_insn (gen_unaligned_loadqi_be (operands[0], operands[1],
5726                                         operands[2], operands[3]));
5727   else
5728     emit_insn (gen_unaligned_loadqi_le (operands[0], operands[1],
5729                                         operands[2], operands[3]));
5730   DONE;
5731 })
5732
5733 (define_expand "unaligned_loadqi_le"
5734   [(set (match_operand:DI 2 "register_operand" "")
5735         (mem:DI (and:DI (match_operand:DI 1 "address_operand" "")
5736                         (const_int -8))))
5737    (set (match_operand:DI 3 "register_operand" "")
5738         (match_dup 1))
5739    (set (subreg:DI (match_operand:QI 0 "register_operand" "") 0)
5740         (zero_extract:DI (match_dup 2)
5741                          (const_int 8)
5742                          (ashift:DI (match_dup 3) (const_int 3))))]
5743   "! WORDS_BIG_ENDIAN"
5744   "")
5745
5746 (define_expand "unaligned_loadqi_be"
5747   [(set (match_operand:DI 2 "register_operand" "")
5748         (mem:DI (and:DI (match_operand:DI 1 "address_operand" "")
5749                         (const_int -8))))
5750    (set (match_operand:DI 3 "register_operand" "")
5751         (match_dup 1))
5752    (set (subreg:DI (match_operand:QI 0 "register_operand" "") 0)
5753         (zero_extract:DI (match_dup 2)
5754                          (const_int 8)
5755                          (minus:DI
5756                            (const_int 56)
5757                            (ashift:DI (match_dup 3) (const_int 3)))))]
5758   "WORDS_BIG_ENDIAN"
5759   "")
5760
5761 (define_expand "unaligned_loadhi"
5762   [(use (match_operand:QI 0 "register_operand" ""))
5763    (use (match_operand:DI 1 "address_operand" ""))
5764    (use (match_operand:DI 2 "register_operand" ""))
5765    (use (match_operand:DI 3 "register_operand" ""))]
5766   ""
5767 {
5768   if (WORDS_BIG_ENDIAN)
5769     emit_insn (gen_unaligned_loadhi_be (operands[0], operands[1],
5770                                         operands[2], operands[3]));
5771   else
5772     emit_insn (gen_unaligned_loadhi_le (operands[0], operands[1],
5773                                         operands[2], operands[3]));
5774   DONE;
5775 })
5776
5777 (define_expand "unaligned_loadhi_le"
5778   [(set (match_operand:DI 2 "register_operand" "")
5779         (mem:DI (and:DI (match_operand:DI 1 "address_operand" "")
5780                         (const_int -8))))
5781    (set (match_operand:DI 3 "register_operand" "")
5782         (match_dup 1))
5783    (set (subreg:DI (match_operand:QI 0 "register_operand" "") 0)
5784         (zero_extract:DI (match_dup 2)
5785                          (const_int 16)
5786                          (ashift:DI (match_dup 3) (const_int 3))))]
5787   "! WORDS_BIG_ENDIAN"
5788   "")
5789
5790 (define_expand "unaligned_loadhi_be"
5791   [(set (match_operand:DI 2 "register_operand" "")
5792         (mem:DI (and:DI (match_operand:DI 1 "address_operand" "")
5793                         (const_int -8))))
5794    (set (match_operand:DI 3 "register_operand" "")
5795         (plus:DI (match_dup 1) (const_int 1)))
5796    (set (subreg:DI (match_operand:QI 0 "register_operand" "") 0)
5797         (zero_extract:DI (match_dup 2)
5798                          (const_int 16)
5799                          (minus:DI
5800                            (const_int 56)
5801                            (ashift:DI (match_dup 3) (const_int 3)))))]
5802   "WORDS_BIG_ENDIAN"
5803   "")
5804
5805 ;; Storing an aligned byte or word requires two temporaries.  Operand 0 is the
5806 ;; aligned SImode MEM.  Operand 1 is the register containing the
5807 ;; byte or word to store.  Operand 2 is the number of bits within the word that
5808 ;; the value should be placed.  Operands 3 and 4 are SImode temporaries.
5809
5810 (define_expand "aligned_store"
5811   [(set (match_operand:SI 3 "register_operand" "")
5812         (match_operand:SI 0 "memory_operand" ""))
5813    (set (subreg:DI (match_dup 3) 0)
5814         (and:DI (subreg:DI (match_dup 3) 0) (match_dup 5)))
5815    (set (subreg:DI (match_operand:SI 4 "register_operand" "") 0)
5816         (ashift:DI (zero_extend:DI (match_operand 1 "register_operand" ""))
5817                    (match_operand:DI 2 "const_int_operand" "")))
5818    (set (subreg:DI (match_dup 4) 0)
5819         (ior:DI (subreg:DI (match_dup 4) 0) (subreg:DI (match_dup 3) 0)))
5820    (set (match_dup 0) (match_dup 4))]
5821   ""
5822 {
5823   operands[5] = GEN_INT (~ (GET_MODE_MASK (GET_MODE (operands[1]))
5824                             << INTVAL (operands[2])));
5825 })
5826
5827 ;; For the unaligned byte and halfword cases, we use code similar to that
5828 ;; in the ;; Architecture book, but reordered to lower the number of registers
5829 ;; required.  Operand 0 is the address.  Operand 1 is the data to store.
5830 ;; Operands 2, 3, and 4 are DImode temporaries, where operands 2 and 4 may
5831 ;; be the same temporary, if desired.  If the address is in a register,
5832 ;; operand 2 can be that register.
5833
5834 (define_expand "unaligned_storeqi"
5835   [(use (match_operand:DI 0 "address_operand" ""))
5836    (use (match_operand:QI 1 "register_operand" ""))
5837    (use (match_operand:DI 2 "register_operand" ""))
5838    (use (match_operand:DI 3 "register_operand" ""))
5839    (use (match_operand:DI 4 "register_operand" ""))]
5840   ""
5841 {
5842   if (WORDS_BIG_ENDIAN)
5843     emit_insn (gen_unaligned_storeqi_be (operands[0], operands[1],
5844                                          operands[2], operands[3],
5845                                          operands[4]));
5846   else
5847     emit_insn (gen_unaligned_storeqi_le (operands[0], operands[1],
5848                                          operands[2], operands[3],
5849                                          operands[4]));
5850   DONE;
5851 })
5852
5853 (define_expand "unaligned_storeqi_le"
5854   [(set (match_operand:DI 3 "register_operand" "")
5855         (mem:DI (and:DI (match_operand:DI 0 "address_operand" "")
5856                         (const_int -8))))
5857    (set (match_operand:DI 2 "register_operand" "")
5858         (match_dup 0))
5859    (set (match_dup 3)
5860         (and:DI (not:DI (ashift:DI (const_int 255)
5861                                    (ashift:DI (match_dup 2) (const_int 3))))
5862                 (match_dup 3)))
5863    (set (match_operand:DI 4 "register_operand" "")
5864         (ashift:DI (zero_extend:DI (match_operand:QI 1 "register_operand" ""))
5865                    (ashift:DI (match_dup 2) (const_int 3))))
5866    (set (match_dup 4) (ior:DI (match_dup 4) (match_dup 3)))
5867    (set (mem:DI (and:DI (match_dup 0) (const_int -8)))
5868         (match_dup 4))]
5869   "! WORDS_BIG_ENDIAN"
5870   "")
5871
5872 (define_expand "unaligned_storeqi_be"
5873   [(set (match_operand:DI 3 "register_operand" "")
5874         (mem:DI (and:DI (match_operand:DI 0 "address_operand" "")
5875                         (const_int -8))))
5876    (set (match_operand:DI 2 "register_operand" "")
5877         (match_dup 0))
5878    (set (match_dup 3)
5879         (and:DI (not:DI (ashift:DI (const_int 255)
5880                           (minus:DI (const_int 56)
5881                                     (ashift:DI (match_dup 2) (const_int 3)))))
5882                 (match_dup 3)))
5883    (set (match_operand:DI 4 "register_operand" "")
5884         (ashift:DI (zero_extend:DI (match_operand:QI 1 "register_operand" ""))
5885                    (minus:DI (const_int 56)
5886                      (ashift:DI (match_dup 2) (const_int 3)))))
5887    (set (match_dup 4) (ior:DI (match_dup 4) (match_dup 3)))
5888    (set (mem:DI (and:DI (match_dup 0) (const_int -8)))
5889         (match_dup 4))]
5890   "WORDS_BIG_ENDIAN"
5891   "")
5892
5893 (define_expand "unaligned_storehi"
5894   [(use (match_operand:DI 0 "address_operand" ""))
5895    (use (match_operand:HI 1 "register_operand" ""))
5896    (use (match_operand:DI 2 "register_operand" ""))
5897    (use (match_operand:DI 3 "register_operand" ""))
5898    (use (match_operand:DI 4 "register_operand" ""))]
5899   ""
5900 {
5901   if (WORDS_BIG_ENDIAN)
5902     emit_insn (gen_unaligned_storehi_be (operands[0], operands[1],
5903                                          operands[2], operands[3],
5904                                          operands[4]));
5905   else
5906     emit_insn (gen_unaligned_storehi_le (operands[0], operands[1],
5907                                          operands[2], operands[3],
5908                                          operands[4]));
5909   DONE;
5910 })
5911
5912 (define_expand "unaligned_storehi_le"
5913   [(set (match_operand:DI 3 "register_operand" "")
5914         (mem:DI (and:DI (match_operand:DI 0 "address_operand" "")
5915                         (const_int -8))))
5916    (set (match_operand:DI 2 "register_operand" "")
5917         (match_dup 0))
5918    (set (match_dup 3)
5919         (and:DI (not:DI (ashift:DI (const_int 65535)
5920                                    (ashift:DI (match_dup 2) (const_int 3))))
5921                 (match_dup 3)))
5922    (set (match_operand:DI 4 "register_operand" "")
5923         (ashift:DI (zero_extend:DI (match_operand:HI 1 "register_operand" ""))
5924                    (ashift:DI (match_dup 2) (const_int 3))))
5925    (set (match_dup 4) (ior:DI (match_dup 4) (match_dup 3)))
5926    (set (mem:DI (and:DI (match_dup 0) (const_int -8)))
5927         (match_dup 4))]
5928   "! WORDS_BIG_ENDIAN"
5929   "")
5930
5931 (define_expand "unaligned_storehi_be"
5932   [(set (match_operand:DI 3 "register_operand" "")
5933         (mem:DI (and:DI (match_operand:DI 0 "address_operand" "")
5934                         (const_int -8))))
5935    (set (match_operand:DI 2 "register_operand" "")
5936         (plus:DI (match_dup 0) (const_int 1)))
5937    (set (match_dup 3)
5938         (and:DI (not:DI (ashift:DI
5939                           (const_int 65535)
5940                           (minus:DI (const_int 56)
5941                                     (ashift:DI (match_dup 2) (const_int 3)))))
5942                 (match_dup 3)))
5943    (set (match_operand:DI 4 "register_operand" "")
5944         (ashift:DI (zero_extend:DI (match_operand:HI 1 "register_operand" ""))
5945                    (minus:DI (const_int 56)
5946                              (ashift:DI (match_dup 2) (const_int 3)))))
5947    (set (match_dup 4) (ior:DI (match_dup 4) (match_dup 3)))
5948    (set (mem:DI (and:DI (match_dup 0) (const_int -8)))
5949         (match_dup 4))]
5950   "WORDS_BIG_ENDIAN"
5951   "")
5952 \f
5953 ;; Here are the define_expand's for QI and HI moves that use the above
5954 ;; patterns.  We have the normal sets, plus the ones that need scratch
5955 ;; registers for reload.
5956
5957 (define_expand "movqi"
5958   [(set (match_operand:QI 0 "nonimmediate_operand" "")
5959         (match_operand:QI 1 "general_operand" ""))]
5960   ""
5961 {
5962   if (TARGET_BWX
5963       ? alpha_expand_mov (QImode, operands)
5964       : alpha_expand_mov_nobwx (QImode, operands))
5965     DONE;
5966 })
5967
5968 (define_expand "movhi"
5969   [(set (match_operand:HI 0 "nonimmediate_operand" "")
5970         (match_operand:HI 1 "general_operand" ""))]
5971   ""
5972 {
5973   if (TARGET_BWX
5974       ? alpha_expand_mov (HImode, operands)
5975       : alpha_expand_mov_nobwx (HImode, operands))
5976     DONE;
5977 })
5978
5979 ;; Here are the versions for reload.  Note that in the unaligned cases
5980 ;; we know that the operand must not be a pseudo-register because stack
5981 ;; slots are always aligned references.
5982
5983 (define_expand "reload_inqi"
5984   [(parallel [(match_operand:QI 0 "register_operand" "=r")
5985               (match_operand:QI 1 "any_memory_operand" "m")
5986               (match_operand:TI 2 "register_operand" "=&r")])]
5987   "! TARGET_BWX"
5988 {
5989   rtx scratch, seq;
5990
5991   if (GET_CODE (operands[1]) != MEM)
5992     abort ();
5993
5994   if (aligned_memory_operand (operands[1], QImode))
5995     {
5996       seq = gen_reload_inqi_help (operands[0], operands[1],
5997                                   gen_rtx_REG (SImode, REGNO (operands[2])));
5998     }
5999   else
6000     {
6001       rtx addr;
6002
6003       /* It is possible that one of the registers we got for operands[2]
6004          might coincide with that of operands[0] (which is why we made
6005          it TImode).  Pick the other one to use as our scratch.  */
6006       if (REGNO (operands[0]) == REGNO (operands[2]))
6007         scratch = gen_rtx_REG (DImode, REGNO (operands[2]) + 1);
6008       else
6009         scratch = gen_rtx_REG (DImode, REGNO (operands[2]));
6010
6011       addr = get_unaligned_address (operands[1], 0);
6012       seq = gen_unaligned_loadqi (operands[0], addr, scratch,
6013                           gen_rtx_REG (DImode, REGNO (operands[0])));
6014       alpha_set_memflags (seq, operands[1]);
6015     }
6016   emit_insn (seq);
6017   DONE;
6018 })
6019
6020 (define_expand "reload_inhi"
6021   [(parallel [(match_operand:HI 0 "register_operand" "=r")
6022               (match_operand:HI 1 "any_memory_operand" "m")
6023               (match_operand:TI 2 "register_operand" "=&r")])]
6024   "! TARGET_BWX"
6025 {
6026   rtx scratch, seq;
6027
6028   if (GET_CODE (operands[1]) != MEM)
6029     abort ();
6030
6031   if (aligned_memory_operand (operands[1], HImode))
6032     {
6033       seq = gen_reload_inhi_help (operands[0], operands[1],
6034                                   gen_rtx_REG (SImode, REGNO (operands[2])));
6035     }
6036   else
6037     {
6038       rtx addr;
6039
6040       /* It is possible that one of the registers we got for operands[2]
6041          might coincide with that of operands[0] (which is why we made
6042          it TImode).  Pick the other one to use as our scratch.  */
6043       if (REGNO (operands[0]) == REGNO (operands[2]))
6044         scratch = gen_rtx_REG (DImode, REGNO (operands[2]) + 1);
6045       else
6046         scratch = gen_rtx_REG (DImode, REGNO (operands[2]));
6047
6048       addr = get_unaligned_address (operands[1], 0);
6049       seq = gen_unaligned_loadhi (operands[0], addr, scratch,
6050                           gen_rtx_REG (DImode, REGNO (operands[0])));
6051       alpha_set_memflags (seq, operands[1]);
6052     }
6053   emit_insn (seq);
6054   DONE;
6055 })
6056
6057 (define_expand "reload_outqi"
6058   [(parallel [(match_operand:QI 0 "any_memory_operand" "=m")
6059               (match_operand:QI 1 "register_operand" "r")
6060               (match_operand:TI 2 "register_operand" "=&r")])]
6061   "! TARGET_BWX"
6062 {
6063   if (GET_CODE (operands[0]) != MEM)
6064     abort ();
6065
6066   if (aligned_memory_operand (operands[0], QImode))
6067     {
6068       emit_insn (gen_reload_outqi_help
6069                  (operands[0], operands[1],
6070                   gen_rtx_REG (SImode, REGNO (operands[2])),
6071                   gen_rtx_REG (SImode, REGNO (operands[2]) + 1)));
6072     }
6073   else
6074     {
6075       rtx addr = get_unaligned_address (operands[0], 0);
6076       rtx scratch1 = gen_rtx_REG (DImode, REGNO (operands[2]));
6077       rtx scratch2 = gen_rtx_REG (DImode, REGNO (operands[2]) + 1);
6078       rtx scratch3 = scratch1;
6079       rtx seq;
6080
6081       if (GET_CODE (addr) == REG)
6082         scratch1 = addr;
6083
6084       seq = gen_unaligned_storeqi (addr, operands[1], scratch1,
6085                                    scratch2, scratch3);
6086       alpha_set_memflags (seq, operands[0]);
6087       emit_insn (seq);
6088     }
6089   DONE;
6090 })
6091
6092 (define_expand "reload_outhi"
6093   [(parallel [(match_operand:HI 0 "any_memory_operand" "=m")
6094               (match_operand:HI 1 "register_operand" "r")
6095               (match_operand:TI 2 "register_operand" "=&r")])]
6096   "! TARGET_BWX"
6097 {
6098   if (GET_CODE (operands[0]) != MEM)
6099     abort ();
6100
6101   if (aligned_memory_operand (operands[0], HImode))
6102     {
6103       emit_insn (gen_reload_outhi_help
6104                  (operands[0], operands[1],
6105                   gen_rtx_REG (SImode, REGNO (operands[2])),
6106                   gen_rtx_REG (SImode, REGNO (operands[2]) + 1)));
6107     }
6108   else
6109     {
6110       rtx addr = get_unaligned_address (operands[0], 0);
6111       rtx scratch1 = gen_rtx_REG (DImode, REGNO (operands[2]));
6112       rtx scratch2 = gen_rtx_REG (DImode, REGNO (operands[2]) + 1);
6113       rtx scratch3 = scratch1;
6114       rtx seq;
6115
6116       if (GET_CODE (addr) == REG)
6117         scratch1 = addr;
6118
6119       seq = gen_unaligned_storehi (addr, operands[1], scratch1,
6120                                    scratch2, scratch3);
6121       alpha_set_memflags (seq, operands[0]);
6122       emit_insn (seq);
6123     }
6124   DONE;
6125 })
6126
6127 ;; Helpers for the above.  The way reload is structured, we can't
6128 ;; always get a proper address for a stack slot during reload_foo
6129 ;; expansion, so we must delay our address manipulations until after.
6130
6131 (define_insn "reload_inqi_help"
6132   [(set (match_operand:QI 0 "register_operand" "=r")
6133         (match_operand:QI 1 "memory_operand" "m"))
6134    (clobber (match_operand:SI 2 "register_operand" "=r"))]
6135   "! TARGET_BWX && (reload_in_progress || reload_completed)"
6136   "#")
6137
6138 (define_insn "reload_inhi_help"
6139   [(set (match_operand:HI 0 "register_operand" "=r")
6140         (match_operand:HI 1 "memory_operand" "m"))
6141    (clobber (match_operand:SI 2 "register_operand" "=r"))]
6142   "! TARGET_BWX && (reload_in_progress || reload_completed)"
6143   "#")
6144
6145 (define_insn "reload_outqi_help"
6146   [(set (match_operand:QI 0 "memory_operand" "=m")
6147         (match_operand:QI 1 "register_operand" "r"))
6148    (clobber (match_operand:SI 2 "register_operand" "=r"))
6149    (clobber (match_operand:SI 3 "register_operand" "=r"))]
6150   "! TARGET_BWX && (reload_in_progress || reload_completed)"
6151   "#")
6152
6153 (define_insn "reload_outhi_help"
6154   [(set (match_operand:HI 0 "memory_operand" "=m")
6155         (match_operand:HI 1 "register_operand" "r"))
6156    (clobber (match_operand:SI 2 "register_operand" "=r"))
6157    (clobber (match_operand:SI 3 "register_operand" "=r"))]
6158   "! TARGET_BWX && (reload_in_progress || reload_completed)"
6159   "#")
6160
6161 (define_split
6162   [(set (match_operand:QI 0 "register_operand" "")
6163         (match_operand:QI 1 "memory_operand" ""))
6164    (clobber (match_operand:SI 2 "register_operand" ""))]
6165   "! TARGET_BWX && reload_completed"
6166   [(const_int 0)]
6167 {
6168   rtx aligned_mem, bitnum;
6169   get_aligned_mem (operands[1], &aligned_mem, &bitnum);
6170
6171   emit_insn (gen_aligned_loadqi (operands[0], aligned_mem, bitnum,
6172                                  operands[2]));
6173   DONE;
6174 })
6175
6176 (define_split
6177   [(set (match_operand:HI 0 "register_operand" "")
6178         (match_operand:HI 1 "memory_operand" ""))
6179    (clobber (match_operand:SI 2 "register_operand" ""))]
6180   "! TARGET_BWX && reload_completed"
6181   [(const_int 0)]
6182 {
6183   rtx aligned_mem, bitnum;
6184   get_aligned_mem (operands[1], &aligned_mem, &bitnum);
6185
6186   emit_insn (gen_aligned_loadhi (operands[0], aligned_mem, bitnum,
6187                                  operands[2]));
6188   DONE;
6189 })
6190
6191 (define_split
6192   [(set (match_operand:QI 0 "memory_operand" "")
6193         (match_operand:QI 1 "register_operand" ""))
6194    (clobber (match_operand:SI 2 "register_operand" ""))
6195    (clobber (match_operand:SI 3 "register_operand" ""))]
6196   "! TARGET_BWX && reload_completed"
6197   [(const_int 0)]
6198 {
6199   rtx aligned_mem, bitnum;
6200   get_aligned_mem (operands[0], &aligned_mem, &bitnum);
6201   emit_insn (gen_aligned_store (aligned_mem, operands[1], bitnum,
6202                                 operands[2], operands[3]));
6203   DONE;
6204 })
6205
6206 (define_split
6207   [(set (match_operand:HI 0 "memory_operand" "")
6208         (match_operand:HI 1 "register_operand" ""))
6209    (clobber (match_operand:SI 2 "register_operand" ""))
6210    (clobber (match_operand:SI 3 "register_operand" ""))]
6211   "! TARGET_BWX && reload_completed"
6212   [(const_int 0)]
6213 {
6214   rtx aligned_mem, bitnum;
6215   get_aligned_mem (operands[0], &aligned_mem, &bitnum);
6216   emit_insn (gen_aligned_store (aligned_mem, operands[1], bitnum,
6217                                 operands[2], operands[3]));
6218   DONE;
6219 })
6220 \f
6221 ;; Bit field extract patterns which use ext[wlq][lh]
6222
6223 (define_expand "extv"
6224   [(set (match_operand:DI 0 "register_operand" "")
6225         (sign_extract:DI (match_operand:QI 1 "memory_operand" "")
6226                          (match_operand:DI 2 "immediate_operand" "")
6227                          (match_operand:DI 3 "immediate_operand" "")))]
6228   ""
6229 {
6230   int ofs;
6231
6232   /* We can do 16, 32 and 64 bit fields, if aligned on byte boundaries.  */
6233   if (INTVAL (operands[3]) % 8 != 0
6234       || (INTVAL (operands[2]) != 16
6235           && INTVAL (operands[2]) != 32
6236           && INTVAL (operands[2]) != 64))
6237     FAIL;
6238
6239   /* From mips.md: extract_bit_field doesn't verify that our source
6240      matches the predicate, so we force it to be a MEM here.  */
6241   if (GET_CODE (operands[1]) != MEM)
6242     FAIL;
6243
6244   /* The bit number is relative to the mode of operand 1 which is
6245      usually QImode (this might actually be a bug in expmed.c). Note 
6246      that the bit number is negative in big-endian mode in this case.
6247      We have to convert that to the offset.  */
6248   if (WORDS_BIG_ENDIAN)
6249     ofs = GET_MODE_BITSIZE (GET_MODE (operands[1]))
6250           - INTVAL (operands[2]) - INTVAL (operands[3]);
6251   else
6252     ofs = INTVAL (operands[3]);
6253
6254   ofs = ofs / 8;
6255
6256   alpha_expand_unaligned_load (operands[0], operands[1],
6257                                INTVAL (operands[2]) / 8,
6258                                ofs, 1);
6259   DONE;
6260 })
6261
6262 (define_expand "extzv"
6263   [(set (match_operand:DI 0 "register_operand" "")
6264         (zero_extract:DI (match_operand:DI 1 "nonimmediate_operand" "")
6265                          (match_operand:DI 2 "immediate_operand" "")
6266                          (match_operand:DI 3 "immediate_operand" "")))]
6267   ""
6268 {
6269   /* We can do 8, 16, 32 and 64 bit fields, if aligned on byte boundaries.  */
6270   if (INTVAL (operands[3]) % 8 != 0
6271       || (INTVAL (operands[2]) != 8
6272           && INTVAL (operands[2]) != 16
6273           && INTVAL (operands[2]) != 32
6274           && INTVAL (operands[2]) != 64))
6275     FAIL;
6276
6277   if (GET_CODE (operands[1]) == MEM)
6278     {
6279       int ofs;
6280
6281       /* Fail 8 bit fields, falling back on a simple byte load.  */
6282       if (INTVAL (operands[2]) == 8)
6283         FAIL;
6284
6285       /* The bit number is relative to the mode of operand 1 which is
6286          usually QImode (this might actually be a bug in expmed.c). Note 
6287          that the bit number is negative in big-endian mode in this case.
6288          We have to convert that to the offset.  */
6289       if (WORDS_BIG_ENDIAN)
6290         ofs = GET_MODE_BITSIZE (GET_MODE (operands[1]))
6291               - INTVAL (operands[2]) - INTVAL (operands[3]);
6292       else
6293         ofs = INTVAL (operands[3]);
6294
6295       ofs = ofs / 8;
6296
6297       alpha_expand_unaligned_load (operands[0], operands[1],
6298                                    INTVAL (operands[2]) / 8,
6299                                    ofs, 0);
6300       DONE;
6301     }
6302 })
6303
6304 (define_expand "insv"
6305   [(set (zero_extract:DI (match_operand:QI 0 "memory_operand" "")
6306                          (match_operand:DI 1 "immediate_operand" "")
6307                          (match_operand:DI 2 "immediate_operand" ""))
6308         (match_operand:DI 3 "register_operand" ""))]
6309   ""
6310 {
6311   int ofs;
6312
6313   /* We can do 16, 32 and 64 bit fields, if aligned on byte boundaries.  */
6314   if (INTVAL (operands[2]) % 8 != 0
6315       || (INTVAL (operands[1]) != 16
6316           && INTVAL (operands[1]) != 32
6317           && INTVAL (operands[1]) != 64))
6318     FAIL;
6319
6320   /* From mips.md: store_bit_field doesn't verify that our source
6321      matches the predicate, so we force it to be a MEM here.  */
6322   if (GET_CODE (operands[0]) != MEM)
6323     FAIL;
6324
6325   /* The bit number is relative to the mode of operand 1 which is
6326      usually QImode (this might actually be a bug in expmed.c). Note 
6327      that the bit number is negative in big-endian mode in this case.
6328      We have to convert that to the offset.  */
6329   if (WORDS_BIG_ENDIAN)
6330     ofs = GET_MODE_BITSIZE (GET_MODE (operands[0]))
6331           - INTVAL (operands[1]) - INTVAL (operands[2]);
6332   else
6333     ofs = INTVAL (operands[2]);
6334
6335   ofs = ofs / 8;
6336
6337   alpha_expand_unaligned_store (operands[0], operands[3],
6338                                 INTVAL (operands[1]) / 8, ofs);
6339   DONE;
6340 })
6341
6342 ;; Block move/clear, see alpha.c for more details.
6343 ;; Argument 0 is the destination
6344 ;; Argument 1 is the source
6345 ;; Argument 2 is the length
6346 ;; Argument 3 is the alignment
6347
6348 (define_expand "movstrqi"
6349   [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
6350                    (match_operand:BLK 1 "memory_operand" ""))
6351               (use (match_operand:DI 2 "immediate_operand" ""))
6352               (use (match_operand:DI 3 "immediate_operand" ""))])]
6353   ""
6354 {
6355   if (alpha_expand_block_move (operands))
6356     DONE;
6357   else
6358     FAIL;
6359 })
6360
6361 (define_expand "clrstrqi"
6362   [(parallel [(set (match_operand:BLK 0 "memory_operand" "")
6363                    (const_int 0))
6364               (use (match_operand:DI 1 "immediate_operand" ""))
6365               (use (match_operand:DI 2 "immediate_operand" ""))])]
6366   ""
6367 {
6368   if (alpha_expand_block_clear (operands))
6369     DONE;
6370   else
6371     FAIL;
6372 })
6373 \f
6374 ;; Subroutine of stack space allocation.  Perform a stack probe.
6375 (define_expand "probe_stack"
6376   [(set (match_dup 1) (match_operand:DI 0 "const_int_operand" ""))]
6377   ""
6378 {
6379   operands[1] = gen_rtx_MEM (DImode, plus_constant (stack_pointer_rtx,
6380                                                     INTVAL (operands[0])));
6381   MEM_VOLATILE_P (operands[1]) = 1;
6382
6383   operands[0] = const0_rtx;
6384 })
6385
6386 ;; This is how we allocate stack space.  If we are allocating a
6387 ;; constant amount of space and we know it is less than 4096
6388 ;; bytes, we need do nothing.
6389 ;;
6390 ;; If it is more than 4096 bytes, we need to probe the stack
6391 ;; periodically.
6392 (define_expand "allocate_stack"
6393   [(set (reg:DI 30)
6394         (plus:DI (reg:DI 30)
6395                  (match_operand:DI 1 "reg_or_cint_operand" "")))
6396    (set (match_operand:DI 0 "register_operand" "=r")
6397         (match_dup 2))]
6398   ""
6399 {
6400   if (GET_CODE (operands[1]) == CONST_INT
6401       && INTVAL (operands[1]) < 32768)
6402     {
6403       if (INTVAL (operands[1]) >= 4096)
6404         {
6405           /* We do this the same way as in the prologue and generate explicit
6406              probes.  Then we update the stack by the constant.  */
6407
6408           int probed = 4096;
6409
6410           emit_insn (gen_probe_stack (GEN_INT (- probed)));
6411           while (probed + 8192 < INTVAL (operands[1]))
6412             emit_insn (gen_probe_stack (GEN_INT (- (probed += 8192))));
6413
6414           if (probed + 4096 < INTVAL (operands[1]))
6415             emit_insn (gen_probe_stack (GEN_INT (- INTVAL(operands[1]))));
6416         }
6417
6418       operands[1] = GEN_INT (- INTVAL (operands[1]));
6419       operands[2] = virtual_stack_dynamic_rtx;
6420     }
6421   else
6422     {
6423       rtx out_label = 0;
6424       rtx loop_label = gen_label_rtx ();
6425       rtx want = gen_reg_rtx (Pmode);
6426       rtx tmp = gen_reg_rtx (Pmode);
6427       rtx memref;
6428
6429       emit_insn (gen_subdi3 (want, stack_pointer_rtx,
6430                              force_reg (Pmode, operands[1])));
6431       emit_insn (gen_adddi3 (tmp, stack_pointer_rtx, GEN_INT (-4096)));
6432
6433       if (GET_CODE (operands[1]) != CONST_INT)
6434         {
6435           out_label = gen_label_rtx ();
6436           emit_insn (gen_cmpdi (want, tmp));
6437           emit_jump_insn (gen_bgeu (out_label));
6438         }
6439
6440       emit_label (loop_label);
6441       memref = gen_rtx_MEM (DImode, tmp);
6442       MEM_VOLATILE_P (memref) = 1;
6443       emit_move_insn (memref, const0_rtx);
6444       emit_insn (gen_adddi3 (tmp, tmp, GEN_INT(-8192)));
6445       emit_insn (gen_cmpdi (tmp, want));
6446       emit_jump_insn (gen_bgtu (loop_label));
6447
6448       memref = gen_rtx_MEM (DImode, want);
6449       MEM_VOLATILE_P (memref) = 1;
6450       emit_move_insn (memref, const0_rtx);
6451
6452       if (out_label)
6453         emit_label (out_label);
6454
6455       emit_move_insn (stack_pointer_rtx, want);
6456       emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
6457       DONE;
6458     }
6459 })
6460
6461 ;; This is used by alpha_expand_prolog to do the same thing as above,
6462 ;; except we cannot at that time generate new basic blocks, so we hide
6463 ;; the loop in this one insn.
6464
6465 (define_insn "prologue_stack_probe_loop"
6466   [(unspec_volatile [(match_operand:DI 0 "register_operand" "r")
6467                      (match_operand:DI 1 "register_operand" "r")]
6468                     UNSPECV_PSPL)]
6469   ""
6470 {
6471   operands[2] = gen_label_rtx ();
6472   ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "L",
6473                              CODE_LABEL_NUMBER (operands[2]));
6474
6475   return "stq $31,-8192(%1)\;subq %0,1,%0\;lda %1,-8192(%1)\;bne %0,%l2";
6476 }
6477   [(set_attr "length" "16")
6478    (set_attr "type" "multi")])
6479
6480 (define_expand "prologue"
6481   [(clobber (const_int 0))]
6482   ""
6483 {
6484   alpha_expand_prologue ();
6485   DONE;
6486 })
6487
6488 ;; These take care of emitting the ldgp insn in the prologue. This will be
6489 ;; an lda/ldah pair and we want to align them properly.  So we have two
6490 ;; unspec_volatile insns, the first of which emits the ldgp assembler macro
6491 ;; and the second of which emits nothing.  However, both are marked as type
6492 ;; IADD (the default) so the alignment code in alpha.c does the right thing
6493 ;; with them.
6494
6495 (define_expand "prologue_ldgp"
6496   [(set (match_dup 0)
6497         (unspec_volatile:DI [(match_dup 1) (match_dup 2)] UNSPECV_LDGP1))
6498    (set (match_dup 0)
6499         (unspec_volatile:DI [(match_dup 0) (match_dup 2)] UNSPECV_PLDGP2))]
6500   ""
6501 {
6502   operands[0] = pic_offset_table_rtx;
6503   operands[1] = gen_rtx_REG (Pmode, 27);
6504   operands[2] = (TARGET_EXPLICIT_RELOCS
6505                  ? GEN_INT (alpha_next_sequence_number++)
6506                  : const0_rtx);
6507 })
6508
6509 (define_insn "*ldgp_er_1"
6510   [(set (match_operand:DI 0 "register_operand" "=r")
6511         (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "r")
6512                              (match_operand 2 "const_int_operand" "")]
6513                             UNSPECV_LDGP1))]
6514   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
6515   "ldah %0,0(%1)\t\t!gpdisp!%2")
6516
6517 (define_insn "*ldgp_er_2"
6518   [(set (match_operand:DI 0 "register_operand" "=r")
6519         (unspec:DI [(match_operand:DI 1 "register_operand" "r")
6520                     (match_operand 2 "const_int_operand" "")]
6521                    UNSPEC_LDGP2))]
6522   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
6523   "lda %0,0(%1)\t\t!gpdisp!%2")
6524
6525 (define_insn "*prologue_ldgp_er_2"
6526   [(set (match_operand:DI 0 "register_operand" "=r")
6527         (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "r")
6528                              (match_operand 2 "const_int_operand" "")]
6529                             UNSPECV_PLDGP2))]
6530   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
6531   "lda %0,0(%1)\t\t!gpdisp!%2\n$%~..ng:")
6532
6533 (define_insn "*prologue_ldgp_1"
6534   [(set (match_operand:DI 0 "register_operand" "=r")
6535         (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "r")
6536                              (match_operand 2 "const_int_operand" "")]
6537                             UNSPECV_LDGP1))]
6538   ""
6539   "ldgp %0,0(%1)\n$%~..ng:")
6540
6541 (define_insn "*prologue_ldgp_2"
6542   [(set (match_operand:DI 0 "register_operand" "=r")
6543         (unspec_volatile:DI [(match_operand:DI 1 "register_operand" "r")
6544                              (match_operand 2 "const_int_operand" "")]
6545                             UNSPECV_PLDGP2))]
6546   ""
6547   "")
6548
6549 ;; The _mcount profiling hook has special calling conventions, and
6550 ;; does not clobber all the registers that a normal call would.  So
6551 ;; hide the fact this is a call at all.
6552
6553 (define_insn "prologue_mcount"
6554   [(unspec_volatile [(const_int 0)] UNSPECV_MCOUNT)]
6555   ""
6556 {
6557   if (TARGET_EXPLICIT_RELOCS)
6558     /* Note that we cannot use a lituse_jsr reloc, since _mcount
6559        cannot be called via the PLT.  */
6560     return "ldq $28,_mcount($29)\t\t!literal\;jsr $28,($28),_mcount";
6561   else
6562     return "lda $28,_mcount\;jsr $28,($28),_mcount";
6563 }
6564   [(set_attr "type" "multi")
6565    (set_attr "length" "8")])
6566
6567 (define_insn "init_fp"
6568   [(set (match_operand:DI 0 "register_operand" "=r")
6569         (match_operand:DI 1 "register_operand" "r"))
6570    (clobber (mem:BLK (match_operand:DI 2 "register_operand" "=r")))]
6571   ""
6572   "bis $31,%1,%0")
6573
6574 (define_expand "epilogue"
6575   [(return)]
6576   ""
6577 {
6578   alpha_expand_epilogue ();
6579 })
6580
6581 (define_expand "sibcall_epilogue"
6582   [(return)]
6583   "TARGET_ABI_OSF"
6584 {
6585   alpha_expand_epilogue ();
6586   DONE;
6587 })
6588
6589 ;; In creating a large stack frame, NT _must_ use ldah+lda to load
6590 ;; the frame size into a register.  We use this pattern to ensure
6591 ;; we get lda instead of addq.
6592 (define_insn "nt_lda"
6593   [(set (match_operand:DI 0 "register_operand" "=r")
6594         (unspec:DI [(match_dup 0)
6595                     (match_operand:DI 1 "const_int_operand" "n")]
6596                    UNSPEC_NT_LDA))]
6597   ""
6598   "lda %0,%1(%0)")
6599
6600 (define_expand "builtin_longjmp"
6601   [(use (match_operand:DI 0 "register_operand" "r"))]
6602   "TARGET_ABI_OSF"
6603 {
6604   /* The elements of the buffer are, in order:  */
6605   rtx fp = gen_rtx_MEM (Pmode, operands[0]);
6606   rtx lab = gen_rtx_MEM (Pmode, plus_constant (operands[0], 8));
6607   rtx stack = gen_rtx_MEM (Pmode, plus_constant (operands[0], 16));
6608   rtx pv = gen_rtx_REG (Pmode, 27);
6609
6610   /* This bit is the same as expand_builtin_longjmp.  */
6611   emit_move_insn (hard_frame_pointer_rtx, fp);
6612   emit_move_insn (pv, lab);
6613   emit_stack_restore (SAVE_NONLOCAL, stack, NULL_RTX);
6614   emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
6615   emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
6616
6617   /* Load the label we are jumping through into $27 so that we know
6618      where to look for it when we get back to setjmp's function for
6619      restoring the gp.  */
6620   emit_jump_insn (gen_builtin_longjmp_internal (pv));
6621   emit_barrier ();
6622   DONE;
6623 })
6624
6625 ;; This is effectively a copy of indirect_jump, but constrained such
6626 ;; that register renaming cannot foil our cunning plan with $27.
6627 (define_insn "builtin_longjmp_internal"
6628   [(set (pc)
6629         (unspec_volatile [(match_operand:DI 0 "register_operand" "c")]
6630                          UNSPECV_LONGJMP))]
6631   ""
6632   "jmp $31,(%0),0"
6633   [(set_attr "type" "ibr")])
6634
6635 (define_insn "*builtin_setjmp_receiver_er_sl_1"
6636   [(unspec_volatile [(label_ref (match_operand 0 "" ""))] UNSPECV_SETJMPR)]
6637   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF && TARGET_AS_CAN_SUBTRACT_LABELS"
6638   "lda $27,$LSJ%=-%l0($27)\n$LSJ%=:")
6639   
6640 (define_insn "*builtin_setjmp_receiver_er_1"
6641   [(unspec_volatile [(label_ref (match_operand 0 "" ""))] UNSPECV_SETJMPR)]
6642   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
6643   "br $27,$LSJ%=\n$LSJ%=:"
6644   [(set_attr "type" "ibr")])
6645
6646 (define_split
6647   [(unspec_volatile [(label_ref (match_operand 0 "" ""))] UNSPECV_SETJMPR)]
6648   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF
6649    && prev_nonnote_insn (insn) == operands[0]"
6650   [(const_int 0)]
6651   "DONE;")
6652
6653 (define_insn "*builtin_setjmp_receiver_1"
6654   [(unspec_volatile [(label_ref (match_operand 0 "" ""))] UNSPECV_SETJMPR)]
6655   "TARGET_ABI_OSF"
6656   "br $27,$LSJ%=\n$LSJ%=:\;ldgp $29,0($27)"
6657   [(set_attr "length" "12")
6658    (set_attr "type" "multi")])
6659
6660 (define_expand "builtin_setjmp_receiver_er"
6661   [(unspec_volatile [(label_ref (match_operand 0 "" ""))] UNSPECV_SETJMPR)
6662    (set (match_dup 1)
6663         (unspec_volatile:DI [(match_dup 2) (match_dup 3)] UNSPECV_LDGP1))
6664    (set (match_dup 1)
6665         (unspec:DI [(match_dup 1) (match_dup 3)] UNSPEC_LDGP2))]
6666   ""
6667 {
6668   operands[1] = pic_offset_table_rtx;
6669   operands[2] = gen_rtx_REG (Pmode, 27);
6670   operands[3] = GEN_INT (alpha_next_sequence_number++);
6671 })
6672
6673 (define_expand "builtin_setjmp_receiver"
6674   [(unspec_volatile [(label_ref (match_operand 0 "" ""))] UNSPECV_SETJMPR)]
6675   "TARGET_ABI_OSF"
6676 {
6677   if (TARGET_EXPLICIT_RELOCS)
6678     {
6679       emit_insn (gen_builtin_setjmp_receiver_er (operands[0]));
6680       DONE;
6681     }
6682 })
6683
6684 (define_expand "exception_receiver_er"
6685   [(set (match_dup 0)
6686         (unspec_volatile:DI [(match_dup 1) (match_dup 2)] UNSPECV_LDGP1))
6687    (set (match_dup 0)
6688         (unspec:DI [(match_dup 0) (match_dup 2)] UNSPEC_LDGP2))]
6689   ""
6690 {
6691   operands[0] = pic_offset_table_rtx;
6692   operands[1] = gen_rtx_REG (Pmode, 26);
6693   operands[2] = GEN_INT (alpha_next_sequence_number++);
6694 })
6695
6696 (define_expand "exception_receiver"
6697   [(unspec_volatile [(match_dup 0)] UNSPECV_EHR)]
6698   "TARGET_ABI_OSF"
6699 {
6700   if (TARGET_LD_BUGGY_LDGP)
6701     operands[0] = alpha_gp_save_rtx ();
6702   else if (TARGET_EXPLICIT_RELOCS)
6703     {
6704       emit_insn (gen_exception_receiver_er ());
6705       DONE;
6706     }
6707   else
6708     operands[0] = const0_rtx;
6709 })
6710
6711 (define_insn "*exception_receiver_1"
6712   [(unspec_volatile [(const_int 0)] UNSPECV_EHR)]
6713   "! TARGET_LD_BUGGY_LDGP"
6714   "ldgp $29,0($26)"
6715   [(set_attr "length" "8")
6716    (set_attr "type" "multi")])
6717
6718 (define_insn "*exception_receiver_2"
6719   [(unspec_volatile [(match_operand:DI 0 "memory_operand" "m")] UNSPECV_EHR)]
6720   "TARGET_LD_BUGGY_LDGP"
6721   "ldq $29,%0"
6722   [(set_attr "type" "ild")])
6723
6724 (define_expand "nonlocal_goto_receiver"
6725   [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)
6726    (set (reg:DI 27) (mem:DI (reg:DI 29)))
6727    (unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)
6728    (use (reg:DI 27))]
6729   "TARGET_ABI_OPEN_VMS"
6730   "")
6731
6732 (define_insn "arg_home"
6733   [(unspec [(const_int 0)] UNSPEC_ARG_HOME)
6734    (use (reg:DI 1))
6735    (use (reg:DI 25))
6736    (use (reg:DI 16))
6737    (use (reg:DI 17))
6738    (use (reg:DI 18))
6739    (use (reg:DI 19))
6740    (use (reg:DI 20))
6741    (use (reg:DI 21))
6742    (use (reg:DI 48))
6743    (use (reg:DI 49))
6744    (use (reg:DI 50))
6745    (use (reg:DI 51))
6746    (use (reg:DI 52))
6747    (use (reg:DI 53))
6748    (clobber (mem:BLK (const_int 0)))
6749    (clobber (reg:DI 24))
6750    (clobber (reg:DI 25))
6751    (clobber (reg:DI 0))]
6752   "TARGET_ABI_OPEN_VMS"
6753   "lda $0,OTS$HOME_ARGS\;ldq $0,8($0)\;jsr $0,OTS$HOME_ARGS"
6754   [(set_attr "length" "16")
6755    (set_attr "type" "multi")])
6756
6757 ;; Load the CIW into r2 for calling __T3E_MISMATCH
6758
6759 (define_expand "umk_mismatch_args"
6760   [(set:DI (match_dup 1) (mem:DI (plus:DI (reg:DI 15) (const_int -16))))
6761    (set:DI (match_dup 2) (mem:DI (plus:DI (match_dup 1) (const_int -32))))
6762    (set:DI (reg:DI 1) (match_operand:DI 0 "const_int_operand" ""))
6763    (set:DI (match_dup 3) (plus:DI (mult:DI (reg:DI 25)
6764                                            (const_int 8))
6765                                   (match_dup 2)))
6766    (set:DI (reg:DI 2) (mem:DI (match_dup 3)))]
6767   "TARGET_ABI_UNICOSMK"
6768 {
6769   operands[1] = gen_reg_rtx (DImode);
6770   operands[2] = gen_reg_rtx (DImode);
6771   operands[3] = gen_reg_rtx (DImode);
6772 })
6773
6774 (define_insn "arg_home_umk"
6775   [(unspec [(const_int 0)] UNSPEC_ARG_HOME)
6776    (use (reg:DI 1))
6777    (use (reg:DI 2))
6778    (use (reg:DI 16))
6779    (use (reg:DI 17))
6780    (use (reg:DI 18))
6781    (use (reg:DI 19))
6782    (use (reg:DI 20))
6783    (use (reg:DI 21))
6784    (use (reg:DI 48))
6785    (use (reg:DI 49))
6786    (use (reg:DI 50))
6787    (use (reg:DI 51))
6788    (use (reg:DI 52))
6789    (use (reg:DI 53))
6790    (clobber (mem:BLK (const_int 0)))
6791    (parallel [
6792    (clobber (reg:DI 22))
6793    (clobber (reg:DI 23))
6794    (clobber (reg:DI 24))
6795    (clobber (reg:DI 0))
6796    (clobber (reg:DI 1))
6797    (clobber (reg:DI 2))
6798    (clobber (reg:DI 3))
6799    (clobber (reg:DI 4))
6800    (clobber (reg:DI 5))
6801    (clobber (reg:DI 6))
6802    (clobber (reg:DI 7))
6803    (clobber (reg:DI 8))])]
6804   "TARGET_ABI_UNICOSMK"
6805   "laum $4,__T3E_MISMATCH($31)\;sll $4,32,$4\;lalm $4,__T3E_MISMATCH($4)\;lal $4,__T3E_MISMATCH($4)\;jsr $3,($4)"
6806   [(set_attr "length" "16")
6807    (set_attr "type" "multi")])
6808
6809 ;; Prefetch data.  
6810 ;;
6811 ;; On EV4, these instructions are nops -- no load occurs.
6812 ;;
6813 ;; On EV5, these instructions act as a normal load, and thus can trap
6814 ;; if the address is invalid.  The OS may (or may not) handle this in
6815 ;; the entMM fault handler and suppress the fault.  If so, then this
6816 ;; has the effect of a read prefetch instruction.
6817 ;;
6818 ;; On EV6, these become official prefetch instructions.
6819
6820 (define_insn "prefetch"
6821   [(prefetch (match_operand:DI 0 "address_operand" "p")
6822              (match_operand:DI 1 "const_int_operand" "n")
6823              (match_operand:DI 2 "const_int_operand" "n"))]
6824   "TARGET_FIXUP_EV5_PREFETCH || TARGET_CPU_EV6"
6825 {
6826   /* Interpret "no temporal locality" as this data should be evicted once
6827      it is used.  The "evict next" alternatives load the data into the cache
6828      and leave the LRU eviction counter pointing to that block.  */
6829   static const char * const alt[2][2] = {
6830     { 
6831       "lds $f31,%a0",           /* read, evict next */
6832       "ldl $31,%a0",            /* read, evict last */
6833     },
6834     {
6835       "ldt $f31,%a0",           /* write, evict next */
6836       "ldq $31,%a0",            /* write, evict last */
6837     }
6838   };
6839
6840   bool write = INTVAL (operands[1]) != 0;
6841   bool lru = INTVAL (operands[2]) != 0;
6842
6843   return alt[write][lru];
6844 }
6845   [(set_attr "type" "ild")])
6846
6847 ;; Close the trap shadow of preceding instructions.  This is generated
6848 ;; by alpha_reorg.
6849
6850 (define_insn "trapb"
6851   [(unspec_volatile [(const_int 0)] UNSPECV_TRAPB)]
6852   ""
6853   "trapb"
6854   [(set_attr "type" "misc")])
6855
6856 ;; No-op instructions used by machine-dependent reorg to preserve
6857 ;; alignment for instruction issue.
6858 ;; The Unicos/Mk assembler does not support these opcodes.
6859
6860 (define_insn "nop"
6861   [(const_int 0)]
6862   ""
6863   "bis $31,$31,$31"
6864   [(set_attr "type" "ilog")])
6865
6866 (define_insn "fnop"
6867   [(const_int 1)]
6868   "TARGET_FP"
6869   "cpys $f31,$f31,$f31"
6870   [(set_attr "type" "fcpys")])
6871
6872 (define_insn "unop"
6873   [(const_int 2)]
6874   ""
6875   "ldq_u $31,0($30)")
6876
6877 ;; On Unicos/Mk we use a macro for aligning code.
6878
6879 (define_insn "realign"
6880   [(unspec_volatile [(match_operand 0 "immediate_operand" "i")]
6881                     UNSPECV_REALIGN)]
6882   ""
6883 {
6884   if (TARGET_ABI_UNICOSMK)
6885     return "gcc@code@align %0";
6886   else
6887     return ".align %0 #realign";
6888 })
6889
6890 ;; The call patterns are at the end of the file because their
6891 ;; wildcard operand0 interferes with nice recognition.
6892
6893 (define_insn "*call_value_osf_1_er"
6894   [(set (match_operand 0 "" "")
6895         (call (mem:DI (match_operand:DI 1 "call_operand" "c,R,s"))
6896               (match_operand 2 "" "")))
6897    (use (reg:DI 29))
6898    (clobber (reg:DI 26))]
6899   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
6900   "@
6901    jsr $26,(%1),0\;ldah $29,0($26)\t\t!gpdisp!%*\;lda $29,0($29)\t\t!gpdisp!%*
6902    bsr $26,$%1..ng
6903    ldq $27,%1($29)\t\t!literal!%#\;jsr $26,($27),0\t\t!lituse_jsr!%#\;ldah $29,0($26)\t\t!gpdisp!%*\;lda $29,0($29)\t\t!gpdisp!%*"
6904   [(set_attr "type" "jsr")
6905    (set_attr "length" "12,*,16")])
6906
6907 ;; We must use peep2 instead of a split because we need accurate life
6908 ;; information for $gp.  Consider the case of { bar(); while (1); }.
6909 (define_peephole2
6910   [(parallel [(set (match_operand 0 "" "")
6911                    (call (mem:DI (match_operand:DI 1 "call_operand" ""))
6912                          (match_operand 2 "" "")))
6913               (use (reg:DI 29))
6914               (clobber (reg:DI 26))])]
6915   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF && reload_completed
6916    && ! current_file_function_operand (operands[1], Pmode)
6917    && peep2_regno_dead_p (1, 29)"
6918   [(parallel [(set (match_dup 0)
6919                    (call (mem:DI (match_dup 3))
6920                          (match_dup 2)))
6921               (set (reg:DI 26) (plus:DI (pc) (const_int 4)))
6922               (unspec_volatile [(reg:DI 29)] UNSPECV_BLOCKAGE)
6923               (use (match_dup 1))
6924               (use (match_dup 4))])]
6925 {
6926   if (CONSTANT_P (operands[1]))
6927     {
6928       operands[3] = gen_rtx_REG (Pmode, 27);
6929       operands[4] = GEN_INT (alpha_next_sequence_number++);
6930       emit_insn (gen_movdi_er_high_g (operands[3], pic_offset_table_rtx,
6931                                       operands[1], operands[4]));
6932     }
6933   else
6934     {
6935       operands[3] = operands[1];
6936       operands[1] = const0_rtx;
6937       operands[4] = const0_rtx;
6938     }
6939 })
6940
6941 (define_peephole2
6942   [(parallel [(set (match_operand 0 "" "")
6943                    (call (mem:DI (match_operand:DI 1 "call_operand" ""))
6944                          (match_operand 2 "" "")))
6945               (use (reg:DI 29))
6946               (clobber (reg:DI 26))])]
6947   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF && reload_completed
6948    && ! current_file_function_operand (operands[1], Pmode)
6949    && ! peep2_regno_dead_p (1, 29)"
6950   [(parallel [(set (match_dup 0)
6951                    (call (mem:DI (match_dup 3))
6952                          (match_dup 2)))
6953               (set (reg:DI 26) (plus:DI (pc) (const_int 4)))
6954               (unspec_volatile [(reg:DI 29)] UNSPECV_BLOCKAGE)
6955               (use (match_dup 1))
6956               (use (match_dup 5))])
6957    (set (reg:DI 29)
6958         (unspec_volatile:DI [(reg:DI 26) (match_dup 4)] UNSPECV_LDGP1))
6959    (set (reg:DI 29)
6960         (unspec:DI [(reg:DI 29) (match_dup 4)] UNSPEC_LDGP2))]
6961 {
6962   if (CONSTANT_P (operands[1]))
6963     {
6964       operands[3] = gen_rtx_REG (Pmode, 27);
6965       operands[5] = GEN_INT (alpha_next_sequence_number++);
6966       emit_insn (gen_movdi_er_high_g (operands[3], pic_offset_table_rtx,
6967                                       operands[1], operands[5]));
6968     }
6969   else
6970     {
6971       operands[3] = operands[1];
6972       operands[1] = const0_rtx;
6973       operands[5] = const0_rtx;
6974     }
6975   operands[4] = GEN_INT (alpha_next_sequence_number++);
6976 })
6977
6978 ;; We add a blockage unspec_volatile to prevent insns from moving down
6979 ;; from above the call to in between the call and the ldah gpdisp.
6980 (define_insn "*call_value_osf_2_er"
6981   [(set (match_operand 0 "" "")
6982         (call (mem:DI (match_operand:DI 1 "register_operand" "c"))
6983               (match_operand 2 "" "")))
6984    (set (reg:DI 26)
6985         (plus:DI (pc) (const_int 4)))
6986    (unspec_volatile [(reg:DI 29)] UNSPECV_BLOCKAGE)
6987    (use (match_operand 3 "" ""))
6988    (use (match_operand 4 "const_int_operand" ""))]
6989   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
6990   "jsr $26,(%1),%3%J4"
6991   [(set_attr "type" "jsr")])
6992
6993 (define_insn "*call_value_osf_1_noreturn"
6994   [(set (match_operand 0 "" "")
6995         (call (mem:DI (match_operand:DI 1 "call_operand" "c,R,s"))
6996               (match_operand 2 "" "")))
6997    (use (reg:DI 29))
6998    (clobber (reg:DI 26))]
6999   "! TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF
7000    && find_reg_note (insn, REG_NORETURN, NULL_RTX)"
7001   "@
7002    jsr $26,($27),0
7003    bsr $26,$%1..ng
7004    jsr $26,%1"
7005   [(set_attr "type" "jsr")
7006    (set_attr "length" "*,*,8")])
7007
7008 (define_insn "*call_value_osf_1"
7009   [(set (match_operand 0 "" "")
7010         (call (mem:DI (match_operand:DI 1 "call_operand" "c,R,s"))
7011               (match_operand 2 "" "")))
7012    (use (reg:DI 29))
7013    (clobber (reg:DI 26))]
7014   "! TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
7015   "@
7016    jsr $26,($27),0\;ldgp $29,0($26)
7017    bsr $26,$%1..ng
7018    jsr $26,%1\;ldgp $29,0($26)"
7019   [(set_attr "type" "jsr")
7020    (set_attr "length" "12,*,16")])
7021
7022 (define_insn "*sibcall_value_osf_1_er"
7023   [(set (match_operand 0 "" "")
7024         (call (mem:DI (match_operand:DI 1 "symbolic_operand" "R,s"))
7025               (match_operand 2 "" "")))
7026    (unspec [(reg:DI 29)] UNSPEC_SIBCALL)]
7027   "TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
7028   "@
7029    br $31,$%1..ng
7030    ldq $27,%1($29)\t\t!literal!%#\;jmp $31,($27),%1\t\t!lituse_jsr!%#"
7031   [(set_attr "type" "jsr")
7032    (set_attr "length" "*,8")])
7033
7034 (define_insn "*sibcall_value_osf_1"
7035   [(set (match_operand 0 "" "")
7036         (call (mem:DI (match_operand:DI 1 "symbolic_operand" "R,s"))
7037               (match_operand 2 "" "")))
7038    (unspec [(reg:DI 29)] UNSPEC_SIBCALL)]
7039   "! TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
7040   "@
7041    br $31,$%1..ng
7042    lda $27,%1\;jmp $31,($27),%1"
7043   [(set_attr "type" "jsr")
7044    (set_attr "length" "*,8")])
7045
7046 (define_insn "*call_value_nt_1"
7047   [(set (match_operand 0 "" "")
7048         (call (mem:DI (match_operand:DI 1 "call_operand" "r,R,s"))
7049               (match_operand 2 "" "")))
7050    (clobber (reg:DI 26))]
7051   "TARGET_ABI_WINDOWS_NT"
7052   "@
7053    jsr $26,(%1)
7054    bsr $26,%1
7055    jsr $26,%1"
7056   [(set_attr "type" "jsr")
7057    (set_attr "length" "*,*,12")])
7058
7059 (define_insn "*call_value_vms_1"
7060   [(set (match_operand 0 "" "")
7061         (call (mem:DI (match_operand:DI 1 "call_operand" "r,s"))
7062               (match_operand 2 "" "")))
7063    (use (match_operand:DI 3 "nonimmediate_operand" "r,m"))
7064    (use (reg:DI 25))
7065    (use (reg:DI 26))
7066    (clobber (reg:DI 27))]
7067   "TARGET_ABI_OPEN_VMS"
7068   "@
7069    mov %3,$27\;jsr $26,0\;ldq $27,0($29)
7070    ldq $27,%3\;jsr $26,%1\;ldq $27,0($29)"
7071   [(set_attr "type" "jsr")
7072    (set_attr "length" "12,16")])
7073
7074 (define_insn "*call_value_umk"
7075   [(set (match_operand 0 "" "")
7076         (call (mem:DI (match_operand:DI 1 "call_operand" "r"))
7077               (match_operand 2 "" "")))
7078    (use (reg:DI 25))
7079    (clobber (reg:DI 26))]
7080   "TARGET_ABI_UNICOSMK"
7081   "jsr $26,(%1)"
7082   [(set_attr "type" "jsr")])
7083