OSDN Git Service

(negdi2, negdi2_internal): Renamed from negdi3...
[pf3gnuchains/gcc-fork.git] / gcc / config / mips / mips.md
1 ;;  Mips.md          Machine Description for MIPS based processors
2 ;;  Contributed by   A. Lichnewsky, lich@inria.inria.fr
3 ;;  Changes by       Michael Meissner, meissner@osf.org
4 ;;  Copyright (C) 1989, 1990, 1991, 1992 Free Software Foundation, Inc.
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, 675 Mass Ave, Cambridge, MA 02139, USA.
21
22 \f
23
24 ;; ....................
25 ;;
26 ;;      Attributes
27 ;;
28 ;; ....................
29
30 ;; Classification of each insn.
31 ;; branch       conditional branch
32 ;; jump         unconditional jump
33 ;; call         unconditional call
34 ;; load         load instruction(s)
35 ;; store        store instruction(s)
36 ;; move         data movement within same register set
37 ;; xfer         transfer to/from coprocessor
38 ;; hilo         transfer of hi/lo registers
39 ;; arith        integer arithmetic instruction
40 ;; darith       double precision integer arithmetic instructions
41 ;; imul         integer multiply
42 ;; idiv         integer divide
43 ;; icmp         integer compare
44 ;; fadd         floating point add/subtract
45 ;; fmul         floating point multiply
46 ;; fdiv         floating point divide
47 ;; fabs         floating point absolute value
48 ;; fneg         floating point negation
49 ;; fcmp         floating point compare
50 ;; fcvt         floating point convert
51 ;; fsqrt        floating point square root
52 ;; multi        multiword sequence (or user asm statements)
53 ;; nop          no operation
54
55 (define_attr "type"
56   "unknown,branch,jump,call,load,store,move,xfer,hilo,arith,darith,imul,idiv,icmp,fadd,fmul,fdiv,fabs,fneg,fcmp,fcvt,fsqrt,multi,nop"
57   (const_string "unknown"))
58
59 ;; Main data type used by the insn
60 (define_attr "mode" "unknown,none,QI,HI,SI,DI,SF,DF,FPSW" (const_string "unknown"))
61
62 ;; # instructions (4 bytes each)
63 (define_attr "length" "" (const_int 1))
64
65 ;; whether or not an instruction has a mandatory delay slot
66 (define_attr "dslot" "no,yes"
67   (if_then_else (eq_attr "type" "branch,jump,call,load,xfer,hilo,fcmp")
68                 (const_string "yes")
69                 (const_string "no")))
70
71 ;; Attribute describing the processor.  This attribute must match exactly
72 ;; with the processor_type enumeration in mips.h.
73
74 ;; Attribute describing the processor
75 ;; (define_attr "cpu" "default,r3000,r6000,r4000"
76 ;;   (const
77 ;;    (cond [(eq (symbol_ref "mips_cpu") (symbol_ref "PROCESSOR_R3000"))   (const_string "r3000")
78 ;;           (eq (symbol_ref "mips_cpu") (symbol_ref "PROCESSOR_R4000"))   (const_string "r4000")
79 ;;           (eq (symbol_ref "mips_cpu") (symbol_ref "PROCESSOR_R6000"))   (const_string "r6000")]
80 ;;          (const_string "default"))))
81
82 (define_attr "cpu" "default,r3000,r6000,r4000"
83   (const (symbol_ref "mips_cpu_attr")))
84
85 ;; Attribute defining whether or not we can use the branch-likely instructions
86 ;; (MIPS ISA level 2)
87
88 (define_attr "branch_likely" "no,yes"
89   (const
90    (if_then_else (ge (symbol_ref "mips_isa") (const_int 2))
91                  (const_string "yes")
92                  (const_string "no"))))
93
94
95 ;; Describe a user's asm statement.
96 (define_asm_attributes
97   [(set_attr "type" "multi")])
98
99 \f
100
101 ;; .........................
102 ;;
103 ;;      Delay slots, can't describe load/fcmp/xfer delay slots here
104 ;;
105 ;; .........................
106
107 (define_delay (eq_attr "type" "branch")
108   [(and (eq_attr "dslot" "no") (eq_attr "length" "1"))
109    (nil)
110    (and (eq_attr "branch_likely" "yes") (and (eq_attr "dslot" "no") (eq_attr "length" "1")))])
111
112 (define_delay (eq_attr "type" "call,jump")
113   [(and (eq_attr "dslot" "no") (eq_attr "length" "1"))
114    (nil)
115    (nil)])
116
117 \f
118
119 ;; .........................
120 ;;
121 ;;      Functional units
122 ;;
123 ;; .........................
124
125 ; (define_function_unit NAME MULTIPLICITY SIMULTANEITY
126 ;                       TEST READY-DELAY ISSUE-DELAY [CONFLICT-LIST])
127
128 ;; Make the default case (PROCESSOR_DEFAULT) handle the worst case
129
130 (define_function_unit "memory" 1 0
131   (and (eq_attr "type" "load") (eq_attr "cpu" "!r3000"))
132   3 0)
133
134 (define_function_unit "memory" 1 0
135   (and (eq_attr "type" "load") (eq_attr "cpu" "r3000"))
136   2 0)
137
138 (define_function_unit "memory"   1 0 (eq_attr "type" "store") 1 0)
139
140 (define_function_unit "addr"     1 0 (eq_attr "type" "fcmp") 2 0)
141
142 (define_function_unit "memory"   1 0 (eq_attr "type" "xfer") 2 0)
143 (define_function_unit "memory"   1 0 (eq_attr "type" "hilo") 3 0)
144
145 (define_function_unit "imuldiv"  1 1
146   (and (eq_attr "type" "imul") (eq_attr "cpu" "!r3000,r4000"))
147   17 0)
148
149 (define_function_unit "imuldiv"  1 1
150   (and (eq_attr "type" "imul") (eq_attr "cpu" "r3000"))
151   12 0)
152
153 (define_function_unit "imuldiv" 1 1
154   (and (eq_attr "type" "imul") (eq_attr "cpu" "r4000"))
155   10 0)
156
157 (define_function_unit "imuldiv"  1 1
158   (and (eq_attr "type" "idiv") (eq_attr "cpu" "!r3000,r4000"))
159   38 0)
160
161 (define_function_unit "imuldiv"  1 1
162   (and (eq_attr "type" "idiv") (eq_attr "cpu" "r3000"))
163   35 0)
164
165 (define_function_unit "imuldiv" 1 1
166   (and (eq_attr "type" "idiv") (eq_attr "cpu" "r4000"))
167   69 0)
168
169 (define_function_unit "adder" 1 1
170   (and (eq_attr "type" "fadd") (eq_attr "cpu" "!r3000,r6000"))
171   4 0)
172
173 (define_function_unit "adder" 1 1
174   (and (eq_attr "type" "fadd") (eq_attr "cpu" "r3000"))
175   2 0)
176
177 (define_function_unit "adder" 1 1
178   (and (eq_attr "type" "fadd") (eq_attr "cpu" "r6000"))
179   3 0)
180
181 (define_function_unit "adder" 1 1
182   (and (eq_attr "type" "fabs,fneg") (eq_attr "cpu" "!r3000"))
183   2 0)
184
185 (define_function_unit "adder" 1 1
186   (and (eq_attr "type" "fabs,fneg") (eq_attr "cpu" "r3000"))
187   1 0)
188
189 (define_function_unit "mult" 1 1
190   (and (eq_attr "type" "fmul") (and (eq_attr "mode" "SF") (eq_attr "cpu" "!r3000,r6000")))
191   7 0)
192
193 (define_function_unit "mult" 1 1
194   (and (eq_attr "type" "fmul") (and (eq_attr "mode" "SF") (eq_attr "cpu" "r3000")))
195   4 0)
196
197 (define_function_unit "mult" 1 1
198   (and (eq_attr "type" "fmul") (and (eq_attr "mode" "SF") (eq_attr "cpu" "r6000")))
199   5 0)
200
201 (define_function_unit "mult" 1 1
202   (and (eq_attr "type" "fmul") (and (eq_attr "mode" "DF") (eq_attr "cpu" "!r3000,r6000")))
203   8 0)
204
205 (define_function_unit "mult" 1 1
206   (and (eq_attr "type" "fmul") (and (eq_attr "mode" "DF") (eq_attr "cpu" "r3000")))
207   5 0)
208
209 (define_function_unit "mult" 1 1
210   (and (eq_attr "type" "fmul") (and (eq_attr "mode" "DF") (eq_attr "cpu" "r6000")))
211   6 0)
212
213 (define_function_unit "divide" 1 1
214   (and (eq_attr "type" "fdiv") (and (eq_attr "mode" "SF") (eq_attr "cpu" "!r3000,r6000")))
215   23 0)
216
217 (define_function_unit "divide" 1 1
218   (and (eq_attr "type" "fdiv") (and (eq_attr "mode" "SF") (eq_attr "cpu" "r3000")))
219   12 0)
220
221 (define_function_unit "divide" 1 1
222   (and (eq_attr "type" "fdiv") (and (eq_attr "mode" "SF") (eq_attr "cpu" "r6000")))
223   15 0)
224
225 (define_function_unit "divide" 1 1
226   (and (eq_attr "type" "fdiv") (and (eq_attr "mode" "DF") (eq_attr "cpu" "!r3000,r6000")))
227   36 0)
228
229 (define_function_unit "divide" 1 1
230   (and (eq_attr "type" "fdiv") (and (eq_attr "mode" "DF") (eq_attr "cpu" "r3000")))
231   19 0)
232
233 (define_function_unit "divide" 1 1
234   (and (eq_attr "type" "fdiv") (and (eq_attr "mode" "DF") (eq_attr "cpu" "r6000")))
235   16 0)
236
237 (define_function_unit "divide" 1 1 (and (eq_attr "type" "fsqrt") (eq_attr "mode" "SF"))  54 0)
238 (define_function_unit "divide" 1 1 (and (eq_attr "type" "fsqrt") (eq_attr "mode" "DF")) 112 0)
239
240 \f
241 ;; The following functional units do not use the cpu type, and use
242 ;; much less memory in genattrtab.c.
243
244 ;; (define_function_unit "memory"   1 0 (eq_attr "type" "load")                                3 0)
245 ;; (define_function_unit "memory"   1 0 (eq_attr "type" "store")                               1 0)
246 ;;       
247 ;; (define_function_unit "fp_comp"  1 0 (eq_attr "type" "fcmp")                                2 0)
248 ;;       
249 ;; (define_function_unit "transfer" 1 0 (eq_attr "type" "xfer")                                2 0)
250 ;; (define_function_unit "transfer" 1 0 (eq_attr "type" "hilo")                                3 0)
251 ;;   
252 ;; (define_function_unit "imuldiv"  1 1 (eq_attr "type" "imul")                               17 0)
253 ;; (define_function_unit "imuldiv"  1 1 (eq_attr "type" "idiv")                               38 0)
254 ;;   
255 ;; (define_function_unit "adder"    1 1 (eq_attr "type" "fadd")                                4 0)
256 ;; (define_function_unit "adder"    1 1 (eq_attr "type" "fabs,fneg")                           2 0)
257 ;;   
258 ;; (define_function_unit "mult"     1 1 (and (eq_attr "type" "fmul") (eq_attr "mode" "SF"))    7 0)
259 ;; (define_function_unit "mult"     1 1 (and (eq_attr "type" "fmul") (eq_attr "mode" "DF"))    8 0)
260 ;;   
261 ;; (define_function_unit "divide"   1 1 (and (eq_attr "type" "fdiv") (eq_attr "mode" "SF"))   23 0)
262 ;; (define_function_unit "divide"   1 1 (and (eq_attr "type" "fdiv") (eq_attr "mode" "DF"))   36 0)
263 ;; 
264 ;; (define_function_unit "sqrt"     1 1 (and (eq_attr "type" "fsqrt") (eq_attr "mode" "SF"))  54 0)
265 ;; (define_function_unit "sqrt"     1 1 (and (eq_attr "type" "fsqrt") (eq_attr "mode" "DF")) 112 0)
266
267 \f
268 ;;
269 ;;  ....................
270 ;;
271 ;;      ADDITION
272 ;;
273 ;;  ....................
274 ;;
275
276 (define_insn "adddf3"
277   [(set (match_operand:DF 0 "register_operand" "=f")
278         (plus:DF (match_operand:DF 1 "register_operand" "f")
279                  (match_operand:DF 2 "register_operand" "f")))]
280   "TARGET_HARD_FLOAT"
281   "add.d\\t%0,%1,%2"
282   [(set_attr "type"     "fadd")
283    (set_attr "mode"     "DF")
284    (set_attr "length"   "1")])
285
286 (define_insn "addsf3"
287   [(set (match_operand:SF 0 "register_operand" "=f")
288         (plus:SF (match_operand:SF 1 "register_operand" "f")
289                  (match_operand:SF 2 "register_operand" "f")))]
290   "TARGET_HARD_FLOAT"
291   "add.s\\t%0,%1,%2"
292   [(set_attr "type"     "fadd")
293    (set_attr "mode"     "SF")
294    (set_attr "length"   "1")])
295
296 (define_expand "addsi3"
297   [(set (match_operand:SI 0 "register_operand" "=d")
298         (plus:SI (match_operand:SI 1 "reg_or_0_operand" "dJ")
299                  (match_operand:SI 2 "arith_operand" "dI")))]
300   ""
301   "
302 {
303   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) == -32768)
304     operands[2] = force_reg (SImode, operands[2]);
305 }")
306
307 (define_insn "addsi3_internal"
308   [(set (match_operand:SI 0 "register_operand" "=d")
309         (plus:SI (match_operand:SI 1 "reg_or_0_operand" "dJ")
310                  (match_operand:SI 2 "arith_operand" "dI")))]
311   "GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != -32768"
312   "*
313 {
314   return (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
315     ? \"subu\\t%0,%z1,%n2\"
316     : \"addu\\t%0,%z1,%2\";
317 }"
318   [(set_attr "type"     "arith")
319    (set_attr "mode"     "SI")
320    (set_attr "length"   "1")])
321
322 (define_expand "adddi3"
323   [(parallel [(set (match_operand:DI 0 "register_operand" "")
324                    (plus:DI (match_operand:DI 1 "register_operand" "")
325                             (match_operand:DI 2 "arith_operand" "")))
326               (clobber (match_dup 3))])]
327   "!TARGET_DEBUG_G_MODE"
328   "
329 {
330   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) == -32768)
331     operands[2] = force_reg (SImode, operands[2]);
332
333   operands[3] = gen_reg_rtx (SImode);
334 }")
335
336 (define_insn "adddi3_internal_1"
337   [(set (match_operand:DI 0 "register_operand" "=d,&d")
338         (plus:DI (match_operand:DI 1 "register_operand" "0,d")
339                  (match_operand:DI 2 "register_operand" "d,d")))
340    (clobber (match_operand:SI 3 "register_operand" "=d,d"))]
341   "!TARGET_DEBUG_G_MODE"
342   "*
343 {
344   return (REGNO (operands[0]) == REGNO (operands[1])
345           && REGNO (operands[0]) == REGNO (operands[2]))
346     ? \"srl\\t%3,%L0,31\;sll\\t%M0,%M0,1\;sll\\t%L0,%L1,1\;addu\\t%M0,%M0,%3\"
347     : \"addu\\t%L0,%L1,%L2\;sltu\\t%3,%L0,%L2\;addu\\t%M0,%M1,%M2\;addu\\t%M0,%M0,%3\";
348 }"
349   [(set_attr "type"     "darith")
350    (set_attr "mode"     "DI")
351    (set_attr "length"   "4")])
352
353 (define_split
354   [(set (match_operand:DI 0 "register_operand" "")
355         (plus:DI (match_operand:DI 1 "register_operand" "")
356                  (match_operand:DI 2 "register_operand" "")))
357    (clobber (match_operand:SI 3 "register_operand" ""))]
358   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
359    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
360    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
361    && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))
362    && (REGNO (operands[0]) != REGNO (operands[1])
363        || REGNO (operands[0]) != REGNO (operands[2]))"
364
365   [(set (subreg:SI (match_dup 0) 0)
366         (plus:SI (subreg:SI (match_dup 1) 0)
367                  (subreg:SI (match_dup 2) 0)))
368
369    (set (match_dup 3)
370         (ltu:SI (subreg:SI (match_dup 0) 0)
371                 (subreg:SI (match_dup 2) 0)))
372
373    (set (subreg:SI (match_dup 0) 1)
374         (plus:SI (subreg:SI (match_dup 1) 1)
375                  (subreg:SI (match_dup 2) 1)))
376
377    (set (subreg:SI (match_dup 0) 1)
378         (plus:SI (subreg:SI (match_dup 0) 1)
379                  (match_dup 3)))]
380   "")
381
382 (define_split
383   [(set (match_operand:DI 0 "register_operand" "")
384         (plus:DI (match_operand:DI 1 "register_operand" "")
385                  (match_operand:DI 2 "register_operand" "")))
386    (clobber (match_operand:SI 3 "register_operand" ""))]
387   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
388    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
389    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
390    && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))
391    && (REGNO (operands[0]) != REGNO (operands[1])
392        || REGNO (operands[0]) != REGNO (operands[2]))"
393
394   [(set (subreg:SI (match_dup 0) 1)
395         (plus:SI (subreg:SI (match_dup 1) 1)
396                  (subreg:SI (match_dup 2) 1)))
397
398    (set (match_dup 3)
399         (ltu:SI (subreg:SI (match_dup 0) 1)
400                 (subreg:SI (match_dup 2) 1)))
401
402    (set (subreg:SI (match_dup 0) 0)
403         (plus:SI (subreg:SI (match_dup 1) 0)
404                  (subreg:SI (match_dup 2) 0)))
405
406    (set (subreg:SI (match_dup 0) 0)
407         (plus:SI (subreg:SI (match_dup 0) 0)
408                  (match_dup 3)))]
409   "")
410
411 (define_insn "adddi3_internal_2"
412   [(set (match_operand:DI 0 "register_operand" "=d,d,d")
413         (plus:DI (match_operand:DI 1 "register_operand" "%d,%d,%d")
414                  (match_operand:DI 2 "small_int" "P,J,N")))
415    (clobber (match_operand:SI 3 "register_operand" "=d,d,d"))]
416   "!TARGET_DEBUG_G_MODE && INTVAL (operands[2]) != -32768"
417   "@
418    addu\\t%L0,%L1,%2\;sltu\\t%3,%L0,%2\;addu\\t%M0,%M1,%3
419    move\\t%L0,%L1\;move\\t%M0,%M1
420    subu\\t%L0,%L1,%n2\;sltu\\t%3,%L0,%2\;subu\\t%M0,%M1,1\;addu\\t%M0,%M0,%3"
421   [(set_attr "type"     "darith")
422    (set_attr "mode"     "DI")
423    (set_attr "length"   "3,2,4")])
424
425 (define_split
426   [(set (match_operand:DI 0 "register_operand" "")
427         (plus:DI (match_operand:DI 1 "register_operand" "")
428                  (match_operand:DI 2 "small_int" "")))
429    (clobber (match_operand:SI 3 "register_operand" "=d"))]
430   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
431    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
432    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
433    && INTVAL (operands[2]) > 0"
434
435   [(set (subreg:SI (match_dup 0) 0)
436         (plus:SI (subreg:SI (match_dup 1) 0)
437                  (match_dup 2)))
438
439    (set (match_dup 3)
440         (ltu:SI (subreg:SI (match_dup 0) 0)
441                 (match_dup 2)))
442
443    (set (subreg:SI (match_dup 0) 1)
444         (plus:SI (subreg:SI (match_dup 1) 1)
445                  (match_dup 3)))]
446   "")
447
448 (define_split
449   [(set (match_operand:DI 0 "register_operand" "")
450         (plus:DI (match_operand:DI 1 "register_operand" "")
451                  (match_operand:DI 2 "small_int" "")))
452    (clobber (match_operand:SI 3 "register_operand" "=d"))]
453   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
454    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
455    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
456    && INTVAL (operands[2]) > 0"
457
458   [(set (subreg:SI (match_dup 0) 1)
459         (plus:SI (subreg:SI (match_dup 1) 1)
460                  (match_dup 2)))
461
462    (set (match_dup 3)
463         (ltu:SI (subreg:SI (match_dup 0) 1)
464                 (match_dup 2)))
465
466    (set (subreg:SI (match_dup 0) 0)
467         (plus:SI (subreg:SI (match_dup 1) 0)
468                  (match_dup 3)))]
469   "")
470 \f
471 ;;
472 ;;  ....................
473 ;;
474 ;;      SUBTRACTION
475 ;;
476 ;;  ....................
477 ;;
478
479 (define_insn "subdf3"
480   [(set (match_operand:DF 0 "register_operand" "=f")
481         (minus:DF (match_operand:DF 1 "register_operand" "f")
482                   (match_operand:DF 2 "register_operand" "f")))]
483   "TARGET_HARD_FLOAT"
484   "sub.d\\t%0,%1,%2"
485   [(set_attr "type"     "fadd")
486    (set_attr "mode"     "DF")
487    (set_attr "length"   "1")])
488
489 (define_insn "subsf3"
490   [(set (match_operand:SF 0 "register_operand" "=f")
491         (minus:SF (match_operand:SF 1 "register_operand" "f")
492                   (match_operand:SF 2 "register_operand" "f")))]
493   "TARGET_HARD_FLOAT"
494   "sub.s\\t%0,%1,%2"
495   [(set_attr "type"     "fadd")
496    (set_attr "mode"     "SF")
497    (set_attr "length"   "1")])
498
499 (define_expand "subsi3"
500   [(set (match_operand:SI 0 "register_operand" "=d")
501         (minus:SI (match_operand:SI 1 "reg_or_0_operand" "dJ")
502                   (match_operand:SI 2 "arith_operand" "dI")))]
503   ""
504   "
505 {
506   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) == -32768)
507     operands[2] = force_reg (SImode, operands[2]);
508 }")
509
510 (define_insn "subsi3_internal"
511   [(set (match_operand:SI 0 "register_operand" "=d")
512         (minus:SI (match_operand:SI 1 "reg_or_0_operand" "dJ")
513                   (match_operand:SI 2 "arith_operand" "dI")))]
514   "GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != -32768"
515   "*
516 {
517   return (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
518     ? \"addu\\t%0,%z1,%n2\"
519     : \"subu\\t%0,%z1,%2\";
520 }"
521   [(set_attr "type"     "arith")
522    (set_attr "mode"     "SI")
523    (set_attr "length"   "1")])
524
525 (define_expand "subdi3"
526   [(parallel [(set (match_operand:DI 0 "register_operand" "=d")
527                    (minus:DI (match_operand:DI 1 "register_operand" "d")
528                              (match_operand:DI 2 "register_operand" "d")))
529               (clobber (match_dup 3))])]
530   "!TARGET_DEBUG_G_MODE"
531   "operands[3] = gen_reg_rtx (SImode);")
532
533 (define_insn "subdi3_internal"
534   [(set (match_operand:DI 0 "register_operand" "=d")
535         (minus:DI (match_operand:DI 1 "register_operand" "d")
536                   (match_operand:DI 2 "register_operand" "d")))
537    (clobber (match_operand:SI 3 "register_operand" "=d"))]
538   "!TARGET_DEBUG_G_MODE"
539   "sltu\\t%3,%L1,%L2\;subu\\t%L0,%L1,%L2\;subu\\t%M0,%M1,%M2\;subu\\t%M0,%M0,%3"
540   [(set_attr "type"     "darith")
541    (set_attr "mode"     "DI")
542    (set_attr "length"   "4")])
543
544 (define_split
545   [(set (match_operand:DI 0 "register_operand" "")
546         (minus:DI (match_operand:DI 1 "register_operand" "")
547                   (match_operand:DI 2 "register_operand" "")))
548    (clobber (match_operand:SI 3 "register_operand" ""))]
549   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
550    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
551    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
552    && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))"
553
554   [(set (match_dup 3)
555         (ltu:SI (subreg:SI (match_dup 1) 0)
556                 (subreg:SI (match_dup 2) 0)))
557
558    (set (subreg:SI (match_dup 0) 0)
559         (minus:SI (subreg:SI (match_dup 1) 0)
560                   (subreg:SI (match_dup 2) 0)))
561
562    (set (subreg:SI (match_dup 0) 1)
563         (minus:SI (subreg:SI (match_dup 1) 1)
564                   (subreg:SI (match_dup 2) 1)))
565
566    (set (subreg:SI (match_dup 0) 1)
567         (minus:SI (subreg:SI (match_dup 0) 1)
568                   (match_dup 3)))]
569   "")
570
571 (define_split
572   [(set (match_operand:DI 0 "register_operand" "")
573         (minus:DI (match_operand:DI 1 "register_operand" "")
574                   (match_operand:DI 2 "register_operand" "")))
575    (clobber (match_operand:SI 3 "register_operand" ""))]
576   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
577    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
578    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
579    && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))"
580
581   [(set (match_dup 3)
582         (ltu:SI (subreg:SI (match_dup 1) 1)
583                 (subreg:SI (match_dup 2) 1)))
584
585    (set (subreg:SI (match_dup 0) 1)
586         (minus:SI (subreg:SI (match_dup 1) 1)
587                   (subreg:SI (match_dup 2) 1)))
588
589    (set (subreg:SI (match_dup 0) 0)
590         (minus:SI (subreg:SI (match_dup 1) 0)
591                   (subreg:SI (match_dup 2) 0)))
592
593    (set (subreg:SI (match_dup 0) 0)
594         (minus:SI (subreg:SI (match_dup 0) 0)
595                   (match_dup 3)))]
596   "")
597
598 (define_insn "subdi3_internal_2"
599   [(set (match_operand:DI 0 "register_operand" "=d,d,d")
600         (minus:DI (match_operand:DI 1 "register_operand" "d,d,d")
601                   (match_operand:DI 2 "small_int" "P,J,N")))
602    (clobber (match_operand:SI 3 "register_operand" "=d,d,d"))]
603   "!TARGET_DEBUG_G_MODE && INTVAL (operands[2]) != -32768"
604   "@
605    sltu\\t%3,%L1,%2\;subu\\t%L0,%L1,%2\;subu\\t%M0,%M1,%3
606    move\\t%L0,%L1\;move\\t%M0,%M1
607    sltu\\t%3,%L1,%2\;subu\\t%L0,%L1,%2\;subu\\t%M0,%M1,1\;subu\\t%M0,%M0,%3"
608   [(set_attr "type"     "darith")
609    (set_attr "mode"     "DI")
610    (set_attr "length"   "3,2,4")])
611
612 (define_split
613   [(set (match_operand:DI 0 "register_operand" "")
614         (minus:DI (match_operand:DI 1 "register_operand" "")
615                   (match_operand:DI 2 "small_int" "")))
616    (clobber (match_operand:SI 3 "register_operand" ""))]
617   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
618    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
619    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
620    && INTVAL (operands[2]) > 0"
621
622   [(set (match_dup 3)
623         (ltu:SI (subreg:SI (match_dup 1) 0)
624                 (match_dup 2)))
625
626    (set (subreg:SI (match_dup 0) 0)
627         (minus:SI (subreg:SI (match_dup 1) 0)
628                   (match_dup 2)))
629
630    (set (subreg:SI (match_dup 0) 1)
631         (minus:SI (subreg:SI (match_dup 1) 1)
632                   (match_dup 3)))]
633   "")
634
635 (define_split
636   [(set (match_operand:DI 0 "register_operand" "")
637         (minus:DI (match_operand:DI 1 "register_operand" "")
638                   (match_operand:DI 2 "small_int" "")))
639    (clobber (match_operand:SI 3 "register_operand" ""))]
640   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
641    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
642    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
643    && INTVAL (operands[2]) > 0"
644
645   [(set (match_dup 3)
646         (ltu:SI (subreg:SI (match_dup 1) 1)
647                 (match_dup 2)))
648
649    (set (subreg:SI (match_dup 0) 1)
650         (minus:SI (subreg:SI (match_dup 1) 1)
651                   (match_dup 2)))
652
653    (set (subreg:SI (match_dup 0) 0)
654         (minus:SI (subreg:SI (match_dup 1) 0)
655                   (match_dup 3)))]
656   "")
657
658 \f
659 ;;
660 ;;  ....................
661 ;;
662 ;;      MULTIPLICATION
663 ;;
664 ;;  ....................
665 ;;
666
667 (define_insn "muldf3"
668   [(set (match_operand:DF 0 "register_operand" "=f")
669         (mult:DF (match_operand:DF 1 "register_operand" "f")
670                  (match_operand:DF 2 "register_operand" "f")))]
671   "TARGET_HARD_FLOAT"
672   "mul.d\\t%0,%1,%2"
673   [(set_attr "type"     "fmul")
674    (set_attr "mode"     "DF")
675    (set_attr "length"   "1")])
676
677 (define_insn "mulsf3"
678   [(set (match_operand:SF 0 "register_operand" "=f")
679         (mult:SF (match_operand:SF 1 "register_operand" "f")
680                  (match_operand:SF 2 "register_operand" "f")))]
681   "TARGET_HARD_FLOAT"
682   "mul.s\\t%0,%1,%2"
683   [(set_attr "type"     "fmul")
684    (set_attr "mode"     "SF")
685    (set_attr "length"   "1")])
686
687 (define_insn "mulsi3"
688   [(set (match_operand:SI 0 "register_operand" "=d")
689         (mult:SI (match_operand:SI 1 "register_operand" "d")
690                  (match_operand:SI 2 "register_operand" "d")))
691    (clobber (reg:SI 64))
692    (clobber (reg:SI 65))]
693   ""
694   "*
695 {
696   rtx xoperands[10];
697
698   xoperands[0] = operands[0];
699   xoperands[1] = gen_rtx (REG, SImode, LO_REGNUM);
700
701   output_asm_insn (\"mult\\t%1,%2\", operands);
702   output_asm_insn (mips_move_1word (xoperands, insn), xoperands);
703   return \"\";
704 }"
705   [(set_attr "type"     "imul")
706    (set_attr "mode"     "SI")
707    (set_attr "length"   "3")])          ;; mult + mflo + delay
708
709 (define_split
710   [(set (match_operand:SI 0 "register_operand" "")
711         (mult:SI (match_operand:SI 1 "register_operand" "")
712                  (match_operand:SI 2 "register_operand" "")))
713    (clobber (reg:SI 64))
714    (clobber (reg:SI 65))]
715   "!TARGET_DEBUG_D_MODE"
716   [(parallel [(set (reg:SI 65)          ;; low register
717                    (mult:SI (match_dup 1)
718                             (match_dup 2)))
719               (clobber (reg:SI 64))])
720    (set (match_dup 0)
721         (reg:SI 65))]
722   "")
723
724 (define_insn "mulsi3_internal"
725   [(set (reg:SI 65)             ;; low register
726         (mult:SI (match_operand:SI 0 "register_operand" "d")
727                  (match_operand:SI 1 "register_operand" "d")))
728    (clobber (reg:SI 64))]
729   ""
730   "mult\\t%0,%1"
731   [(set_attr "type"     "imul")
732    (set_attr "mode"     "SI")
733    (set_attr "length"   "1")])
734
735 (define_insn "mulsidi3"
736   [(set (match_operand:DI 0 "register_operand" "=d")
737         (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "d"))
738                  (sign_extend:DI (match_operand:SI 2 "register_operand" "d"))))
739    (clobber (reg:DI 64))]
740   ""
741   "*
742 {
743   rtx xoperands[10];
744
745   xoperands[0] = operands[0];
746   xoperands[1] = gen_rtx (REG, DImode, MD_REG_FIRST);
747
748   output_asm_insn (\"mult\\t%1,%2\", operands);
749   output_asm_insn (mips_move_2words (xoperands, insn), xoperands);
750   return \"\";
751 }"
752   [(set_attr "type"     "imul")
753    (set_attr "mode"     "SI")
754    (set_attr "length"   "4")])          ;; mult + mflo + mfhi + delay
755
756 (define_insn "umulsidi3"
757   [(set (match_operand:DI 0 "register_operand" "=d")
758         (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "d"))
759                  (zero_extend:DI (match_operand:SI 2 "register_operand" "d"))))
760    (clobber (reg:DI 64))]
761   ""
762   "*
763 {
764   rtx xoperands[10];
765
766   xoperands[0] = operands[0];
767   xoperands[1] = gen_rtx (REG, DImode, MD_REG_FIRST);
768
769   output_asm_insn (\"multu\\t%1,%2\", operands);
770   output_asm_insn (mips_move_2words (xoperands, insn), xoperands);
771   return \"\";
772 }"
773   [(set_attr "type"     "imul")
774    (set_attr "mode"     "SI")
775    (set_attr "length"   "4")])          ;; mult + mflo + mfhi + delay
776
777 \f
778 ;;
779 ;;  ....................
780 ;;
781 ;;      DIVISION and REMAINDER
782 ;;
783 ;;  ....................
784 ;;
785
786 (define_insn "divdf3"
787   [(set (match_operand:DF 0 "register_operand" "=f")
788         (div:DF (match_operand:DF 1 "register_operand" "f")
789                 (match_operand:DF 2 "register_operand" "f")))]
790   "TARGET_HARD_FLOAT"
791   "div.d\\t%0,%1,%2"
792   [(set_attr "type"     "fdiv")
793    (set_attr "mode"     "DF")
794    (set_attr "length"   "1")])
795
796 (define_insn "divsf3"
797   [(set (match_operand:SF 0 "register_operand" "=f")
798         (div:SF (match_operand:SF 1 "register_operand" "f")
799                 (match_operand:SF 2 "register_operand" "f")))]
800   "TARGET_HARD_FLOAT"
801   "div.s\\t%0,%1,%2"
802   [(set_attr "type"     "fdiv")
803    (set_attr "mode"     "SF")
804    (set_attr "length"   "1")])
805
806 ;; If optimizing, prefer the divmod functions over separate div and
807 ;; mod functions, since this will allow using one instruction for both
808 ;; the quotient and remainder.  At present, the divmod is not moved out
809 ;; of loops if it is constant within the loop, so allow -mdebugc to
810 ;; use the old method of doing things.
811
812 ;; 64 is the multiply/divide hi register
813 ;; 65 is the multiply/divide lo register
814
815 (define_insn "divmodsi4"
816   [(set (match_operand:SI 0 "register_operand" "=d")
817         (div:SI (match_operand:SI 1 "register_operand" "d")
818                 (match_operand:SI 2 "register_operand" "d")))
819    (set (match_operand:SI 3 "register_operand" "=d")
820         (mod:SI (match_dup 1)
821                 (match_dup 2)))
822    (clobber (reg:SI 64))
823    (clobber (reg:SI 65))]
824   "optimize"
825   "*
826 {
827   if (find_reg_note (insn, REG_UNUSED, operands[3]))
828     return \"div\\t%0,%1,%2\";
829
830   if (find_reg_note (insn, REG_UNUSED, operands[0]))
831     return \"rem\\t%3,%1,%2\";
832
833   return \"div\\t%0,%1,%2\;mfhi\\t%3\";
834 }"
835   [(set_attr "type"     "idiv")
836    (set_attr "mode"     "SI")
837    (set_attr "length"   "13")])         ;; various tests for dividing by 0 and such
838
839 (define_insn "udivmodsi4"
840   [(set (match_operand:SI 0 "register_operand" "=d")
841         (udiv:SI (match_operand:SI 1 "register_operand" "d")
842                  (match_operand:SI 2 "register_operand" "d")))
843    (set (match_operand:SI 3 "register_operand" "=d")
844         (umod:SI (match_dup 1)
845                  (match_dup 2)))
846    (clobber (reg:SI 64))
847    (clobber (reg:SI 65))]
848   "optimize"
849   "*
850 {
851   if (find_reg_note (insn, REG_UNUSED, operands[3]))
852     return \"divu\\t%0,%1,%2\";
853
854   if (find_reg_note (insn, REG_UNUSED, operands[0]))
855     return \"remu\\t%3,%1,%2\";
856
857   return \"divu\\t%0,%1,%2\;mfhi\\t%3\";
858 }"
859   [(set_attr "type"     "idiv")
860    (set_attr "mode"     "SI")
861    (set_attr "length"   "13")])         ;; various tests for dividing by 0 and such
862
863 (define_insn "divsi3"
864   [(set (match_operand:SI 0 "register_operand" "=d")
865         (div:SI (match_operand:SI 1 "register_operand" "d")
866                 (match_operand:SI 2 "register_operand" "d")))
867    (clobber (reg:SI 64))
868    (clobber (reg:SI 65))]
869   "!optimize"
870   "div\\t%0,%1,%2"
871   [(set_attr "type"     "idiv")
872    (set_attr "mode"     "SI")
873    (set_attr "length"   "13")])         ;; various tests for dividing by 0 and such
874
875 (define_insn "modsi3"
876   [(set (match_operand:SI 0 "register_operand" "=d")
877         (mod:SI (match_operand:SI 1 "register_operand" "d")
878                 (match_operand:SI 2 "register_operand" "d")))
879    (clobber (reg:SI 64))
880    (clobber (reg:SI 65))]
881   "!optimize"
882   "rem\\t%0,%1,%2"
883   [(set_attr "type"     "idiv")
884    (set_attr "mode"     "SI")
885    (set_attr "length"   "14")])         ;; various tests for dividing by 0 and such
886
887 (define_insn "udivsi3"
888   [(set (match_operand:SI 0 "register_operand" "=d")
889         (udiv:SI (match_operand:SI 1 "register_operand" "d")
890                  (match_operand:SI 2 "register_operand" "d")))
891    (clobber (reg:SI 64))
892    (clobber (reg:SI 65))]
893   "!optimize"
894   "divu\\t%0,%1,%2"
895   [(set_attr "type"     "idiv")
896    (set_attr "mode"     "SI")
897    (set_attr "length"   "14")])         ;; various tests for dividing by 0 and such
898
899 (define_insn "umodsi3"
900   [(set (match_operand:SI 0 "register_operand" "=d")
901         (umod:SI (match_operand:SI 1 "register_operand" "d")
902                  (match_operand:SI 2 "register_operand" "d")))
903    (clobber (reg:SI 64))
904    (clobber (reg:SI 65))]
905   "!optimize"
906   "remu\\t%0,%1,%2"
907   [(set_attr "type"     "idiv")
908    (set_attr "mode"     "SI")
909    (set_attr "length"   "14")])         ;; various tests for dividing by 0 and such
910
911 \f
912 ;;
913 ;;  ....................
914 ;;
915 ;;      SQUARE ROOT
916 ;;
917 ;;  ....................
918
919 (define_insn "sqrtdf2"
920   [(set (match_operand:DF 0 "register_operand" "=f")
921         (sqrt:DF (match_operand:DF 1 "register_operand" "f")))]
922   "TARGET_HARD_FLOAT && HAVE_SQRT_P()"
923   "sqrt.d\\t%0,%1"
924   [(set_attr "type"     "fabs")
925    (set_attr "mode"     "DF")
926    (set_attr "length"   "1")])
927
928 (define_insn "sqrtsf2"
929   [(set (match_operand:SF 0 "register_operand" "=f")
930         (sqrt:SF (match_operand:SF 1 "register_operand" "f")))]
931   "TARGET_HARD_FLOAT && HAVE_SQRT_P()"
932   "sqrt.s\\t%0,%1"
933   [(set_attr "type"     "fabs")
934    (set_attr "mode"     "SF")
935    (set_attr "length"   "1")])
936
937 \f
938 ;;
939 ;;  ....................
940 ;;
941 ;;      ABSOLUTE VALUE
942 ;;
943 ;;  ....................
944
945 ;; Do not use the integer abs macro instruction, since that signals an
946 ;; exception on -2147483648 (sigh).
947
948 (define_insn "abssi2"
949   [(set (match_operand:SI 0 "register_operand" "=d")
950         (abs:SI (match_operand:SI 1 "register_operand" "d")))]
951   ""
952   "*
953 {
954   dslots_jump_total++;
955   dslots_jump_filled++;
956   operands[2] = const0_rtx;
957
958   return (REGNO (operands[0]) == REGNO (operands[1]))
959                 ? \"bgez\\t%1,1f%#\\n\\tsubu\\t%0,%z2,%0\\n1:\"
960                 : \"%(bgez\\t%1,1f\\n\\tmove\\t%0,%1\\n\\tsubu\\t%0,%z2,%0\\n1:%)\";
961 }"
962   [(set_attr "type"     "multi")
963    (set_attr "mode"     "SI")
964    (set_attr "length"   "3")])
965
966 (define_insn "absdf2"
967   [(set (match_operand:DF 0 "register_operand" "=f")
968         (abs:DF (match_operand:DF 1 "register_operand" "f")))]
969   "TARGET_HARD_FLOAT"
970   "abs.d\\t%0,%1"
971   [(set_attr "type"     "fabs")
972    (set_attr "mode"     "DF")
973    (set_attr "length"   "1")])
974
975 (define_insn "abssf2"
976   [(set (match_operand:SF 0 "register_operand" "=f")
977         (abs:SF (match_operand:SF 1 "register_operand" "f")))]
978   "TARGET_HARD_FLOAT"
979   "abs.s\\t%0,%1"
980   [(set_attr "type"     "fabs")
981    (set_attr "mode"     "SF")
982    (set_attr "length"   "1")])
983
984 \f
985 ;;
986 ;;  ....................
987 ;;
988 ;;      FIND FIRST BIT INSTRUCTION
989 ;;
990 ;;  ....................
991 ;;
992
993 (define_insn "ffssi2"
994   [(set (match_operand:SI 0 "register_operand" "=&d")
995         (ffs:SI (match_operand:SI 1 "register_operand" "d")))
996    (clobber (match_scratch:SI 2 "=&d"))
997    (clobber (match_scratch:SI 3 "=&d"))]
998   ""
999   "*
1000 {
1001   dslots_jump_total += 2;
1002   dslots_jump_filled += 2;
1003   operands[4] = const0_rtx;
1004
1005   if (optimize && find_reg_note (insn, REG_DEAD, operands[1]))
1006     return \"%(\\
1007 move\\t%0,%z4\\n\\
1008 \\tbeq\\t%1,%z4,2f\\n\\
1009 1:\\tand\\t%2,%1,0x0001\\n\\
1010 \\taddu\\t%0,%0,1\\n\\
1011 \\tbeq\\t%2,%z4,1b\\n\\
1012 \\tsrl\\t%1,%1,1\\n\\
1013 2:%)\";
1014
1015   return \"%(\\
1016 move\\t%0,%z4\\n\\
1017 \\tmove\\t%3,%1\\n\\
1018 \\tbeq\\t%3,%z4,2f\\n\\
1019 1:\\tand\\t%2,%3,0x0001\\n\\
1020 \\taddu\\t%0,%0,1\\n\\
1021 \\tbeq\\t%2,%z4,1b\\n\\
1022 \\tsrl\\t%3,%3,1\\n\\
1023 2:%)\";
1024 }"
1025   [(set_attr "type"     "multi")
1026    (set_attr "mode"     "SI")
1027    (set_attr "length"   "6")])
1028
1029 \f
1030 ;;
1031 ;;  ....................
1032 ;;
1033 ;;      NEGATION and ONE'S COMPLEMENT
1034 ;;
1035 ;;  ....................
1036
1037 (define_insn "negsi2"
1038   [(set (match_operand:SI 0 "register_operand" "=d")
1039         (neg:SI (match_operand:SI 1 "register_operand" "d")))]
1040   ""
1041   "*
1042 {
1043   operands[2] = const0_rtx;
1044   return \"subu\\t%0,%z2,%1\";
1045 }"
1046   [(set_attr "type"     "arith")
1047    (set_attr "mode"     "SI")
1048    (set_attr "length"   "1")])
1049
1050 (define_expand "negdi2"
1051   [(parallel [(set (match_operand:DI 0 "register_operand" "=d")
1052                    (neg:DI (match_operand:DI 1 "register_operand" "d")))
1053               (clobber (match_dup 2))])]
1054   "!TARGET_DEBUG_G_MODE"
1055   "operands[2] = gen_reg_rtx (SImode);")
1056
1057 (define_insn "negdi2_internal"
1058   [(set (match_operand:DI 0 "register_operand" "=d")
1059         (neg:DI (match_operand:DI 1 "register_operand" "d")))
1060    (clobber (match_operand:SI 2 "register_operand" "=d"))]
1061   "!TARGET_DEBUG_G_MODE"
1062   "*
1063 {
1064   operands[3] = const0_rtx;
1065   return \"subu\\t%L0,%z3,%L1\;subu\\t%M0,%z3,%M1\;sltu\\t%2,%z3,%L0\;subu\\t%M0,%M0,%2\";
1066 }"
1067   [(set_attr "type"     "darith")
1068    (set_attr "mode"     "DI")
1069    (set_attr "length"   "4")])
1070
1071 (define_insn "negdf2"
1072   [(set (match_operand:DF 0 "register_operand" "=f")
1073         (neg:DF (match_operand:DF 1 "register_operand" "f")))]
1074   "TARGET_HARD_FLOAT"
1075   "neg.d\\t%0,%1"
1076   [(set_attr "type"     "fneg")
1077    (set_attr "mode"     "DF")
1078    (set_attr "length"   "1")])
1079
1080 (define_insn "negsf2"
1081   [(set (match_operand:SF 0 "register_operand" "=f")
1082         (neg:SF (match_operand:SF 1 "register_operand" "f")))]
1083   "TARGET_HARD_FLOAT"
1084   "neg.s\\t%0,%1"
1085   [(set_attr "type"     "fneg")
1086    (set_attr "mode"     "SF")
1087    (set_attr "length"   "1")])
1088
1089 (define_insn "one_cmplsi2"
1090   [(set (match_operand:SI 0 "register_operand" "=d")
1091         (not:SI (match_operand:SI 1 "register_operand" "d")))]
1092   ""
1093   "*
1094 {
1095   operands[2] = const0_rtx;
1096   return \"nor\\t%0,%z2,%1\";
1097 }"
1098   [(set_attr "type"     "arith")
1099    (set_attr "mode"     "SI")
1100    (set_attr "length"   "1")])
1101
1102 (define_insn "one_cmpldi2"
1103   [(set (match_operand:DI 0 "register_operand" "=d")
1104         (not:SI (match_operand:DI 1 "register_operand" "d")))]
1105   ""
1106   "*
1107 {
1108   operands[2] = const0_rtx;
1109   return \"nor\\t%M0,%z2,%M1\;nor\\t%L0,%z2,%L1\";
1110 }"
1111   [(set_attr "type"     "darith")
1112    (set_attr "mode"     "DI")
1113    (set_attr "length"   "2")])
1114
1115 (define_split
1116   [(set (match_operand:DI 0 "register_operand" "")
1117         (not:DI (match_operand:DI 1 "register_operand" "")))]
1118   "reload_completed && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
1119    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
1120    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))"
1121
1122   [(set (subreg:SI (match_dup 0) 0) (not:SI (subreg:SI (match_dup 1) 0)))
1123    (set (subreg:SI (match_dup 0) 1) (not:SI (subreg:SI (match_dup 1) 1)))]
1124   "")
1125
1126 ;; Simple hack to recognize the "nor" instruction on the MIPS
1127 ;; This must appear before the normal or patterns, so that the
1128 ;; combiner will correctly fold things.
1129
1130 (define_insn "norsi3"
1131   [(set (match_operand:SI 0 "register_operand" "=d")
1132         (not:SI (ior:SI (match_operand:SI 1 "reg_or_0_operand" "dJ")
1133                         (match_operand:SI 2 "reg_or_0_operand" "dJ"))))]
1134   ""
1135   "nor\\t%0,%z1,%z2"
1136   [(set_attr "type"     "arith")
1137    (set_attr "mode"     "SI")
1138    (set_attr "length"   "1")])
1139
1140 (define_insn "nordi3"
1141   [(set (match_operand:DI 0 "register_operand" "=d")
1142         (not:DI (ior:DI (match_operand:DI 1 "register_operand" "d")
1143                         (match_operand:DI 2 "register_operand" "d"))))]
1144   ""
1145   "nor\\t%M0,%M1,%M2\;nor\\t%L0,%L1,%L2"
1146   [(set_attr "type"     "darith")
1147    (set_attr "mode"     "DI")
1148    (set_attr "length"   "2")])
1149
1150 (define_split
1151   [(set (match_operand:DI 0 "register_operand" "")
1152         (not:DI (ior:DI (match_operand:DI 1 "register_operand" "")
1153                         (match_operand:DI 2 "register_operand" ""))))]
1154   "reload_completed && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
1155    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
1156    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
1157    && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))"
1158
1159   [(set (subreg:SI (match_dup 0) 0) (not:SI (ior:SI (subreg:SI (match_dup 1) 0) (subreg:SI (match_dup 2) 0))))
1160    (set (subreg:SI (match_dup 0) 1) (not:SI (ior:SI (subreg:SI (match_dup 1) 1) (subreg:SI (match_dup 2) 1))))]
1161   "")
1162
1163 \f
1164 ;;
1165 ;;  ....................
1166 ;;
1167 ;;      LOGICAL
1168 ;;
1169 ;;  ....................
1170 ;;
1171
1172 (define_insn "andsi3"
1173   [(set (match_operand:SI 0 "register_operand" "=d,d")
1174         (and:SI (match_operand:SI 1 "uns_arith_operand" "%d,d")
1175                 (match_operand:SI 2 "uns_arith_operand" "d,K")))]
1176   ""
1177   "@
1178    and\\t%0,%1,%2
1179    andi\\t%0,%1,%x2"
1180   [(set_attr "type"     "arith")
1181    (set_attr "mode"     "SI")
1182    (set_attr "length"   "1")])
1183
1184 (define_insn "anddi3"
1185   [(set (match_operand:DI 0 "register_operand" "=d")
1186         (and:DI (match_operand:DI 1 "register_operand" "d")
1187                 (match_operand:DI 2 "register_operand" "d")))]
1188   "!TARGET_DEBUG_G_MODE"
1189   "and\\t%M0,%M1,%M2\;and\\t%L0,%L1,%L2"
1190   [(set_attr "type"     "darith")
1191    (set_attr "mode"     "DI")
1192    (set_attr "length"   "2")])
1193
1194 (define_split
1195   [(set (match_operand:DI 0 "register_operand" "")
1196         (and:DI (match_operand:DI 1 "register_operand" "")
1197                 (match_operand:DI 2 "register_operand" "")))]
1198   "reload_completed && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
1199    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
1200    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
1201    && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))"
1202
1203   [(set (subreg:SI (match_dup 0) 0) (and:SI (subreg:SI (match_dup 1) 0) (subreg:SI (match_dup 2) 0)))
1204    (set (subreg:SI (match_dup 0) 1) (and:SI (subreg:SI (match_dup 1) 1) (subreg:SI (match_dup 2) 1)))]
1205   "")
1206
1207 (define_insn "iorsi3"
1208   [(set (match_operand:SI 0 "register_operand" "=d,d")
1209         (ior:SI (match_operand:SI 1 "uns_arith_operand" "%d,d")
1210                 (match_operand:SI 2 "uns_arith_operand" "d,K")))]
1211   ""
1212   "@
1213    or\\t%0,%1,%2
1214    ori\\t%0,%1,%x2"
1215   [(set_attr "type"     "arith")
1216    (set_attr "mode"     "SI")
1217    (set_attr "length"   "1")])
1218
1219 (define_insn "iordi3"
1220   [(set (match_operand:DI 0 "register_operand" "=d")
1221         (ior:DI (match_operand:DI 1 "register_operand" "d")
1222                 (match_operand:DI 2 "register_operand" "d")))]
1223   "!TARGET_DEBUG_G_MODE"
1224   "or\\t%M0,%M1,%M2\;or\\t%L0,%L1,%L2"
1225   [(set_attr "type"     "darith")
1226    (set_attr "mode"     "DI")
1227    (set_attr "length"   "2")])
1228
1229 (define_split
1230   [(set (match_operand:DI 0 "register_operand" "")
1231         (ior:DI (match_operand:DI 1 "register_operand" "")
1232                 (match_operand:DI 2 "register_operand" "")))]
1233   "reload_completed && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
1234    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
1235    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
1236    && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))"
1237
1238   [(set (subreg:SI (match_dup 0) 0) (ior:SI (subreg:SI (match_dup 1) 0) (subreg:SI (match_dup 2) 0)))
1239    (set (subreg:SI (match_dup 0) 1) (ior:SI (subreg:SI (match_dup 1) 1) (subreg:SI (match_dup 2) 1)))]
1240   "")
1241
1242 (define_insn "xorsi3"
1243   [(set (match_operand:SI 0 "register_operand" "=d,d")
1244         (xor:SI (match_operand:SI 1 "uns_arith_operand" "%d,d")
1245                 (match_operand:SI 2 "uns_arith_operand" "d,K")))]
1246   ""
1247   "@
1248    xor\\t%0,%1,%2
1249    xori\\t%0,%1,%x2"
1250   [(set_attr "type"     "arith")
1251    (set_attr "mode"     "SI")
1252    (set_attr "length"   "1")])
1253
1254 (define_insn "xordi3"
1255   [(set (match_operand:DI 0 "register_operand" "=d")
1256         (xor:DI (match_operand:DI 1 "register_operand" "d")
1257                 (match_operand:DI 2 "register_operand" "d")))]
1258   "!TARGET_DEBUG_G_MODE"
1259   "xor\\t%M0,%M1,%M2\;xor\\t%L0,%L1,%L2"
1260   [(set_attr "type"     "darith")
1261    (set_attr "mode"     "DI")
1262    (set_attr "length"   "2")])
1263
1264 (define_split
1265   [(set (match_operand:DI 0 "register_operand" "")
1266         (xor:DI (match_operand:DI 1 "register_operand" "")
1267                 (match_operand:DI 2 "register_operand" "")))]
1268   "reload_completed && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
1269    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
1270    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))
1271    && GET_CODE (operands[2]) == REG && GP_REG_P (REGNO (operands[2]))"
1272
1273   [(set (subreg:SI (match_dup 0) 0) (xor:SI (subreg:SI (match_dup 1) 0) (subreg:SI (match_dup 2) 0)))
1274    (set (subreg:SI (match_dup 0) 1) (xor:SI (subreg:SI (match_dup 1) 1) (subreg:SI (match_dup 2) 1)))]
1275   "")
1276
1277 \f
1278 ;;
1279 ;;  ....................
1280 ;;
1281 ;;      TRUNCATION
1282 ;;
1283 ;;  ....................
1284
1285 (define_insn "truncdfsf2"
1286   [(set (match_operand:SF 0 "register_operand" "=f")
1287         (float_truncate:SF (match_operand:DF 1 "register_operand" "f")))]
1288   "TARGET_HARD_FLOAT"
1289   "cvt.s.d\\t%0,%1"
1290   [(set_attr "type"     "fcvt")
1291    (set_attr "mode"     "SF")
1292    (set_attr "length"   "1")])
1293
1294 \f
1295 ;;
1296 ;;  ....................
1297 ;;
1298 ;;      ZERO EXTENSION
1299 ;;
1300 ;;  ....................
1301
1302 ;; Extension insns.
1303 ;; Those for integer source operand
1304 ;; are ordered widest source type first.
1305
1306 (define_insn "zero_extendhisi2"
1307   [(set (match_operand:SI 0 "register_operand" "=d,d,d")
1308         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "d,R,m")))]
1309   ""
1310   "*
1311 {
1312   if (which_alternative == 0)
1313     return \"andi\\t%0,%1,0xffff\";
1314   else
1315     return mips_move_1word (operands, insn, TRUE);
1316 }"
1317   [(set_attr "type"     "arith,load,load")
1318    (set_attr "mode"     "SI")
1319    (set_attr "length"   "1,1,2")])
1320
1321 (define_insn "zero_extendqihi2"
1322   [(set (match_operand:HI 0 "register_operand" "=d,d,d")
1323         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "d,R,m")))]
1324   ""
1325   "*
1326 {
1327   if (which_alternative == 0)
1328     return \"andi\\t%0,%1,0x00ff\";
1329   else
1330     return mips_move_1word (operands, insn, TRUE);
1331 }"
1332   [(set_attr "type"     "arith,load,load")
1333    (set_attr "mode"     "HI")
1334    (set_attr "length"   "1,1,2")])
1335
1336 (define_insn "zero_extendqisi2"
1337   [(set (match_operand:SI 0 "register_operand" "=d,d,d")
1338         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "d,R,m")))]
1339   ""
1340   "*
1341 {
1342   if (which_alternative == 0)
1343     return \"andi\\t%0,%1,0x00ff\";
1344   else
1345     return mips_move_1word (operands, insn, TRUE);
1346 }"
1347   [(set_attr "type"     "arith,load,load")
1348    (set_attr "mode"     "SI")
1349    (set_attr "length"   "1,1,2")])
1350
1351 \f
1352 ;;
1353 ;;  ....................
1354 ;;
1355 ;;      SIGN EXTENSION
1356 ;;
1357 ;;  ....................
1358
1359 ;; Extension insns.
1360 ;; Those for integer source operand
1361 ;; are ordered widest source type first.
1362
1363 ;; These patterns originally accepted general_operands, however, slightly
1364 ;; better code is generated by only accepting register_operands, and then
1365 ;; letting combine generate the lh and lb insns.
1366
1367 (define_expand "extendhisi2"
1368   [(set (match_operand:SI 0 "register_operand" "")
1369         (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
1370   ""
1371   "
1372 {
1373   if (optimize && GET_CODE (operands[1]) == MEM)
1374     operands[1] = force_not_mem (operands[1]);
1375
1376   if (GET_CODE (operands[1]) != MEM)
1377     {
1378       rtx op1   = gen_lowpart (SImode, operands[1]);
1379       rtx temp  = gen_reg_rtx (SImode);
1380       rtx shift = gen_rtx (CONST_INT, VOIDmode, 16);
1381
1382       emit_insn (gen_ashlsi3 (temp, op1, shift));
1383       emit_insn (gen_ashrsi3 (operands[0], temp, shift));
1384       DONE;
1385     }
1386 }")
1387
1388 (define_insn "extendhisi2_internal"
1389   [(set (match_operand:SI 0 "register_operand" "=d,d")
1390         (sign_extend:SI (match_operand:HI 1 "memory_operand" "R,m")))]
1391   ""
1392   "* return mips_move_1word (operands, insn, FALSE);"
1393   [(set_attr "type"     "load")
1394    (set_attr "mode"     "SI")
1395    (set_attr "length"   "1,2")])
1396
1397 (define_expand "extendqihi2"
1398   [(set (match_operand:HI 0 "register_operand" "")
1399         (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))]
1400   ""
1401   "
1402 {
1403   if (optimize && GET_CODE (operands[1]) == MEM)
1404     operands[1] = force_not_mem (operands[1]);
1405
1406   if (GET_CODE (operands[1]) != MEM)
1407     {
1408       rtx op0   = gen_lowpart (SImode, operands[0]);
1409       rtx op1   = gen_lowpart (SImode, operands[1]);
1410       rtx temp  = gen_reg_rtx (SImode);
1411       rtx shift = gen_rtx (CONST_INT, VOIDmode, 24);
1412
1413       emit_insn (gen_ashlsi3 (temp, op1, shift));
1414       emit_insn (gen_ashrsi3 (op0, temp, shift));
1415       DONE;
1416     }
1417 }")
1418
1419 (define_insn "extendqihi2_internal"
1420   [(set (match_operand:HI 0 "register_operand" "=d,d")
1421         (sign_extend:HI (match_operand:QI 1 "memory_operand" "R,m")))]
1422   ""
1423   "* return mips_move_1word (operands, insn, FALSE);"
1424   [(set_attr "type"     "load")
1425    (set_attr "mode"     "SI")
1426    (set_attr "length"   "1,2")])
1427
1428
1429 (define_expand "extendqisi2"
1430   [(set (match_operand:SI 0 "register_operand" "")
1431         (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))]
1432   ""
1433   "
1434 {
1435   if (optimize && GET_CODE (operands[1]) == MEM)
1436     operands[1] = force_not_mem (operands[1]);
1437
1438   if (GET_CODE (operands[1]) != MEM)
1439     {
1440       rtx op1   = gen_lowpart (SImode, operands[1]);
1441       rtx temp  = gen_reg_rtx (SImode);
1442       rtx shift = gen_rtx (CONST_INT, VOIDmode, 24);
1443
1444       emit_insn (gen_ashlsi3 (temp, op1, shift));
1445       emit_insn (gen_ashrsi3 (operands[0], temp, shift));
1446       DONE;
1447     }
1448 }")
1449
1450 (define_insn "extendqisi2_insn"
1451   [(set (match_operand:SI 0 "register_operand" "=d,d")
1452         (sign_extend:SI (match_operand:QI 1 "memory_operand" "R,m")))]
1453   ""
1454   "* return mips_move_1word (operands, insn, FALSE);"
1455   [(set_attr "type"     "load")
1456    (set_attr "mode"     "SI")
1457    (set_attr "length"   "1,2")])
1458
1459
1460 (define_insn "extendsfdf2"
1461   [(set (match_operand:DF 0 "register_operand" "=f")
1462         (float_extend:DF (match_operand:SF 1 "register_operand" "f")))]
1463   "TARGET_HARD_FLOAT"
1464   "cvt.d.s\\t%0,%1"
1465   [(set_attr "type"     "fcvt")
1466    (set_attr "mode"     "DF")
1467    (set_attr "length"   "1")])
1468
1469 \f
1470
1471 ;;
1472 ;;  ....................
1473 ;;
1474 ;;      CONVERSIONS
1475 ;;
1476 ;;  ....................
1477
1478 (define_insn "fix_truncdfsi2"
1479   [(set (match_operand:SI 0 "general_operand" "=d,*f,R,o")
1480         (fix:SI (match_operand:DF 1 "register_operand" "f,*f,f,f")))
1481    (clobber (match_scratch:SI 2 "=d,*d,d,d"))
1482    (clobber (match_scratch:DF 3 "=f,*X,f,f"))]
1483   "TARGET_HARD_FLOAT"
1484   "*
1485 {
1486   rtx xoperands[10];
1487
1488   if (which_alternative == 1)
1489     return \"trunc.w.d %0,%1,%2\";
1490
1491   output_asm_insn (\"trunc.w.d %3,%1,%2\", operands);
1492
1493   xoperands[0] = operands[0];
1494   xoperands[1] = operands[3];
1495   output_asm_insn (mips_move_1word (xoperands, insn, FALSE), xoperands);
1496   return \"\";
1497 }"
1498   [(set_attr "type"     "fcvt")
1499    (set_attr "mode"     "DF")
1500    (set_attr "length"   "11,9,10,11")])
1501
1502
1503 (define_insn "fix_truncsfsi2"
1504   [(set (match_operand:SI 0 "general_operand" "=d,*f,R,o")
1505         (fix:SI (match_operand:SF 1 "register_operand" "f,*f,f,f")))
1506    (clobber (match_scratch:SI 2 "=d,*d,d,d"))
1507    (clobber (match_scratch:SF 3 "=f,*X,f,f"))]
1508   "TARGET_HARD_FLOAT"
1509   "*
1510 {
1511   rtx xoperands[10];
1512
1513   if (which_alternative == 1)
1514     return \"trunc.w.s %0,%1,%2\";
1515
1516   output_asm_insn (\"trunc.w.s %3,%1,%2\", operands);
1517
1518   xoperands[0] = operands[0];
1519   xoperands[1] = operands[3];
1520   output_asm_insn (mips_move_1word (xoperands, insn, FALSE), xoperands);
1521   return \"\";
1522 }"
1523   [(set_attr "type"     "fcvt")
1524    (set_attr "mode"     "SF")
1525    (set_attr "length"   "11,9,10,11")])
1526
1527
1528 (define_insn "floatsidf2"
1529   [(set (match_operand:DF 0 "register_operand" "=f,f,f")
1530         (float:DF (match_operand:SI 1 "nonimmediate_operand" "d,R,m")))]
1531   "TARGET_HARD_FLOAT"
1532   "*
1533 {
1534   dslots_load_total++;
1535   if (GET_CODE (operands[1]) == MEM)
1536     return \"l.s\\t%0,%1%#\;cvt.d.w\\t%0,%0\";
1537
1538   return \"mtc1\\t%1,%0%#\;cvt.d.w\\t%0,%0\";
1539 }"
1540   [(set_attr "type"     "fcvt")
1541    (set_attr "mode"     "DF")
1542    (set_attr "length"   "3,4,3")])
1543
1544
1545 (define_insn "floatsisf2"
1546   [(set (match_operand:SF 0 "register_operand" "=f,f,f")
1547         (float:SF (match_operand:SI 1 "nonimmediate_operand" "d,R,m")))]
1548   "TARGET_HARD_FLOAT"
1549   "*
1550 {
1551   dslots_load_total++;
1552   if (GET_CODE (operands[1]) == MEM)
1553     return \"l.s\\t%0,%1%#\;cvt.s.w\\t%0,%0\";
1554
1555   return \"mtc1\\t%1,%0%#\;cvt.s.w\\t%0,%0\";
1556 }"
1557   [(set_attr "type"     "fcvt")
1558    (set_attr "mode"     "SF")
1559    (set_attr "length"   "3,4,3")])
1560
1561
1562 (define_expand "fixuns_truncdfsi2"
1563   [(set (match_operand:SI 0 "register_operand" "")
1564         (unsigned_fix:SI (match_operand:DF 1 "register_operand" "")))]
1565   "TARGET_HARD_FLOAT"
1566   "
1567 {
1568   rtx reg1 = gen_reg_rtx (DFmode);
1569   rtx reg2 = gen_reg_rtx (DFmode);
1570   rtx reg3 = gen_reg_rtx (SImode);
1571   rtx label1 = gen_label_rtx ();
1572   rtx label2 = gen_label_rtx ();
1573   REAL_VALUE_TYPE offset = REAL_VALUE_LDEXP (1.0, 31);
1574
1575   if (reg1)                     /* turn off complaints about unreached code */
1576     {
1577       emit_move_insn (reg1, immed_real_const_1 (offset, DFmode));
1578       do_pending_stack_adjust ();
1579
1580       emit_insn (gen_cmpdf (operands[1], reg1));
1581       emit_jump_insn (gen_bge (label1));
1582
1583       emit_insn (gen_fix_truncdfsi2 (operands[0], operands[1]));
1584       emit_jump_insn (gen_rtx (SET, VOIDmode, pc_rtx,
1585                                gen_rtx (LABEL_REF, VOIDmode, label2)));
1586       emit_barrier ();
1587
1588       emit_label (label1);
1589       emit_move_insn (reg2, gen_rtx (MINUS, DFmode, operands[1], reg1));
1590       emit_move_insn (reg3, gen_rtx (CONST_INT, VOIDmode, 0x80000000));
1591
1592       emit_insn (gen_fix_truncdfsi2 (operands[0], reg2));
1593       emit_insn (gen_iorsi3 (operands[0], operands[0], reg3));
1594
1595       emit_label (label2);
1596
1597       /* allow REG_NOTES to be set on last insn (labels don't have enough
1598          fields, and can't be used for REG_NOTES anyway).  */
1599       emit_insn (gen_rtx (USE, VOIDmode, stack_pointer_rtx));
1600       DONE;
1601     }
1602 }")
1603
1604
1605 (define_expand "fixuns_truncsfsi2"
1606   [(set (match_operand:SI 0 "register_operand" "")
1607         (unsigned_fix:SI (match_operand:SF 1 "register_operand" "")))]
1608   "TARGET_HARD_FLOAT"
1609   "
1610 {
1611   rtx reg1 = gen_reg_rtx (SFmode);
1612   rtx reg2 = gen_reg_rtx (SFmode);
1613   rtx reg3 = gen_reg_rtx (SImode);
1614   rtx label1 = gen_label_rtx ();
1615   rtx label2 = gen_label_rtx ();
1616   REAL_VALUE_TYPE offset = REAL_VALUE_LDEXP (1.0, 31);
1617
1618   if (reg1)                     /* turn off complaints about unreached code */
1619     {
1620       emit_move_insn (reg1, immed_real_const_1 (offset, SFmode));
1621       do_pending_stack_adjust ();
1622
1623       emit_insn (gen_cmpsf (operands[1], reg1));
1624       emit_jump_insn (gen_bge (label1));
1625
1626       emit_insn (gen_fix_truncsfsi2 (operands[0], operands[1]));
1627       emit_jump_insn (gen_rtx (SET, VOIDmode, pc_rtx,
1628                                gen_rtx (LABEL_REF, VOIDmode, label2)));
1629       emit_barrier ();
1630
1631       emit_label (label1);
1632       emit_move_insn (reg2, gen_rtx (MINUS, SFmode, operands[1], reg1));
1633       emit_move_insn (reg3, gen_rtx (CONST_INT, VOIDmode, 0x80000000));
1634
1635       emit_insn (gen_fix_truncsfsi2 (operands[0], reg2));
1636       emit_insn (gen_iorsi3 (operands[0], operands[0], reg3));
1637
1638       emit_label (label2);
1639
1640       /* allow REG_NOTES to be set on last insn (labels don't have enough
1641          fields, and can't be used for REG_NOTES anyway).  */
1642       emit_insn (gen_rtx (USE, VOIDmode, stack_pointer_rtx));
1643       DONE;
1644     }
1645 }")
1646
1647 \f
1648 ;;
1649 ;;  ....................
1650 ;;
1651 ;;      DATA MOVEMENT
1652 ;;
1653 ;;  ....................
1654
1655 ;; unaligned word moves generated by the block moves.
1656
1657 (define_expand "movsi_unaligned"
1658   [(set (match_operand:SI 0 "general_operand" "")
1659         (unspec [(match_operand:SI 1 "general_operand" "")] 0))]
1660   ""
1661   "
1662 {
1663   /* Handle loads.  */
1664   if (GET_CODE (operands[0]) == MEM)
1665     {
1666       rtx reg = gen_reg_rtx (SImode);
1667       rtx insn = emit_insn (gen_movsi_ulw (reg, operands[1]));
1668       rtx addr = XEXP (operands[0], 0);
1669       if (CONSTANT_P (addr))
1670         REG_NOTES (insn) = gen_rtx (EXPR_LIST, REG_EQUIV, addr, REG_NOTES (insn));
1671
1672       if (reg_or_0_operand (operands[1], SImode))
1673         DONE;
1674
1675       operands[1] = reg;
1676     }
1677
1678   /* Generate appropriate load, store.  If not a load or store,
1679      do a normal movsi.  */
1680   if (GET_CODE (operands[0]) != MEM && GET_CODE (operands[1]) != MEM)
1681     {
1682       emit_insn (gen_movsi (operands[0], operands[1]));
1683       DONE;
1684     }
1685
1686   /* Fall through and generate normal code.  */
1687 }")
1688
1689 (define_insn "movsi_ulw"
1690   [(set (match_operand:SI 0 "register_operand" "=&d,&d,d,d")
1691         (unspec [(match_operand:SI 1 "general_operand" "R,o,dIKL,M")] 0))]
1692   ""
1693   "*
1694 {
1695   enum rtx_code code;
1696   char *ret;
1697   rtx offset;
1698   rtx addr;
1699   rtx mem_addr;
1700
1701   if (which_alternative != 0)
1702     return mips_move_1word (operands, insn, FALSE);
1703
1704   if (TARGET_STATS)
1705     mips_count_memory_refs (operands[1], 2);
1706
1707   /* The stack/frame pointers are always aligned, so we can convert
1708      to the faster lw if we are referencing an aligned stack location.  */
1709
1710   offset = const0_rtx;
1711   addr = XEXP (operands[1], 0);
1712   mem_addr = eliminate_constant_term (addr, &offset);
1713
1714   if ((INTVAL (offset) & (UNITS_PER_WORD-1)) == 0
1715       && (mem_addr == stack_pointer_rtx || mem_addr == frame_pointer_rtx))
1716     ret = \"lw\\t%0,%1\";
1717
1718   else
1719     {
1720       ret = \"ulw\\t%0,%1\";
1721       if (TARGET_GAS)
1722         {
1723           enum rtx_code code = GET_CODE (addr);
1724
1725           if (code == CONST || code == SYMBOL_REF || code == LABEL_REF)
1726             {
1727               operands[2] = gen_rtx (REG, SImode, GP_REG_FIRST + 1);
1728               ret = \"%[la\\t%2,%1\;ulw\\t%0,0(%2)%]\";
1729             }
1730         }
1731     }
1732
1733   return mips_fill_delay_slot (ret, DELAY_LOAD, operands, insn);
1734 }"
1735   [(set_attr "type"     "load,load,move,arith")
1736    (set_attr "mode"     "SI")
1737    (set_attr "length"   "2,4,1,2")])
1738
1739 (define_insn "movsi_usw"
1740   [(set (match_operand:SI 0 "memory_operand" "=R,o")
1741         (unspec [(match_operand:SI 1 "reg_or_0_operand" "dJ,dJ")] 0))]
1742   ""
1743   "*
1744 {
1745   rtx offset = const0_rtx;
1746   rtx addr = XEXP (operands[0], 0);
1747   rtx mem_addr = eliminate_constant_term (addr, &offset);
1748
1749   if (TARGET_STATS)
1750     mips_count_memory_refs (operands[0], 2);
1751
1752   /* The stack/frame pointers are always aligned, so we can convert
1753      to the faster sw if we are referencing an aligned stack location.  */
1754
1755   if ((INTVAL (offset) & (UNITS_PER_WORD-1)) == 0
1756       && (mem_addr == stack_pointer_rtx || mem_addr == frame_pointer_rtx))
1757     return \"sw\\t%1,%0\";
1758
1759
1760   if (TARGET_GAS)
1761     {
1762       enum rtx_code code = GET_CODE (XEXP (operands[0], 0));
1763
1764       if (code == CONST || code == SYMBOL_REF || code == LABEL_REF)
1765         {
1766           operands[2] = gen_rtx (REG, SImode, GP_REG_FIRST + 1);
1767           return \"%[la\\t%2,%0\;usw\\t%z1,0(%2)%]\";
1768         }
1769     }
1770
1771   return \"usw\\t%z1,%0\";
1772 }"
1773   [(set_attr "type"     "store")
1774    (set_attr "mode"     "SI")
1775    (set_attr "length"   "2,4")])
1776
1777
1778 ;; 64-bit integer moves
1779
1780 ;; Unlike most other insns, the move insns can't be split with
1781 ;; different predicates, because register spilling and other parts of
1782 ;; the compiler, have memoized the insn number already.
1783
1784 (define_expand "movdi"
1785   [(set (match_operand:DI 0 "nonimmediate_operand" "")
1786         (match_operand:DI 1 "general_operand" ""))]
1787   ""
1788   "
1789 {
1790   if ((reload_in_progress | reload_completed) == 0
1791       && !register_operand (operands[0], DImode)
1792       && !register_operand (operands[1], DImode)
1793       && (GET_CODE (operands[1]) != CONST_INT || INTVAL (operands[1]) != 0)
1794       && operands[1] != CONST0_RTX (DImode))
1795     {
1796       rtx temp = force_reg (DImode, operands[1]);
1797       emit_move_insn (operands[0], temp);
1798       DONE;
1799     }
1800 }")
1801
1802 (define_insn "movdi_internal"
1803   [(set (match_operand:DI 0 "nonimmediate_operand" "=d,d,d,d,R,o,*d,*x")
1804         (match_operand:DI 1 "general_operand" "d,iF,R,o,d,d,*x,*d"))]
1805   "register_operand (operands[0], DImode)
1806    || register_operand (operands[1], DImode)
1807    || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0)
1808    || operands[1] == CONST0_RTX (DImode)"
1809   "* return mips_move_2words (operands, insn); "
1810   [(set_attr "type"     "move,arith,load,load,store,store,hilo,hilo")
1811    (set_attr "mode"     "DI")
1812    (set_attr "length"   "2,4,2,4,2,4,2,2")])
1813
1814 (define_split
1815   [(set (match_operand:DI 0 "register_operand" "")
1816         (match_operand:DI 1 "register_operand" ""))]
1817   "reload_completed && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
1818    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
1819    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))"
1820
1821   [(set (subreg:SI (match_dup 0) 0) (subreg:SI (match_dup 1) 0))
1822    (set (subreg:SI (match_dup 0) 1) (subreg:SI (match_dup 1) 1))]
1823   "")
1824
1825
1826 ;; 32-bit Integer moves
1827
1828 (define_split
1829   [(set (match_operand:SI 0 "register_operand" "")
1830         (match_operand:SI 1 "large_int" ""))]
1831   "!TARGET_DEBUG_D_MODE"
1832   [(set (match_dup 0)
1833         (match_dup 2))
1834    (set (match_dup 0)
1835         (ior:SI (match_dup 0)
1836                 (match_dup 3)))]
1837   "
1838 {
1839   operands[2] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) & 0xffff0000);
1840   operands[3] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[1]) & 0x0000ffff);
1841 }")
1842
1843 ;; Unlike most other insns, the move insns can't be split with
1844 ;; different predicates, because register spilling and other parts of
1845 ;; the compiler, have memoized the insn number already.
1846
1847 (define_expand "movsi"
1848   [(set (match_operand:SI 0 "nonimmediate_operand" "")
1849         (match_operand:SI 1 "general_operand" ""))]
1850   ""
1851   "
1852 {
1853   if ((reload_in_progress | reload_completed) == 0
1854       && !register_operand (operands[0], SImode)
1855       && !register_operand (operands[1], SImode)
1856       && (GET_CODE (operands[1]) != CONST_INT || INTVAL (operands[1]) != 0))
1857     {
1858       rtx temp = force_reg (SImode, operands[1]);
1859       emit_move_insn (operands[0], temp);
1860       DONE;
1861     }
1862 }")
1863
1864 ;; The difference between these two is whether or not ints are allowed
1865 ;; in FP registers (off by default, use -mdebugh to enable).
1866
1867 (define_insn "movsi_internal1"
1868   [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,d,d,d,R,m,*d,*f*z,*f,*f,*f,*R,*m,*x,*d")
1869         (match_operand:SI 1 "general_operand" "d,S,IKL,Mnis,R,m,dJ,dJ,*f*z,*d,*f,*R,*m,*f,*f,*d,*x"))]
1870   "TARGET_DEBUG_H_MODE
1871    && (register_operand (operands[0], SImode)
1872        || register_operand (operands[1], SImode)
1873        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0))"
1874   "* return mips_move_1word (operands, insn, TRUE);"
1875   [(set_attr "type"     "move,load,arith,arith,load,load,store,store,xfer,xfer,move,load,load,store,store,hilo,hilo")
1876    (set_attr "mode"     "SI")
1877    (set_attr "length"   "1,2,1,2,1,2,1,2,1,1,1,1,2,1,2,1,1")])
1878
1879 (define_insn "movsi_internal2"
1880   [(set (match_operand:SI 0 "nonimmediate_operand" "=d,d,d,d,d,d,R,m,*d,*z,*d,*x")
1881         (match_operand:SI 1 "general_operand" "d,S,IKL,Mnis,R,m,dJ,dJ,*z,*d,*x,*d"))]
1882   "!TARGET_DEBUG_H_MODE
1883    && (register_operand (operands[0], SImode)
1884        || register_operand (operands[1], SImode)
1885        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0))"
1886   "* return mips_move_1word (operands, insn, TRUE);"
1887   [(set_attr "type"     "move,load,arith,arith,load,load,store,store,xfer,xfer,hilo,hilo")
1888    (set_attr "mode"     "SI")
1889    (set_attr "length"   "1,2,1,2,1,2,1,2,1,1,1,1")])
1890
1891
1892 ;; 16-bit Integer moves
1893
1894 ;; Unlike most other insns, the move insns can't be split with
1895 ;; different predicates, because register spilling and other parts of
1896 ;; the compiler, have memoized the insn number already.
1897 ;; Unsigned loads are used because BYTE_LOADS_ZERO_EXTEND is defined
1898
1899 (define_expand "movhi"
1900   [(set (match_operand:HI 0 "nonimmediate_operand" "")
1901         (match_operand:HI 1 "general_operand" ""))]
1902   ""
1903   "
1904 {
1905   if ((reload_in_progress | reload_completed) == 0
1906       && !register_operand (operands[0], HImode)
1907       && !register_operand (operands[1], HImode)
1908       && (GET_CODE (operands[1]) != CONST_INT || INTVAL (operands[1]) != 0))
1909     {
1910       rtx temp = force_reg (HImode, operands[1]);
1911       emit_move_insn (operands[0], temp);
1912       DONE;
1913     }
1914 }")
1915
1916 ;; The difference between these two is whether or not ints are allowed
1917 ;; in FP registers (off by default, use -mdebugh to enable).
1918
1919 (define_insn "movhi_internal1"
1920   [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d,d,R,m,*d,*f,*f*z,*x,*d")
1921         (match_operand:HI 1 "general_operand"       "d,IK,R,m,dJ,dJ,*f*z,*d,*f,*d,*x"))]
1922   "TARGET_DEBUG_H_MODE
1923    && (register_operand (operands[0], HImode)
1924        || register_operand (operands[1], HImode)
1925        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0))"
1926   "* return mips_move_1word (operands, insn, TRUE);"
1927   [(set_attr "type"     "move,arith,load,load,store,store,xfer,xfer,move,hilo,hilo")
1928    (set_attr "mode"     "HI")
1929    (set_attr "length"   "1,1,1,2,1,2,1,1,1,1,1")])
1930
1931 (define_insn "movhi_internal2"
1932   [(set (match_operand:HI 0 "nonimmediate_operand" "=d,d,d,d,R,m,*d,*z,*x,*d")
1933         (match_operand:HI 1 "general_operand"       "d,IK,R,m,dJ,dJ,*z,*d,*d,*x"))]
1934   "!TARGET_DEBUG_H_MODE
1935    && (register_operand (operands[0], HImode)
1936        || register_operand (operands[1], HImode)
1937        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0))"
1938   "* return mips_move_1word (operands, insn, TRUE);"
1939   [(set_attr "type"     "move,arith,load,load,store,store,xfer,xfer,hilo,hilo")
1940    (set_attr "mode"     "HI")
1941    (set_attr "length"   "1,1,1,2,1,2,1,1,1,1")])
1942
1943
1944 ;; 8-bit Integer moves
1945
1946 ;; Unlike most other insns, the move insns can't be split with
1947 ;; different predicates, because register spilling and other parts of
1948 ;; the compiler, have memoized the insn number already.
1949 ;; Unsigned loads are used because BYTE_LOADS_ZERO_EXTEND is defined
1950
1951 (define_expand "movqi"
1952   [(set (match_operand:QI 0 "nonimmediate_operand" "")
1953         (match_operand:QI 1 "general_operand" ""))]
1954   ""
1955   "
1956 {
1957   if ((reload_in_progress | reload_completed) == 0
1958       && !register_operand (operands[0], QImode)
1959       && !register_operand (operands[1], QImode)
1960       && (GET_CODE (operands[1]) != CONST_INT || INTVAL (operands[1]) != 0))
1961     {
1962       rtx temp = force_reg (QImode, operands[1]);
1963       emit_move_insn (operands[0], temp);
1964       DONE;
1965     }
1966 }")
1967
1968 ;; The difference between these two is whether or not ints are allowed
1969 ;; in FP registers (off by default, use -mdebugh to enable).
1970
1971 (define_insn "movqi_internal1"
1972   [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,d,R,m,*d,*f*z,*f,*x,*d")
1973         (match_operand:QI 1 "general_operand"       "d,IK,R,m,dJ,dJ,*f*z,*d,*f,*d,*x"))]
1974   "TARGET_DEBUG_H_MODE
1975    && (register_operand (operands[0], QImode)
1976        || register_operand (operands[1], QImode)
1977        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0))"
1978   "* return mips_move_1word (operands, insn, TRUE);"
1979   [(set_attr "type"     "move,arith,load,load,store,store,xfer,xfer,move,hilo,hilo")
1980    (set_attr "mode"     "QI")
1981    (set_attr "length"   "1,1,1,2,1,2,1,1,1,1,1")])
1982
1983 (define_insn "movqi_internal2"
1984   [(set (match_operand:QI 0 "nonimmediate_operand" "=d,d,d,d,R,m,*d,*z,*x,*d")
1985         (match_operand:QI 1 "general_operand"       "d,IK,R,m,dJ,dJ,*z,*d,*d,*x"))]
1986   "!TARGET_DEBUG_H_MODE
1987    && (register_operand (operands[0], QImode)
1988        || register_operand (operands[1], QImode)
1989        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0))"
1990   "* return mips_move_1word (operands, insn, TRUE);"
1991   [(set_attr "type"     "move,arith,load,load,store,store,xfer,xfer,hilo,hilo")
1992    (set_attr "mode"     "QI")
1993    (set_attr "length"   "1,1,1,2,1,2,1,1,1,1")])
1994
1995
1996 ;; 32-bit floating point moves
1997
1998 (define_expand "movsf"
1999   [(set (match_operand:SF 0 "nonimmediate_operand" "")
2000         (match_operand:SF 1 "general_operand" ""))]
2001   ""
2002   "
2003 {
2004   if ((reload_in_progress | reload_completed) == 0
2005       && !register_operand (operands[0], SFmode)
2006       && !register_operand (operands[1], SFmode)
2007       && (GET_CODE (operands[1]) != CONST_INT || INTVAL (operands[1]) != 0)
2008       && operands[1] != CONST0_RTX (SFmode))
2009     {
2010       rtx temp = force_reg (SFmode, operands[1]);
2011       emit_move_insn (operands[0], temp);
2012       DONE;
2013     }
2014 }")
2015
2016 (define_insn "movsf_internal1"
2017   [(set (match_operand:SF 0 "nonimmediate_operand" "=f,f,f,f,R,m,*f,*d,*d,*d,*d,*R,*m")
2018         (match_operand:SF 1 "general_operand" "f,G,R,Em,fG,fG,*d,*f,*G*d,*R,*E*m,*d,*d"))]
2019   "TARGET_HARD_FLOAT
2020    && (register_operand (operands[0], SFmode)
2021        || register_operand (operands[1], SFmode)
2022        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0)
2023        || operands[1] == CONST0_RTX (SFmode))"
2024   "* return mips_move_1word (operands, insn, FALSE);"
2025   [(set_attr "type"     "move,xfer,load,load,store,store,xfer,xfer,move,load,load,store,store")
2026    (set_attr "mode"     "SF")
2027    (set_attr "length"   "1,1,1,2,1,2,1,1,1,1,2,1,2")])
2028
2029
2030 (define_insn "movsf_internal2"
2031   [(set (match_operand:SF 0 "nonimmediate_operand" "=d,d,d,R,m")
2032         (match_operand:SF 1 "general_operand" "      Gd,R,Em,d,d"))]
2033   "TARGET_SOFT_FLOAT
2034    && (register_operand (operands[0], SFmode)
2035        || register_operand (operands[1], SFmode)
2036        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0)
2037        || operands[1] == CONST0_RTX (SFmode))"
2038   "* return mips_move_1word (operands, insn, FALSE);"
2039   [(set_attr "type"     "move,load,load,store,store")
2040    (set_attr "mode"     "SF")
2041    (set_attr "length"   "1,1,2,1,2")])
2042
2043
2044 ;; 64-bit floating point moves
2045
2046 (define_expand "movdf"
2047   [(set (match_operand:DF 0 "nonimmediate_operand" "")
2048         (match_operand:DF 1 "general_operand" ""))]
2049   ""
2050   "
2051 {
2052   if ((reload_in_progress | reload_completed) == 0
2053       && !register_operand (operands[0], DFmode)
2054       && !register_operand (operands[1], DFmode)
2055       && (GET_CODE (operands[1]) != CONST_INT || INTVAL (operands[1]) != 0)
2056       && operands[1] != CONST0_RTX (DFmode))
2057     {
2058       rtx temp = force_reg (DFmode, operands[1]);
2059       emit_move_insn (operands[0], temp);
2060       DONE;
2061     }
2062 }")
2063
2064 (define_insn "movdf_internal1"
2065   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,f,f,R,o,f,*f,*d,*d,*d,*d,*R,*o")
2066         (match_operand:DF 1 "general_operand" "f,R,o,fG,fG,E,*d,*f,*d*G,*R,*o*E,*d,*d"))]
2067   "TARGET_HARD_FLOAT
2068    && (register_operand (operands[0], DFmode)
2069        || register_operand (operands[1], DFmode)
2070        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0)
2071        || operands[1] == CONST0_RTX (DFmode))"
2072   "* return mips_move_2words (operands, insn); "
2073   [(set_attr "type"     "move,load,load,store,store,load,xfer,xfer,move,load,load,store,store")
2074    (set_attr "mode"     "DF")
2075    (set_attr "length"   "1,2,4,2,4,4,2,2,2,2,4,2,4")])
2076
2077 (define_insn "movdf_internal2"
2078   [(set (match_operand:DF 0 "nonimmediate_operand" "=d,d,d,R,o")
2079         (match_operand:DF 1 "general_operand" "dG,R,oE,d,d"))]
2080   "TARGET_SOFT_FLOAT
2081    && (register_operand (operands[0], DFmode)
2082        || register_operand (operands[1], DFmode)
2083        || (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) == 0)
2084        || operands[1] == CONST0_RTX (DFmode))"
2085   "* return mips_move_2words (operands, insn); "
2086   [(set_attr "type"     "move,load,load,store,store")
2087    (set_attr "mode"     "DF")
2088    (set_attr "length"   "2,2,4,2,4")])
2089
2090 (define_split
2091   [(set (match_operand:DF 0 "register_operand" "")
2092         (match_operand:DF 1 "register_operand" ""))]
2093   "reload_completed && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2094    && GET_CODE (operands[0]) == REG && GP_REG_P (REGNO (operands[0]))
2095    && GET_CODE (operands[1]) == REG && GP_REG_P (REGNO (operands[1]))"
2096
2097   [(set (subreg:SI (match_dup 0) 0) (subreg:SI (match_dup 1) 0))
2098    (set (subreg:SI (match_dup 0) 1) (subreg:SI (match_dup 1) 1))]
2099   "")
2100
2101 \f
2102 ;; Block moves, see mips.c for more details.
2103 ;; Argument 0 is the destination
2104 ;; Argument 1 is the source
2105 ;; Argument 2 is the length
2106 ;; Argument 3 is the alignment
2107
2108 (define_expand "movstrsi"
2109   [(parallel [(set (mem:BLK (match_operand:BLK 0 "general_operand" ""))
2110                    (mem:BLK (match_operand:BLK 1 "general_operand" "")))
2111               (use (match_operand:SI 2 "arith32_operand" ""))
2112               (use (match_operand:SI 3 "immediate_operand" ""))])]
2113   ""
2114   "
2115 {
2116   if (operands[0])              /* avoid unused code messages */
2117     {
2118       expand_block_move (operands);
2119       DONE;
2120     }
2121 }")
2122
2123 ;; Insn generated by block moves
2124
2125 (define_insn "movstrsi_internal"
2126   [(set (match_operand:BLK 0 "memory_operand" "=Ro")    ;; destination
2127         (match_operand:BLK 1 "memory_operand" "Ro"))    ;; source
2128    (clobber (match_scratch:SI 4 "=&d"))                 ;; temp 1
2129    (clobber (match_scratch:SI 5 "=&d"))                 ;; temp 2
2130    (clobber (match_scratch:SI 6 "=&d"))                 ;; temp 3
2131    (clobber (match_scratch:SI 7 "=&d"))                 ;; temp 4
2132    (use (match_operand:SI 2 "small_int" "I"))           ;; # bytes to move
2133    (use (match_operand:SI 3 "small_int" "I"))           ;; alignment
2134    (use (const_int 0))]                                 ;; normal block move
2135   ""
2136   "* return output_block_move (insn, operands, 4, BLOCK_MOVE_NORMAL);"
2137   [(set_attr "type"     "multi")
2138    (set_attr "mode"     "none")
2139    (set_attr "length"   "20")])
2140
2141 ;; Split a block move into 2 parts, the first part is everything
2142 ;; except for the last move, and the second part is just the last
2143 ;; store, which is exactly 1 instruction (ie, not a usw), so it can
2144 ;; fill a delay slot.  This also prevents a bug in delayed branches
2145 ;; from showing up, which reuses one of the registers in our clobbers.
2146
2147 (define_split
2148   [(set (mem:BLK (match_operand:SI 0 "register_operand" ""))
2149         (mem:BLK (match_operand:SI 1 "register_operand" "")))
2150    (clobber (match_operand:SI 4 "register_operand" ""))
2151    (clobber (match_operand:SI 5 "register_operand" ""))
2152    (clobber (match_operand:SI 6 "register_operand" ""))
2153    (clobber (match_operand:SI 7 "register_operand" ""))
2154    (use (match_operand:SI 2 "small_int" ""))
2155    (use (match_operand:SI 3 "small_int" ""))
2156    (use (const_int 0))]
2157
2158   "reload_completed && !TARGET_DEBUG_D_MODE && INTVAL (operands[2]) > 0"
2159
2160   ;; All but the last move
2161   [(parallel [(set (mem:BLK (match_dup 0))
2162                    (mem:BLK (match_dup 1)))
2163               (clobber (match_dup 4))
2164               (clobber (match_dup 5))
2165               (clobber (match_dup 6))
2166               (clobber (match_dup 7))
2167               (use (match_dup 2))
2168               (use (match_dup 3))
2169               (use (const_int 1))])
2170
2171    ;; The last store, so it can fill a delay slot
2172    (parallel [(set (mem:BLK (match_dup 0))
2173                    (mem:BLK (match_dup 1)))
2174               (clobber (match_dup 4))
2175               (clobber (match_dup 5))
2176               (clobber (match_dup 6))
2177               (clobber (match_dup 7))
2178               (use (match_dup 2))
2179               (use (match_dup 3))
2180               (use (const_int 2))])]
2181
2182   "")
2183
2184 (define_insn "movstrsi_internal2"
2185   [(set (match_operand:BLK 0 "memory_operand" "=Ro")    ;; destination
2186         (match_operand:BLK 1 "memory_operand" "Ro"))    ;; source
2187    (clobber (match_scratch:SI 4 "=&d"))                 ;; temp 1
2188    (clobber (match_scratch:SI 5 "=&d"))                 ;; temp 2
2189    (clobber (match_scratch:SI 6 "=&d"))                 ;; temp 3
2190    (clobber (match_scratch:SI 7 "=&d"))                 ;; temp 4
2191    (use (match_operand:SI 2 "small_int" "I"))           ;; # bytes to move
2192    (use (match_operand:SI 3 "small_int" "I"))           ;; alignment
2193    (use (const_int 1))]                                 ;; all but last store
2194   ""
2195   "* return output_block_move (insn, operands, 4, BLOCK_MOVE_NOT_LAST);"
2196   [(set_attr "type"     "multi")
2197    (set_attr "mode"     "none")
2198    (set_attr "length"   "20")])
2199
2200 (define_insn "movstrsi_internal3"
2201   [(set (match_operand:BLK 0 "memory_operand" "=Ro")    ;; destination
2202         (match_operand:BLK 1 "memory_operand" "Ro"))    ;; source
2203    (clobber (match_scratch:SI 4 "=&d"))                 ;; temp 1
2204    (clobber (match_scratch:SI 5 "=&d"))                 ;; temp 2
2205    (clobber (match_scratch:SI 6 "=&d"))                 ;; temp 3
2206    (clobber (match_scratch:SI 7 "=&d"))                 ;; temp 4
2207    (use (match_operand:SI 2 "small_int" "I"))           ;; # bytes to move
2208    (use (match_operand:SI 3 "small_int" "I"))           ;; alignment
2209    (use (const_int 2))]                                 ;; just last store of block mvoe
2210   ""
2211   "* return output_block_move (insn, operands, 4, BLOCK_MOVE_LAST);"
2212   [(set_attr "type"     "store")
2213    (set_attr "mode"     "none")
2214    (set_attr "length"   "1")])
2215
2216 \f
2217 ;;
2218 ;;  ....................
2219 ;;
2220 ;;      SHIFTS
2221 ;;
2222 ;;  ....................
2223
2224 (define_insn "ashlsi3"
2225   [(set (match_operand:SI 0 "register_operand" "=d")
2226         (ashift:SI (match_operand:SI 1 "register_operand" "d")
2227                    (match_operand:SI 2 "arith_operand" "dI")))]
2228   ""
2229   "*
2230 {
2231   if (GET_CODE (operands[2]) == CONST_INT)
2232     operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);
2233
2234   return \"sll\\t%0,%1,%2\";
2235 }"
2236   [(set_attr "type"     "arith")
2237    (set_attr "mode"     "SI")
2238    (set_attr "length"   "1")])
2239
2240
2241 (define_expand "ashldi3"
2242   [(parallel [(set (match_operand:DI 0 "register_operand" "")
2243                    (ashift:DI (match_operand:DI 1 "register_operand" "")
2244                               (match_operand:SI 2 "arith_operand" "")))
2245               (clobber (match_dup  3))])]
2246   "!TARGET_DEBUG_G_MODE"
2247   "operands[3] = gen_reg_rtx (SImode);")
2248
2249
2250 (define_insn "ashldi3_internal"
2251   [(set (match_operand:DI 0 "register_operand" "=&d")
2252         (ashift:DI (match_operand:DI 1 "register_operand" "d")
2253                    (match_operand:SI 2 "register_operand" "d")))
2254    (clobber (match_operand:SI 3 "register_operand" "=d"))]
2255   "!TARGET_DEBUG_G_MODE"
2256   "* 
2257 {
2258   operands[4] = const0_rtx;
2259   dslots_jump_total += 3;
2260   dslots_jump_filled += 2;
2261
2262   return \"sll\\t%3,%2,26\\n\\
2263 \\tbgez\\t%3,1f\\n\\
2264 \\tsll\\t%M0,%L1,%2\\n\\
2265 \\t%(b\\t3f\\n\\
2266 \\tmove\\t%L0,%z4%)\\n\\
2267 \\n\\
2268 1:\\n\\
2269 \\t%(beq\\t%3,%z4,2f\\n\\
2270 \\tsll\\t%M0,%M1,%2%)\\n\\
2271 \\n\\
2272 \\tsubu\\t%3,%z4,%2\\n\\
2273 \\tsrl\\t%3,%L1,%3\\n\\
2274 \\tor\\t%M0,%M0,%3\\n\\
2275 2:\\n\\
2276 \\tsll\\t%L0,%L1,%2\\n\\
2277 3:\";
2278 }"
2279   [(set_attr "type"     "darith")
2280    (set_attr "mode"     "SI")
2281    (set_attr "length"   "12")])
2282
2283
2284 (define_insn "ashldi3_internal2"
2285   [(set (match_operand:DI 0 "register_operand" "=d")
2286         (ashift:DI (match_operand:DI 1 "register_operand" "d")
2287                    (match_operand:SI 2 "small_int" "IJK")))
2288    (clobber (match_operand:SI 3 "register_operand" "=d"))]
2289   "!TARGET_DEBUG_G_MODE && (INTVAL (operands[2]) & 32) != 0"
2290   "*
2291 {
2292   operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);
2293   operands[4] = const0_rtx;
2294   return \"sll\\t%M0,%L1,%2\;move\\t%L0,%z4\";
2295 }"
2296   [(set_attr "type"     "darith")
2297    (set_attr "mode"     "DI")
2298    (set_attr "length"   "2")])
2299
2300
2301 (define_split
2302   [(set (match_operand:DI 0 "register_operand" "")
2303         (ashift:DI (match_operand:DI 1 "register_operand" "")
2304                    (match_operand:SI 2 "small_int" "")))
2305    (clobber (match_operand:SI 3 "register_operand" ""))]
2306   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2307    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
2308    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
2309    && (INTVAL (operands[2]) & 32) != 0"
2310
2311   [(set (subreg:SI (match_dup 0) 1) (ashift:SI (subreg:SI (match_dup 1) 0) (match_dup 2)))
2312    (set (subreg:SI (match_dup 0) 0) (const_int 0))]
2313
2314   "operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);")
2315
2316
2317 (define_split
2318   [(set (match_operand:DI 0 "register_operand" "")
2319         (ashift:DI (match_operand:DI 1 "register_operand" "")
2320                    (match_operand:SI 2 "small_int" "")))
2321    (clobber (match_operand:SI 3 "register_operand" ""))]
2322   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2323    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
2324    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
2325    && (INTVAL (operands[2]) & 32) != 0"
2326
2327   [(set (subreg:SI (match_dup 0) 0) (ashift:SI (subreg:SI (match_dup 1) 1) (match_dup 2)))
2328    (set (subreg:SI (match_dup 0) 1) (const_int 0))]
2329
2330   "operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);")
2331
2332
2333 (define_insn "ashldi3_internal3"
2334   [(set (match_operand:DI 0 "register_operand" "=d")
2335         (ashift:DI (match_operand:DI 1 "register_operand" "d")
2336                    (match_operand:SI 2 "small_int" "IJK")))
2337    (clobber (match_operand:SI 3 "register_operand" "=d"))]
2338   "!TARGET_DEBUG_G_MODE
2339    && (INTVAL (operands[2]) & 63) < 32
2340    && (INTVAL (operands[2]) & 63) != 0"
2341   "*
2342 {
2343   int amount = INTVAL (operands[2]);
2344
2345   operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31));
2346   operands[4] = const0_rtx;
2347   operands[5] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31));
2348
2349   return \"sll\\t%M0,%M1,%2\;srl\\t%3,%L1,%5\;or\\t%M0,%M0,%3\;sll\\t%L0,%L1,%2\";
2350 }"
2351   [(set_attr "type"     "darith")
2352    (set_attr "mode"     "DI")
2353    (set_attr "length"   "4")])
2354
2355
2356 (define_split
2357   [(set (match_operand:DI 0 "register_operand" "")
2358         (ashift:DI (match_operand:DI 1 "register_operand" "")
2359                    (match_operand:SI 2 "small_int" "")))
2360    (clobber (match_operand:SI 3 "register_operand" ""))]
2361   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2362    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
2363    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
2364    && (INTVAL (operands[2]) & 63) < 32
2365    && (INTVAL (operands[2]) & 63) != 0"
2366
2367   [(set (subreg:SI (match_dup 0) 1)
2368         (ashift:SI (subreg:SI (match_dup 1) 1)
2369                    (match_dup 2)))
2370
2371    (set (match_dup 3)
2372         (lshiftrt:SI (subreg:SI (match_dup 1) 0)
2373                      (match_dup 4)))
2374
2375    (set (subreg:SI (match_dup 0) 1)
2376         (ior:SI (subreg:SI (match_dup 0) 1)
2377                 (match_dup 3)))
2378
2379    (set (subreg:SI (match_dup 0) 0)
2380         (ashift:SI (subreg:SI (match_dup 1) 0)
2381                    (match_dup 2)))]
2382   "
2383 {
2384   int amount = INTVAL (operands[2]);
2385   operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31));
2386   operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31));
2387 }")
2388
2389
2390 (define_split
2391   [(set (match_operand:DI 0 "register_operand" "")
2392         (ashift:DI (match_operand:DI 1 "register_operand" "")
2393                    (match_operand:SI 2 "small_int" "")))
2394    (clobber (match_operand:SI 3 "register_operand" ""))]
2395   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2396    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
2397    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
2398    && (INTVAL (operands[2]) & 63) < 32
2399    && (INTVAL (operands[2]) & 63) != 0"
2400
2401   [(set (subreg:SI (match_dup 0) 0)
2402         (ashift:SI (subreg:SI (match_dup 1) 0)
2403                    (match_dup 2)))
2404
2405    (set (match_dup 3)
2406         (lshiftrt:SI (subreg:SI (match_dup 1) 1)
2407                      (match_dup 4)))
2408
2409    (set (subreg:SI (match_dup 0) 0)
2410         (ior:SI (subreg:SI (match_dup 0) 0)
2411                 (match_dup 3)))
2412
2413    (set (subreg:SI (match_dup 0) 1)
2414         (ashift:SI (subreg:SI (match_dup 1) 1)
2415                    (match_dup 2)))]
2416   "
2417 {
2418   int amount = INTVAL (operands[2]);
2419   operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31));
2420   operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31));
2421 }")
2422
2423
2424 (define_insn "ashrsi3"
2425   [(set (match_operand:SI 0 "register_operand" "=d")
2426         (ashiftrt:SI (match_operand:SI 1 "register_operand" "d")
2427                      (match_operand:SI 2 "arith_operand" "dI")))]
2428   ""
2429   "*
2430 {
2431   if (GET_CODE (operands[2]) == CONST_INT)
2432     operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);
2433
2434   return \"sra\\t%0,%1,%2\";
2435 }"
2436   [(set_attr "type"     "arith")
2437    (set_attr "mode"     "SI")
2438    (set_attr "length"   "1")])
2439
2440
2441 (define_expand "ashrdi3"
2442   [(parallel [(set (match_operand:DI 0 "register_operand" "")
2443                    (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
2444                                 (match_operand:SI 2 "arith_operand" "")))
2445               (clobber (match_dup  3))])]
2446   "!TARGET_DEBUG_G_MODE"
2447   "operands[3] = gen_reg_rtx (SImode);")
2448
2449
2450 (define_insn "ashrdi3_internal"
2451   [(set (match_operand:DI 0 "register_operand" "=&d")
2452         (ashiftrt:DI (match_operand:DI 1 "register_operand" "d")
2453                      (match_operand:SI 2 "register_operand" "d")))
2454    (clobber (match_operand:SI 3 "register_operand" "=d"))]
2455   "!TARGET_DEBUG_G_MODE"
2456   "* 
2457 {
2458   operands[4] = const0_rtx;
2459   dslots_jump_total += 3;
2460   dslots_jump_filled += 2;
2461
2462   return \"sll\\t%3,%2,26\\n\\
2463 \\tbgez\\t%3,1f\\n\\
2464 \\tsra\\t%L0,%M1,%2\\n\\
2465 \\t%(b\\t3f\\n\\
2466 \\tsra\\t%M0,%M1,31%)\\n\\
2467 \\n\\
2468 1:\\n\\
2469 \\t%(beq\\t%3,%z4,2f\\n\\
2470 \\tsrl\\t%L0,%L1,%2%)\\n\\
2471 \\n\\
2472 \\tsubu\\t%3,%z4,%2\\n\\
2473 \\tsll\\t%3,%M1,%3\\n\\
2474 \\tor\\t%L0,%L0,%3\\n\\
2475 2:\\n\\
2476 \\tsra\\t%M0,%M1,%2\\n\\
2477 3:\";
2478 }"
2479   [(set_attr "type"     "darith")
2480    (set_attr "mode"     "DI")
2481    (set_attr "length"   "12")])
2482
2483
2484 (define_insn "ashrdi3_internal2"
2485   [(set (match_operand:DI 0 "register_operand" "=d")
2486         (ashiftrt:DI (match_operand:DI 1 "register_operand" "d")
2487                      (match_operand:SI 2 "small_int" "IJK")))
2488    (clobber (match_operand:SI 3 "register_operand" "=d"))]
2489   "!TARGET_DEBUG_G_MODE && (INTVAL (operands[2]) & 32) != 0"
2490   "*
2491 {
2492   operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);
2493   return \"sra\\t%L0,%M1,%2\;sra\\t%M0,%M1,31\";
2494 }"
2495   [(set_attr "type"     "darith")
2496    (set_attr "mode"     "DI")
2497    (set_attr "length"   "2")])
2498
2499
2500 (define_split
2501   [(set (match_operand:DI 0 "register_operand" "")
2502         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
2503                      (match_operand:SI 2 "small_int" "")))
2504    (clobber (match_operand:SI 3 "register_operand" ""))]
2505   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2506    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
2507    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
2508    && (INTVAL (operands[2]) & 32) != 0"
2509
2510   [(set (subreg:SI (match_dup 0) 0) (ashiftrt:SI (subreg:SI (match_dup 1) 1) (match_dup 2)))
2511    (set (subreg:SI (match_dup 0) 1) (ashiftrt:SI (subreg:SI (match_dup 1) 1) (const_int 31)))]
2512
2513   "operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);")
2514
2515
2516 (define_split
2517   [(set (match_operand:DI 0 "register_operand" "")
2518         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
2519                      (match_operand:SI 2 "small_int" "")))
2520    (clobber (match_operand:SI 3 "register_operand" ""))]
2521   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2522    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
2523    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
2524    && (INTVAL (operands[2]) & 32) != 0"
2525
2526   [(set (subreg:SI (match_dup 0) 1) (ashiftrt:SI (subreg:SI (match_dup 1) 0) (match_dup 2)))
2527    (set (subreg:SI (match_dup 0) 0) (ashiftrt:SI (subreg:SI (match_dup 1) 0) (const_int 31)))]
2528
2529   "operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);")
2530
2531
2532 (define_insn "ashrdi3_internal3"
2533   [(set (match_operand:DI 0 "register_operand" "=d")
2534         (ashiftrt:DI (match_operand:DI 1 "register_operand" "d")
2535                      (match_operand:SI 2 "small_int" "IJK")))
2536    (clobber (match_operand:SI 3 "register_operand" "=d"))]
2537   "!TARGET_DEBUG_G_MODE
2538    && (INTVAL (operands[2]) & 63) < 32
2539    && (INTVAL (operands[2]) & 63) != 0"
2540   "*
2541 {
2542   int amount = INTVAL (operands[2]);
2543
2544   operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31));
2545   operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31));
2546
2547   return \"srl\\t%L0,%L1,%2\;sll\\t%3,%M1,%4\;or\\t%L0,%L0,%3\;sra\\t%M0,%M1,%2\";
2548 }"
2549   [(set_attr "type"     "darith")
2550    (set_attr "mode"     "DI")
2551    (set_attr "length"   "4")])
2552
2553
2554 (define_split
2555   [(set (match_operand:DI 0 "register_operand" "")
2556         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
2557                      (match_operand:SI 2 "small_int" "")))
2558    (clobber (match_operand:SI 3 "register_operand" ""))]
2559   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2560    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
2561    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
2562    && (INTVAL (operands[2]) & 63) < 32
2563    && (INTVAL (operands[2]) & 63) != 0"
2564
2565   [(set (subreg:SI (match_dup 0) 0)
2566         (lshiftrt:SI (subreg:SI (match_dup 1) 0)
2567                      (match_dup 2)))
2568
2569    (set (match_dup 3)
2570         (ashift:SI (subreg:SI (match_dup 1) 1)
2571                    (match_dup 4)))
2572
2573    (set (subreg:SI (match_dup 0) 0)
2574         (ior:SI (subreg:SI (match_dup 0) 0)
2575                 (match_dup 3)))
2576
2577    (set (subreg:SI (match_dup 0) 1)
2578         (ashiftrt:SI (subreg:SI (match_dup 1) 1)
2579                      (match_dup 2)))]
2580   "
2581 {
2582   int amount = INTVAL (operands[2]);
2583   operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31));
2584   operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31));
2585 }")
2586
2587
2588 (define_split
2589   [(set (match_operand:DI 0 "register_operand" "")
2590         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
2591                      (match_operand:SI 2 "small_int" "")))
2592    (clobber (match_operand:SI 3 "register_operand" ""))]
2593   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2594    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
2595    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
2596    && (INTVAL (operands[2]) & 63) < 32
2597    && (INTVAL (operands[2]) & 63) != 0"
2598
2599   [(set (subreg:SI (match_dup 0) 1)
2600         (lshiftrt:SI (subreg:SI (match_dup 1) 1)
2601                      (match_dup 2)))
2602
2603    (set (match_dup 3)
2604         (ashift:SI (subreg:SI (match_dup 1) 0)
2605                    (match_dup 4)))
2606
2607    (set (subreg:SI (match_dup 0) 1)
2608         (ior:SI (subreg:SI (match_dup 0) 1)
2609                 (match_dup 3)))
2610
2611    (set (subreg:SI (match_dup 0) 0)
2612         (ashiftrt:SI (subreg:SI (match_dup 1) 0)
2613                      (match_dup 2)))]
2614   "
2615 {
2616   int amount = INTVAL (operands[2]);
2617   operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31));
2618   operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31));
2619 }")
2620
2621
2622 (define_insn "lshrsi3"
2623   [(set (match_operand:SI 0 "register_operand" "=d")
2624         (lshiftrt:SI (match_operand:SI 1 "register_operand" "d")
2625                      (match_operand:SI 2 "arith_operand" "dI")))]
2626   ""
2627   "*
2628 {
2629   if (GET_CODE (operands[2]) == CONST_INT)
2630     operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);
2631
2632   return \"srl\\t%0,%1,%2\";
2633 }"
2634   [(set_attr "type"     "arith")
2635    (set_attr "mode"     "SI")
2636    (set_attr "length"   "1")])
2637
2638
2639 (define_expand "lshrdi3"
2640   [(parallel [(set (match_operand:DI 0 "register_operand" "")
2641                    (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
2642                                 (match_operand:SI 2 "arith_operand" "")))
2643               (clobber (match_dup  3))])]
2644   "!TARGET_DEBUG_G_MODE"
2645   "operands[3] = gen_reg_rtx (SImode);")
2646
2647
2648 (define_insn "lshrdi3_internal"
2649   [(set (match_operand:DI 0 "register_operand" "=&d")
2650         (lshiftrt:DI (match_operand:DI 1 "register_operand" "d")
2651                      (match_operand:SI 2 "register_operand" "d")))
2652    (clobber (match_operand:SI 3 "register_operand" "=d"))]
2653   "!TARGET_DEBUG_G_MODE"
2654   "* 
2655 {
2656   operands[4] = const0_rtx;
2657   dslots_jump_total += 3;
2658   dslots_jump_filled += 2;
2659
2660   return \"sll\\t%3,%2,26\\n\\
2661 \\tbgez\\t%3,1f\\n\\
2662 \\tsrl\\t%L0,%M1,%2\\n\\
2663 \\t%(b\\t3f\\n\\
2664 \\tmove\\t%M0,%z4%)\\n\\
2665 \\n\\
2666 1:\\n\\
2667 \\t%(beq\\t%3,%z4,2f\\n\\
2668 \\tsrl\\t%L0,%L1,%2%)\\n\\
2669 \\n\\
2670 \\tsubu\\t%3,%z4,%2\\n\\
2671 \\tsll\\t%3,%M1,%3\\n\\
2672 \\tor\\t%L0,%L0,%3\\n\\
2673 2:\\n\\
2674 \\tsrl\\t%M0,%M1,%2\\n\\
2675 3:\";
2676 }"
2677   [(set_attr "type"     "darith")
2678    (set_attr "mode"     "DI")
2679    (set_attr "length"   "12")])
2680
2681
2682 (define_insn "lshrdi3_internal2"
2683   [(set (match_operand:DI 0 "register_operand" "=d")
2684         (lshiftrt:DI (match_operand:DI 1 "register_operand" "d")
2685                      (match_operand:SI 2 "small_int" "IJK")))
2686    (clobber (match_operand:SI 3 "register_operand" "=d"))]
2687   "!TARGET_DEBUG_G_MODE && (INTVAL (operands[2]) & 32) != 0"
2688   "*
2689 {
2690   operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);
2691   operands[4] = const0_rtx;
2692   return \"srl\\t%L0,%M1,%2\;move\\t%M0,%z4\";
2693 }"
2694   [(set_attr "type"     "darith")
2695    (set_attr "mode"     "DI")
2696    (set_attr "length"   "2")])
2697
2698
2699 (define_split
2700   [(set (match_operand:DI 0 "register_operand" "")
2701         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
2702                      (match_operand:SI 2 "small_int" "")))
2703    (clobber (match_operand:SI 3 "register_operand" ""))]
2704   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2705    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
2706    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
2707    && (INTVAL (operands[2]) & 32) != 0"
2708
2709   [(set (subreg:SI (match_dup 0) 0) (lshiftrt:SI (subreg:SI (match_dup 1) 1) (match_dup 2)))
2710    (set (subreg:SI (match_dup 0) 1) (const_int 0))]
2711
2712   "operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);")
2713
2714
2715 (define_split
2716   [(set (match_operand:DI 0 "register_operand" "")
2717         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
2718                      (match_operand:SI 2 "small_int" "")))
2719    (clobber (match_operand:SI 3 "register_operand" ""))]
2720   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2721    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
2722    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
2723    && (INTVAL (operands[2]) & 32) != 0"
2724
2725   [(set (subreg:SI (match_dup 0) 1) (lshiftrt:SI (subreg:SI (match_dup 1) 0) (match_dup 2)))
2726    (set (subreg:SI (match_dup 0) 0) (const_int 0))]
2727
2728   "operands[2] = gen_rtx (CONST_INT, VOIDmode, (XINT (operands[2], 0))& 0x1f);")
2729
2730
2731 (define_insn "lshrdi3_internal3"
2732   [(set (match_operand:DI 0 "register_operand" "=d")
2733         (lshiftrt:DI (match_operand:DI 1 "register_operand" "d")
2734                    (match_operand:SI 2 "small_int" "IJK")))
2735    (clobber (match_operand:SI 3 "register_operand" "=d"))]
2736   "!TARGET_DEBUG_G_MODE
2737    && (INTVAL (operands[2]) & 63) < 32
2738    && (INTVAL (operands[2]) & 63) != 0"
2739   "*
2740 {
2741   int amount = INTVAL (operands[2]);
2742
2743   operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31));
2744   operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31));
2745
2746   return \"srl\\t%L0,%L1,%2\;sll\\t%3,%M1,%4\;or\\t%L0,%L0,%3\;srl\\t%M0,%M1,%2\";
2747 }"
2748   [(set_attr "type"     "darith")
2749    (set_attr "mode"     "DI")
2750    (set_attr "length"   "4")])
2751
2752
2753 (define_split
2754   [(set (match_operand:DI 0 "register_operand" "")
2755         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
2756                      (match_operand:SI 2 "small_int" "")))
2757    (clobber (match_operand:SI 3 "register_operand" ""))]
2758   "reload_completed && !WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2759    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
2760    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
2761    && (INTVAL (operands[2]) & 63) < 32
2762    && (INTVAL (operands[2]) & 63) != 0"
2763
2764   [(set (subreg:SI (match_dup 0) 0)
2765         (lshiftrt:SI (subreg:SI (match_dup 1) 0)
2766                      (match_dup 2)))
2767
2768    (set (match_dup 3)
2769         (ashift:SI (subreg:SI (match_dup 1) 1)
2770                    (match_dup 4)))
2771
2772    (set (subreg:SI (match_dup 0) 0)
2773         (ior:SI (subreg:SI (match_dup 0) 0)
2774                 (match_dup 3)))
2775
2776    (set (subreg:SI (match_dup 0) 1)
2777         (lshiftrt:SI (subreg:SI (match_dup 1) 1)
2778                      (match_dup 2)))]
2779   "
2780 {
2781   int amount = INTVAL (operands[2]);
2782   operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31));
2783   operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31));
2784 }")
2785
2786
2787 (define_split
2788   [(set (match_operand:DI 0 "register_operand" "")
2789         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
2790                      (match_operand:SI 2 "small_int" "")))
2791    (clobber (match_operand:SI 3 "register_operand" ""))]
2792   "reload_completed && WORDS_BIG_ENDIAN && !TARGET_DEBUG_D_MODE && !TARGET_DEBUG_G_MODE
2793    && GET_CODE (operands[0]) == REG && REGNO (operands[0]) < FIRST_PSEUDO_REGISTER
2794    && GET_CODE (operands[1]) == REG && REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
2795    && (INTVAL (operands[2]) & 63) < 32
2796    && (INTVAL (operands[2]) & 63) != 0"
2797
2798   [(set (subreg:SI (match_dup 0) 1)
2799         (lshiftrt:SI (subreg:SI (match_dup 1) 1)
2800                      (match_dup 2)))
2801
2802    (set (match_dup 3)
2803         (ashift:SI (subreg:SI (match_dup 1) 0)
2804                    (match_dup 4)))
2805
2806    (set (subreg:SI (match_dup 0) 1)
2807         (ior:SI (subreg:SI (match_dup 0) 1)
2808                 (match_dup 3)))
2809
2810    (set (subreg:SI (match_dup 0) 0)
2811         (lshiftrt:SI (subreg:SI (match_dup 1) 0)
2812                      (match_dup 2)))]
2813   "
2814 {
2815   int amount = INTVAL (operands[2]);
2816   operands[2] = gen_rtx (CONST_INT, VOIDmode, (amount & 31));
2817   operands[4] = gen_rtx (CONST_INT, VOIDmode, ((-amount) & 31));
2818 }")
2819
2820 \f
2821 ;;
2822 ;;  ....................
2823 ;;
2824 ;;      COMPARISONS
2825 ;;
2826 ;;  ....................
2827
2828 ;; Flow here is rather complex:
2829 ;;
2830 ;;  1)  The cmp{si,sf,df} routine is called.  It deposits the
2831 ;;      arguments into the branch_cmp array, and the type into
2832 ;;      branch_type.  No RTL is generated.
2833 ;;
2834 ;;  2)  The appropriate branch define_expand is called, which then
2835 ;;      creates the appropriate RTL for the comparison and branch.
2836 ;;      Different CC modes are used, based on what type of branch is
2837 ;;      done, so that we can constrain things appropriately.  There
2838 ;;      are assumptions in the rest of GCC that break if we fold the
2839 ;;      operands into the branchs for integer operations, and use cc0
2840 ;;      for floating point, so we use the fp status register instead.
2841 ;;      If needed, an appropriate temporary is created to hold the
2842 ;;      of the integer compare.
2843
2844 (define_expand "cmpsi"
2845   [(set (cc0)
2846         (compare:CC (match_operand:SI 0 "register_operand" "")
2847                     (match_operand:SI 1 "arith_operand" "")))]
2848   ""
2849   "
2850 {
2851   if (operands[0])              /* avoid unused code message */
2852     {
2853       branch_cmp[0] = operands[0];
2854       branch_cmp[1] = operands[1];
2855       branch_type = CMP_SI;
2856       DONE;
2857     }
2858 }")
2859
2860 (define_expand "tstsi"
2861   [(set (cc0)
2862         (match_operand:SI 0 "register_operand" ""))]
2863   ""
2864   "
2865 {
2866   if (operands[0])              /* avoid unused code message */
2867     {
2868       branch_cmp[0] = operands[0];
2869       branch_cmp[1] = const0_rtx;
2870       branch_type = CMP_SI;
2871       DONE;
2872     }
2873 }")
2874
2875 (define_expand "cmpdf"
2876   [(set (cc0)
2877         (compare:CC_FP (match_operand:DF 0 "register_operand" "")
2878                        (match_operand:DF 1 "register_operand" "")))]
2879   "TARGET_HARD_FLOAT"
2880   "
2881 {
2882   if (operands[0])              /* avoid unused code message */
2883     {
2884       branch_cmp[0] = operands[0];
2885       branch_cmp[1] = operands[1];
2886       branch_type = CMP_DF;
2887       DONE;
2888     }
2889 }")
2890
2891 (define_expand "cmpsf"
2892   [(set (cc0)
2893         (compare:CC_FP (match_operand:SF 0 "register_operand" "")
2894                        (match_operand:SF 1 "register_operand" "")))]
2895   "TARGET_HARD_FLOAT"
2896   "
2897 {
2898   if (operands[0])              /* avoid unused code message */
2899     {
2900       branch_cmp[0] = operands[0];
2901       branch_cmp[1] = operands[1];
2902       branch_type = CMP_SF;
2903       DONE;
2904     }
2905 }")
2906
2907 \f
2908 ;;
2909 ;;  ....................
2910 ;;
2911 ;;      CONDITIONAL BRANCHES
2912 ;;
2913 ;;  ....................
2914
2915 (define_insn "branch_fp_ne"
2916   [(set (pc)
2917         (if_then_else (ne:CC_FP (reg:CC_FP 66)
2918                                 (const_int 0))
2919                       (match_operand 0 "pc_or_label_operand" "")
2920                       (match_operand 1 "pc_or_label_operand" "")))]
2921   ""
2922   "*
2923 {
2924   mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn));
2925   return (operands[0] != pc_rtx) ? \"%*bc1t%?\\t%0\" : \"%*bc1f%?\\t%1\";
2926 }"
2927   [(set_attr "type"     "branch")
2928    (set_attr "mode"     "none")
2929    (set_attr "length"   "1")])
2930
2931 (define_insn "branch_fp_ne_rev"
2932   [(set (pc)
2933         (if_then_else (ne:CC_REV_FP (reg:CC_REV_FP 66)
2934                                     (const_int 0))
2935                       (match_operand 0 "pc_or_label_operand" "")
2936                       (match_operand 1 "pc_or_label_operand" "")))]
2937   ""
2938   "*
2939 {
2940   mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn));
2941   return (operands[0] != pc_rtx) ? \"%*bc1f%?\\t%0\" : \"%*bc1t%?\\t%1\";
2942 }"
2943   [(set_attr "type"     "branch")
2944    (set_attr "mode"     "none")
2945    (set_attr "length"   "1")])
2946
2947 (define_insn "branch_fp_eq"
2948   [(set (pc)
2949         (if_then_else (eq:CC_FP (reg:CC_FP 66)
2950                                 (const_int 0))
2951                       (match_operand 0 "pc_or_label_operand" "")
2952                       (match_operand 1 "pc_or_label_operand" "")))]
2953   ""
2954   "*
2955 {
2956   mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn));
2957   return (operands[0] != pc_rtx) ? \"%*bc1f%?\\t%0\" : \"%*bc1t%?\\t%1\";
2958 }"
2959   [(set_attr "type"     "branch")
2960    (set_attr "mode"     "none")
2961    (set_attr "length"   "1")])
2962
2963 (define_insn "branch_fp_eq_rev"
2964   [(set (pc)
2965         (if_then_else (eq:CC_REV_FP (reg:CC_REV_FP 66)
2966                                     (const_int 0))
2967                       (match_operand 0 "pc_or_label_operand" "")
2968                       (match_operand 1 "pc_or_label_operand" "")))]
2969   ""
2970   "*
2971 {
2972   mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn));
2973   return (operands[0] != pc_rtx) ? \"%*bc1t%?\\t%0\" : \"%*bc1f%?\\t%1\";
2974 }"
2975   [(set_attr "type"     "branch")
2976    (set_attr "mode"     "none")
2977    (set_attr "length"   "1")])
2978
2979
2980 (define_insn "branch_zero"
2981   [(set (pc)
2982         (if_then_else (match_operator:SI 0 "cmp_op"
2983                                          [(match_operand:SI 1 "register_operand" "d")
2984                                           (const_int 0)])
2985         (match_operand 2 "pc_or_label_operand" "")
2986         (match_operand 3 "pc_or_label_operand" "")))]
2987   ""
2988   "*
2989 {
2990   mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn));
2991   if (operands[2] != pc_rtx)
2992     {                           /* normal jump */
2993       switch (GET_CODE (operands[0]))
2994         {
2995         case EQ:  return \"%*beq%?\\t%z1,%.,%2\";
2996         case NE:  return \"%*bne%?\\t%z1,%.,%2\";
2997         case GTU: return \"%*bne%?\\t%z1,%.,%2\";
2998         case LEU: return \"%*beq%?\\t%z1,%.,%2\";
2999         case GEU: return \"%*j\\t%2\";
3000         case LTU: return \"%*bne%?\\t%.,%.,%2\";
3001         }
3002
3003       return \"%*b%C0z%?\\t%z1,%2\";
3004     }
3005   else
3006     {                           /* inverted jump */
3007       switch (GET_CODE (operands[0]))
3008         {
3009         case EQ:  return \"%*bne%?\\t%z1,%.,%3\";
3010         case NE:  return \"%*beq%?\\t%z1,%.,%3\";
3011         case GTU: return \"%*beq%?\\t%z1,%.,%3\";
3012         case LEU: return \"%*bne%?\\t%z1,%.,%3\";
3013         case GEU: return \"%*beq%?\\t%.,%.,%3\";
3014         case LTU: return \"%*j\\t%3\";
3015         }
3016
3017       return \"%*b%N0z%?\\t%z1,%3\";
3018     }
3019 }"
3020   [(set_attr "type"     "branch")
3021    (set_attr "mode"     "none")
3022    (set_attr "length"   "1")])
3023
3024
3025 (define_insn "branch_equality"
3026   [(set (pc)
3027         (if_then_else (match_operator:SI 0 "equality_op"
3028                                          [(match_operand:SI 1 "register_operand" "d")
3029                                           (match_operand:SI 2 "register_operand" "d")])
3030         (match_operand 3 "pc_or_label_operand" "")
3031         (match_operand 4 "pc_or_label_operand" "")))]
3032   ""
3033   "*
3034 {
3035   mips_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn));
3036   return (operands[3] != pc_rtx)
3037         ? \"%*b%C0%?\\t%z1,%z2,%3\"
3038         : \"%*b%N0%?\\t%z1,%z2,%4\";
3039 }"
3040   [(set_attr "type"     "branch")
3041    (set_attr "mode"     "none")
3042    (set_attr "length"   "1")])
3043
3044
3045 (define_expand "beq"
3046   [(set (pc)
3047         (if_then_else (eq:CC_EQ (cc0)
3048                                 (const_int 0))
3049                       (label_ref (match_operand 0 "" ""))
3050                       (pc)))]
3051   ""
3052   "
3053 {
3054   if (operands[0])              /* avoid unused code warning */
3055     {
3056       gen_conditional_branch (operands, EQ);
3057       DONE;
3058     }
3059 }")
3060
3061 (define_expand "bne"
3062   [(set (pc)
3063         (if_then_else (ne:CC_EQ (cc0)
3064                                 (const_int 0))
3065                       (label_ref (match_operand 0 "" ""))
3066                       (pc)))]
3067   ""
3068   "
3069 {
3070   if (operands[0])              /* avoid unused code warning */
3071     {
3072       gen_conditional_branch (operands, NE);
3073       DONE;
3074     }
3075 }")
3076
3077 (define_expand "bgt"
3078   [(set (pc)
3079         (if_then_else (gt:CC (cc0)
3080                              (const_int 0))
3081                       (label_ref (match_operand 0 "" ""))
3082                       (pc)))]
3083   ""
3084   "
3085 {
3086   if (operands[0])              /* avoid unused code warning */
3087     {
3088       gen_conditional_branch (operands, GT);
3089       DONE;
3090     }
3091 }")
3092
3093 (define_expand "bge"
3094   [(set (pc)
3095         (if_then_else (ge:CC (cc0)
3096                              (const_int 0))
3097                       (label_ref (match_operand 0 "" ""))
3098                       (pc)))]
3099   ""
3100   "
3101 {
3102   if (operands[0])              /* avoid unused code warning */
3103     {
3104       gen_conditional_branch (operands, GE);
3105       DONE;
3106     }
3107 }")
3108
3109 (define_expand "blt"
3110   [(set (pc)
3111         (if_then_else (lt:CC (cc0)
3112                              (const_int 0))
3113                       (label_ref (match_operand 0 "" ""))
3114                       (pc)))]
3115   ""
3116   "
3117 {
3118   if (operands[0])              /* avoid unused code warning */
3119     {
3120       gen_conditional_branch (operands, LT);
3121       DONE;
3122     }
3123 }")
3124
3125 (define_expand "ble"
3126   [(set (pc)
3127         (if_then_else (le:CC (cc0)
3128                              (const_int 0))
3129                       (label_ref (match_operand 0 "" ""))
3130                       (pc)))]
3131   ""
3132   "
3133 {
3134   if (operands[0])              /* avoid unused code warning */
3135     {
3136       gen_conditional_branch (operands, LE);
3137       DONE;
3138     }
3139 }")
3140
3141 (define_expand "bgtu"
3142   [(set (pc)
3143         (if_then_else (gtu:CC (cc0)
3144                               (const_int 0))
3145                       (label_ref (match_operand 0 "" ""))
3146                       (pc)))]
3147   ""
3148   "
3149 {
3150   if (operands[0])              /* avoid unused code warning */
3151     {
3152       gen_conditional_branch (operands, GTU);
3153       DONE;
3154     }
3155 }")
3156
3157 (define_expand "bgeu"
3158   [(set (pc)
3159         (if_then_else (geu:CC (cc0)
3160                               (const_int 0))
3161                       (label_ref (match_operand 0 "" ""))
3162                       (pc)))]
3163   ""
3164   "
3165 {
3166   if (operands[0])              /* avoid unused code warning */
3167     {
3168       gen_conditional_branch (operands, GEU);
3169       DONE;
3170     }
3171 }")
3172
3173
3174 (define_expand "bltu"
3175   [(set (pc)
3176         (if_then_else (ltu:CC (cc0)
3177                               (const_int 0))
3178                       (label_ref (match_operand 0 "" ""))
3179                       (pc)))]
3180   ""
3181   "
3182 {
3183   if (operands[0])              /* avoid unused code warning */
3184     {
3185       gen_conditional_branch (operands, LTU);
3186       DONE;
3187     }
3188 }")
3189
3190 (define_expand "bleu"
3191   [(set (pc)
3192         (if_then_else (leu:CC (cc0)
3193                               (const_int 0))
3194                       (label_ref (match_operand 0 "" ""))
3195                       (pc)))]
3196   ""
3197   "
3198 {
3199   if (operands[0])              /* avoid unused code warning */
3200     {
3201       gen_conditional_branch (operands, LEU);
3202       DONE;
3203     }
3204 }")
3205
3206 \f
3207 ;;
3208 ;;  ....................
3209 ;;
3210 ;;      SETTING A REGISTER FROM A COMPARISON
3211 ;;
3212 ;;  ....................
3213
3214 (define_expand "seq"
3215   [(set (match_operand:SI 0 "register_operand" "=d")
3216         (eq:SI (match_dup 1)
3217                (match_dup 2)))]
3218   ""
3219   "
3220 {
3221   if (branch_type != CMP_SI)
3222     FAIL;
3223
3224   /* set up operands from compare.  */
3225   operands[1] = branch_cmp[0];
3226   operands[2] = branch_cmp[1];
3227
3228   if (!TARGET_DEBUG_C_MODE)
3229     {
3230       gen_int_relational (EQ, operands[0], operands[1], operands[2], (int *)0);
3231       DONE;
3232     }
3233
3234   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
3235     operands[2] = force_reg (SImode, operands[2]);
3236
3237   /* fall through and generate default code */
3238 }")
3239
3240
3241 (define_insn "seq_si_zero"
3242   [(set (match_operand:SI 0 "register_operand" "=d")
3243         (eq:SI (match_operand:SI 1 "register_operand" "d")
3244                (const_int 0)))]
3245   ""
3246   "sltu\\t%0,%1,1"
3247  [(set_attr "type"      "arith")
3248    (set_attr "mode"     "SI")
3249    (set_attr "length"   "1")])
3250
3251 (define_insn "seq_si"
3252   [(set (match_operand:SI 0 "register_operand" "=d,d")
3253         (eq:SI (match_operand:SI 1 "register_operand" "%d,d")
3254                (match_operand:SI 2 "uns_arith_operand" "d,K")))]
3255   "TARGET_DEBUG_C_MODE"
3256   "@
3257    xor\\t%0,%1,%2\;sltu\\t%0,%0,1
3258    xori\\t%0,%1,%2\;sltu\\t%0,%0,1"
3259  [(set_attr "type"      "arith")
3260    (set_attr "mode"     "SI")
3261    (set_attr "length"   "2")])
3262
3263 (define_split
3264   [(set (match_operand:SI 0 "register_operand" "")
3265         (eq:SI (match_operand:SI 1 "register_operand" "")
3266                (match_operand:SI 2 "uns_arith_operand" "")))]
3267   "TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE
3268     && (GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != 0)"
3269   [(set (match_dup 0)
3270         (xor:SI (match_dup 1)
3271                 (match_dup 2)))
3272    (set (match_dup 0)
3273         (ltu:SI (match_dup 0)
3274                 (const_int 1)))]
3275   "")
3276
3277 (define_expand "sne"
3278   [(set (match_operand:SI 0 "register_operand" "=d")
3279         (ne:SI (match_dup 1)
3280                (match_dup 2)))]
3281   ""
3282   "
3283 {
3284   if (branch_type != CMP_SI)
3285     FAIL;
3286
3287   /* set up operands from compare.  */
3288   operands[1] = branch_cmp[0];
3289   operands[2] = branch_cmp[1];
3290
3291   if (!TARGET_DEBUG_C_MODE)
3292     {
3293       gen_int_relational (NE, operands[0], operands[1], operands[2], (int *)0);
3294       DONE;
3295     }
3296
3297   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
3298     operands[2] = force_reg (SImode, operands[2]);
3299
3300   /* fall through and generate default code */
3301 }")
3302
3303 (define_insn "sne_si_zero"
3304   [(set (match_operand:SI 0 "register_operand" "=d")
3305         (ne:SI (match_operand:SI 1 "register_operand" "d")
3306                (const_int 0)))]
3307   ""
3308   "sltu\\t%0,%.,%1"
3309  [(set_attr "type"      "arith")
3310    (set_attr "mode"     "SI")
3311    (set_attr "length"   "1")])
3312
3313 (define_insn "sne_si"
3314   [(set (match_operand:SI 0 "register_operand" "=d,d")
3315         (ne:SI (match_operand:SI 1 "register_operand" "%d,d")
3316                (match_operand:SI 2 "uns_arith_operand" "d,K")))]
3317   "TARGET_DEBUG_C_MODE"
3318   "@
3319     xor\\t%0,%1,%2\;sltu\\t%0,%.,%0
3320     xori\\t%0,%1,%x2\;sltu\\t%0,%.,%0"
3321  [(set_attr "type"      "arith")
3322    (set_attr "mode"     "SI")
3323    (set_attr "length"   "2")])
3324
3325 (define_split
3326   [(set (match_operand:SI 0 "register_operand" "")
3327         (ne:SI (match_operand:SI 1 "register_operand" "")
3328                (match_operand:SI 2 "uns_arith_operand" "")))]
3329   "TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE
3330     && (GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != 0)"
3331   [(set (match_dup 0)
3332         (xor:SI (match_dup 1)
3333                 (match_dup 2)))
3334    (set (match_dup 0)
3335         (gtu:SI (match_dup 0)
3336                 (const_int 0)))]
3337   "")
3338
3339 (define_expand "sgt"
3340   [(set (match_operand:SI 0 "register_operand" "=d")
3341         (gt:SI (match_dup 1)
3342                (match_dup 2)))]
3343   ""
3344   "
3345 {
3346   if (branch_type != CMP_SI)
3347     FAIL;
3348
3349   /* set up operands from compare.  */
3350   operands[1] = branch_cmp[0];
3351   operands[2] = branch_cmp[1];
3352
3353   if (!TARGET_DEBUG_C_MODE)
3354     {
3355       gen_int_relational (GT, operands[0], operands[1], operands[2], (int *)0);
3356       DONE;
3357     }
3358
3359   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) != 0)
3360     operands[2] = force_reg (SImode, operands[2]);
3361
3362   /* fall through and generate default code */
3363 }")
3364
3365 (define_insn "sgt_si"
3366   [(set (match_operand:SI 0 "register_operand" "=d")
3367         (gt:SI (match_operand:SI 1 "register_operand" "d")
3368                (match_operand:SI 2 "reg_or_0_operand" "dJ")))]
3369   ""
3370   "slt\\t%0,%z2,%1"
3371  [(set_attr "type"      "arith")
3372    (set_attr "mode"     "SI")
3373    (set_attr "length"   "1")])
3374
3375 (define_expand "sge"
3376   [(set (match_operand:SI 0 "register_operand" "=d")
3377         (ge:SI (match_dup 1)
3378                (match_dup 2)))]
3379   ""
3380   "
3381 {
3382   if (branch_type != CMP_SI)
3383     FAIL;
3384
3385   /* set up operands from compare.  */
3386   operands[1] = branch_cmp[0];
3387   operands[2] = branch_cmp[1];
3388
3389   if (!TARGET_DEBUG_C_MODE)
3390     {
3391       gen_int_relational (GE, operands[0], operands[1], operands[2], (int *)0);
3392       DONE;
3393     }
3394
3395   /* fall through and generate default code */
3396 }")
3397
3398 (define_insn "sge_si"
3399   [(set (match_operand:SI 0 "register_operand" "=d")
3400         (ge:SI (match_operand:SI 1 "register_operand" "d")
3401                (match_operand:SI 2 "arith_operand" "dI")))]
3402   "TARGET_DEBUG_C_MODE"
3403   "slt\\t%0,%1,%2\;xori\\t%0,%0,0x0001"
3404  [(set_attr "type"      "arith")
3405    (set_attr "mode"     "SI")
3406    (set_attr "length"   "2")])
3407
3408 (define_split
3409   [(set (match_operand:SI 0 "register_operand" "")
3410         (ge:SI (match_operand:SI 1 "register_operand" "")
3411                (match_operand:SI 2 "arith_operand" "")))]
3412   "TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE"
3413   [(set (match_dup 0)
3414         (lt:SI (match_dup 1)
3415                (match_dup 2)))
3416    (set (match_dup 0)
3417         (xor:SI (match_dup 0)
3418                 (const_int 1)))]
3419   "")
3420
3421 (define_expand "slt"
3422   [(set (match_operand:SI 0 "register_operand" "=d")
3423         (lt:SI (match_dup 1)
3424                (match_dup 2)))]
3425   ""
3426   "
3427 {
3428   if (branch_type != CMP_SI)
3429     FAIL;
3430
3431   /* set up operands from compare.  */
3432   operands[1] = branch_cmp[0];
3433   operands[2] = branch_cmp[1];
3434
3435   if (!TARGET_DEBUG_C_MODE)
3436     {
3437       gen_int_relational (LT, operands[0], operands[1], operands[2], (int *)0);
3438       DONE;
3439     }
3440
3441   /* fall through and generate default code */
3442 }")
3443
3444 (define_insn "slt_si"
3445   [(set (match_operand:SI 0 "register_operand" "=d")
3446         (lt:SI (match_operand:SI 1 "register_operand" "d")
3447                (match_operand:SI 2 "arith_operand" "dI")))]
3448   ""
3449   "slt\\t%0,%1,%2"
3450  [(set_attr "type"      "arith")
3451    (set_attr "mode"     "SI")
3452    (set_attr "length"   "1")])
3453
3454 (define_expand "sle"
3455   [(set (match_operand:SI 0 "register_operand" "=d")
3456         (le:SI (match_dup 1)
3457                (match_dup 2)))]
3458   ""
3459   "
3460 {
3461   if (branch_type != CMP_SI)
3462     FAIL;
3463
3464   /* set up operands from compare.  */
3465   operands[1] = branch_cmp[0];
3466   operands[2] = branch_cmp[1];
3467
3468   if (!TARGET_DEBUG_C_MODE)
3469     {
3470       gen_int_relational (LE, operands[0], operands[1], operands[2], (int *)0);
3471       DONE;
3472     }
3473
3474   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32767)
3475     operands[2] = force_reg (SImode, operands[2]);
3476
3477   /* fall through and generate default code */
3478 }")
3479
3480 (define_insn "sle_si_const"
3481   [(set (match_operand:SI 0 "register_operand" "=d")
3482         (le:SI (match_operand:SI 1 "register_operand" "d")
3483                (match_operand:SI 2 "small_int" "I")))]
3484   "INTVAL (operands[2]) < 32767"
3485   "*
3486 {
3487   operands[2] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[2])+1);
3488   return \"slt\\t%0,%1,%2\";
3489 }"
3490  [(set_attr "type"      "arith")
3491    (set_attr "mode"     "SI")
3492    (set_attr "length"   "1")])
3493
3494 (define_insn "sle_si_reg"
3495   [(set (match_operand:SI 0 "register_operand" "=d")
3496         (le:SI (match_operand:SI 1 "register_operand" "d")
3497                (match_operand:SI 2 "register_operand" "d")))]
3498   "TARGET_DEBUG_C_MODE"
3499   "slt\\t%0,%z2,%1\;xori\\t%0,%0,0x0001"
3500  [(set_attr "type"      "arith")
3501    (set_attr "mode"     "SI")
3502    (set_attr "length"   "2")])
3503
3504 (define_split
3505   [(set (match_operand:SI 0 "register_operand" "")
3506         (le:SI (match_operand:SI 1 "register_operand" "")
3507                (match_operand:SI 2 "register_operand" "")))]
3508   "TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE"
3509   [(set (match_dup 0)
3510         (lt:SI (match_dup 2)
3511                (match_dup 1)))
3512    (set (match_dup 0)
3513         (xor:SI (match_dup 0)
3514                 (const_int 1)))]
3515   "")
3516
3517 (define_expand "sgtu"
3518   [(set (match_operand:SI 0 "register_operand" "=d")
3519         (gtu:SI (match_dup 1)
3520                 (match_dup 2)))]
3521   ""
3522   "
3523 {
3524   if (branch_type != CMP_SI)
3525     FAIL;
3526
3527   /* set up operands from compare.  */
3528   operands[1] = branch_cmp[0];
3529   operands[2] = branch_cmp[1];
3530
3531   if (!TARGET_DEBUG_C_MODE)
3532     {
3533       gen_int_relational (GTU, operands[0], operands[1], operands[2], (int *)0);
3534       DONE;
3535     }
3536
3537   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) != 0)
3538     operands[2] = force_reg (SImode, operands[2]);
3539
3540   /* fall through and generate default code */
3541 }")
3542
3543 (define_insn "sgtu_si"
3544   [(set (match_operand:SI 0 "register_operand" "=d")
3545         (gtu:SI (match_operand:SI 1 "register_operand" "d")
3546                 (match_operand:SI 2 "reg_or_0_operand" "dJ")))]
3547   ""
3548   "sltu\\t%0,%z2,%1"
3549  [(set_attr "type"      "arith")
3550    (set_attr "mode"     "SI")
3551    (set_attr "length"   "1")])
3552
3553 (define_expand "sgeu"
3554   [(set (match_operand:SI 0 "register_operand" "=d")
3555         (geu:SI (match_dup 1)
3556                 (match_dup 2)))]
3557   ""
3558   "
3559 {
3560   if (branch_type != CMP_SI)
3561     FAIL;
3562
3563   /* set up operands from compare.  */
3564   operands[1] = branch_cmp[0];
3565   operands[2] = branch_cmp[1];
3566
3567   if (!TARGET_DEBUG_C_MODE)
3568     {
3569       gen_int_relational (GEU, operands[0], operands[1], operands[2], (int *)0);
3570       DONE;
3571     }
3572
3573   /* fall through and generate default code */
3574 }")
3575
3576 (define_insn "sgeu_si"
3577   [(set (match_operand:SI 0 "register_operand" "=d")
3578         (geu:SI (match_operand:SI 1 "register_operand" "d")
3579                 (match_operand:SI 2 "arith_operand" "dI")))]
3580   "TARGET_DEBUG_C_MODE"
3581   "sltu\\t%0,%1,%2\;xori\\t%0,%0,0x0001"
3582  [(set_attr "type"      "arith")
3583    (set_attr "mode"     "SI")
3584    (set_attr "length"   "2")])
3585
3586 (define_split
3587   [(set (match_operand:SI 0 "register_operand" "")
3588         (geu:SI (match_operand:SI 1 "register_operand" "")
3589                 (match_operand:SI 2 "arith_operand" "")))]
3590   "TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE"
3591   [(set (match_dup 0)
3592         (ltu:SI (match_dup 1)
3593                 (match_dup 2)))
3594    (set (match_dup 0)
3595         (xor:SI (match_dup 0)
3596                 (const_int 1)))]
3597   "")
3598
3599 (define_expand "sltu"
3600   [(set (match_operand:SI 0 "register_operand" "=d")
3601         (ltu:SI (match_dup 1)
3602                 (match_dup 2)))]
3603   ""
3604   "
3605 {
3606   if (branch_type != CMP_SI)
3607     FAIL;
3608
3609   /* set up operands from compare.  */
3610   operands[1] = branch_cmp[0];
3611   operands[2] = branch_cmp[1];
3612
3613   if (!TARGET_DEBUG_C_MODE)
3614     {
3615       gen_int_relational (LTU, operands[0], operands[1], operands[2], (int *)0);
3616       DONE;
3617     }
3618
3619   /* fall through and generate default code */
3620 }")
3621
3622 (define_insn "sltu_si"
3623   [(set (match_operand:SI 0 "register_operand" "=d")
3624         (ltu:SI (match_operand:SI 1 "register_operand" "d")
3625                 (match_operand:SI 2 "arith_operand" "dI")))]
3626   ""
3627   "sltu\\t%0,%1,%2"
3628  [(set_attr "type"      "arith")
3629    (set_attr "mode"     "SI")
3630    (set_attr "length"   "1")])
3631
3632 (define_expand "sleu"
3633   [(set (match_operand:SI 0 "register_operand" "=d")
3634         (leu:SI (match_dup 1)
3635                 (match_dup 2)))]
3636   ""
3637   "
3638 {
3639   if (branch_type != CMP_SI)
3640     FAIL;
3641
3642   /* set up operands from compare.  */
3643   operands[1] = branch_cmp[0];
3644   operands[2] = branch_cmp[1];
3645
3646   if (!TARGET_DEBUG_C_MODE)
3647     {
3648       gen_int_relational (LEU, operands[0], operands[1], operands[2], (int *)0);
3649       DONE;
3650     }
3651
3652   if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) >= 32767)
3653     operands[2] = force_reg (SImode, operands[2]);
3654
3655   /* fall through and generate default code */
3656 }")
3657
3658 (define_insn "sleu_si_const"
3659   [(set (match_operand:SI 0 "register_operand" "=d")
3660         (leu:SI (match_operand:SI 1 "register_operand" "d")
3661                 (match_operand:SI 2 "small_int" "I")))]
3662   "INTVAL (operands[2]) < 32767"
3663   "*
3664 {
3665   operands[2] = gen_rtx (CONST_INT, VOIDmode, INTVAL (operands[2])+1);
3666   return \"sltu\\t%0,%1,%2\";
3667 }"
3668  [(set_attr "type"      "arith")
3669    (set_attr "mode"     "SI")
3670    (set_attr "length"   "1")])
3671
3672 (define_insn "sleu_si_reg"
3673   [(set (match_operand:SI 0 "register_operand" "=d")
3674         (leu:SI (match_operand:SI 1 "register_operand" "d")
3675                 (match_operand:SI 2 "register_operand" "d")))]
3676   "TARGET_DEBUG_C_MODE"
3677   "sltu\\t%0,%z2,%1\;xori\\t%0,%0,0x0001"
3678  [(set_attr "type"      "arith")
3679    (set_attr "mode"     "SI")
3680    (set_attr "length"   "2")])
3681
3682 (define_split
3683   [(set (match_operand:SI 0 "register_operand" "")
3684         (leu:SI (match_operand:SI 1 "register_operand" "")
3685                 (match_operand:SI 2 "register_operand" "")))]
3686   "TARGET_DEBUG_C_MODE && !TARGET_DEBUG_D_MODE"
3687   [(set (match_dup 0)
3688         (ltu:SI (match_dup 2)
3689                 (match_dup 1)))
3690    (set (match_dup 0)
3691         (xor:SI (match_dup 0)
3692                 (const_int 1)))]
3693   "")
3694
3695 \f
3696 ;;
3697 ;;  ....................
3698 ;;
3699 ;;      FLOATING POINT COMPARISONS
3700 ;;
3701 ;;  ....................
3702
3703 (define_insn "seq_df"
3704   [(set (reg:CC_FP 66)
3705         (eq:CC_FP (match_operand:DF 0 "register_operand" "f")
3706                   (match_operand:DF 1 "register_operand" "f")))]
3707   ""
3708   "*
3709 {
3710   rtx xoperands[10];
3711   xoperands[0] = gen_rtx (REG, CC_FPmode, FPSW_REGNUM);
3712   xoperands[1] = operands[0];
3713   xoperands[2] = operands[1];
3714
3715   return mips_fill_delay_slot (\"c.eq.d\\t%0,%1\", DELAY_FCMP, xoperands, insn);
3716 }"
3717  [(set_attr "type"      "fcmp")
3718   (set_attr "mode"      "FPSW")
3719   (set_attr "length"    "1")])
3720
3721 (define_insn "sne_df"
3722   [(set (reg:CC_REV_FP 66)
3723         (ne:CC_REV_FP (match_operand:DF 0 "register_operand" "f")
3724                       (match_operand:DF 1 "register_operand" "f")))]
3725   ""
3726   "*
3727 {
3728   rtx xoperands[10];
3729   xoperands[0] = gen_rtx (REG, CC_FPmode, FPSW_REGNUM);
3730   xoperands[1] = operands[0];
3731   xoperands[2] = operands[1];
3732
3733   return mips_fill_delay_slot (\"c.eq.d\\t%0,%1\", DELAY_FCMP, xoperands, insn);
3734 }"
3735  [(set_attr "type"      "fcmp")
3736   (set_attr "mode"      "FPSW")
3737   (set_attr "length"    "1")])
3738
3739 (define_insn "slt_df"
3740   [(set (reg:CC_FP 66)
3741         (lt:CC_FP (match_operand:DF 0 "register_operand" "f")
3742                   (match_operand:DF 1 "register_operand" "f")))]
3743   ""
3744   "*
3745 {
3746   rtx xoperands[10];
3747   xoperands[0] = gen_rtx (REG, CC_FPmode, FPSW_REGNUM);
3748   xoperands[1] = operands[0];
3749   xoperands[2] = operands[1];
3750
3751   return mips_fill_delay_slot (\"c.lt.d\\t%0,%1\", DELAY_FCMP, xoperands, insn);
3752 }"
3753  [(set_attr "type"      "fcmp")
3754   (set_attr "mode"      "FPSW")
3755   (set_attr "length"    "1")])
3756
3757 (define_insn "sle_df"
3758   [(set (reg:CC_FP 66)
3759         (le:CC_FP (match_operand:DF 0 "register_operand" "f")
3760                   (match_operand:DF 1 "register_operand" "f")))]
3761   ""
3762   "*
3763 {
3764   rtx xoperands[10];
3765   xoperands[0] = gen_rtx (REG, CC_FPmode, FPSW_REGNUM);
3766   xoperands[1] = operands[0];
3767   xoperands[2] = operands[1];
3768
3769   return mips_fill_delay_slot (\"c.le.d\\t%0,%1\", DELAY_FCMP, xoperands, insn);
3770 }"
3771  [(set_attr "type"      "fcmp")
3772   (set_attr "mode"      "FPSW")
3773   (set_attr "length"    "1")])
3774
3775 (define_insn "sgt_df"
3776   [(set (reg:CC_FP 66)
3777         (gt:CC_FP (match_operand:DF 0 "register_operand" "f")
3778                   (match_operand:DF 1 "register_operand" "f")))]
3779   ""
3780   "*
3781 {
3782   rtx xoperands[10];
3783   xoperands[0] = gen_rtx (REG, CC_FPmode, FPSW_REGNUM);
3784   xoperands[1] = operands[0];
3785   xoperands[2] = operands[1];
3786
3787   return mips_fill_delay_slot (\"c.lt.d\\t%1,%0\", DELAY_FCMP, xoperands, insn);
3788 }"
3789  [(set_attr "type"      "fcmp")
3790   (set_attr "mode"      "FPSW")
3791   (set_attr "length"    "1")])
3792
3793 (define_insn "sge_df"
3794   [(set (reg:CC_FP 66)
3795         (ge:CC_FP (match_operand:DF 0 "register_operand" "f")
3796                   (match_operand:DF 1 "register_operand" "f")))]
3797   ""
3798   "*
3799 {
3800   rtx xoperands[10];
3801   xoperands[0] = gen_rtx (REG, CC_FPmode, FPSW_REGNUM);
3802   xoperands[1] = operands[0];
3803   xoperands[2] = operands[1];
3804
3805   return mips_fill_delay_slot (\"c.le.d\\t%1,%0\", DELAY_FCMP, xoperands, insn);
3806 }"
3807  [(set_attr "type"      "fcmp")
3808   (set_attr "mode"      "FPSW")
3809   (set_attr "length"    "1")])
3810
3811 (define_insn "seq_sf"
3812   [(set (reg:CC_FP 66)
3813         (eq:CC_FP (match_operand:SF 0 "register_operand" "f")
3814                   (match_operand:SF 1 "register_operand" "f")))]
3815   ""
3816   "*
3817 {
3818   rtx xoperands[10];
3819   xoperands[0] = gen_rtx (REG, CC_FPmode, FPSW_REGNUM);
3820   xoperands[1] = operands[0];
3821   xoperands[2] = operands[1];
3822
3823   return mips_fill_delay_slot (\"c.eq.s\\t%0,%1\", DELAY_FCMP, xoperands, insn);
3824 }"
3825  [(set_attr "type"      "fcmp")
3826   (set_attr "mode"      "FPSW")
3827   (set_attr "length"    "1")])
3828
3829 (define_insn "sne_sf"
3830   [(set (reg:CC_REV_FP 66)
3831         (ne:CC_REV_FP (match_operand:SF 0 "register_operand" "f")
3832                       (match_operand:SF 1 "register_operand" "f")))]
3833   ""
3834   "*
3835 {
3836   rtx xoperands[10];
3837   xoperands[0] = gen_rtx (REG, CC_FPmode, FPSW_REGNUM);
3838   xoperands[1] = operands[0];
3839   xoperands[2] = operands[1];
3840
3841   return mips_fill_delay_slot (\"c.eq.s\\t%0,%1\", DELAY_FCMP, xoperands, insn);
3842 }"
3843  [(set_attr "type"      "fcmp")
3844   (set_attr "mode"      "FPSW")
3845   (set_attr "length"    "1")])
3846
3847 (define_insn "slt_sf"
3848   [(set (reg:CC_FP 66)
3849         (lt:CC_FP (match_operand:SF 0 "register_operand" "f")
3850                   (match_operand:SF 1 "register_operand" "f")))]
3851   ""
3852   "*
3853 {
3854   rtx xoperands[10];
3855   xoperands[0] = gen_rtx (REG, CC_FPmode, FPSW_REGNUM);
3856   xoperands[1] = operands[0];
3857   xoperands[2] = operands[1];
3858
3859   return mips_fill_delay_slot (\"c.lt.s\\t%0,%1\", DELAY_FCMP, xoperands, insn);
3860 }"
3861  [(set_attr "type"      "fcmp")
3862   (set_attr "mode"      "FPSW")
3863   (set_attr "length"    "1")])
3864
3865 (define_insn "sle_sf"
3866   [(set (reg:CC_FP 66)
3867         (le:CC_FP (match_operand:SF 0 "register_operand" "f")
3868                   (match_operand:SF 1 "register_operand" "f")))]
3869   ""
3870   "*
3871 {
3872   rtx xoperands[10];
3873   xoperands[0] = gen_rtx (REG, CC_FPmode, FPSW_REGNUM);
3874   xoperands[1] = operands[0];
3875   xoperands[2] = operands[1];
3876
3877   return mips_fill_delay_slot (\"c.le.s\\t%0,%1\", DELAY_FCMP, xoperands, insn);
3878 }"
3879  [(set_attr "type"      "fcmp")
3880   (set_attr "mode"      "FPSW")
3881   (set_attr "length"    "1")])
3882
3883 (define_insn "sgt_sf"
3884   [(set (reg:CC_FP 66)
3885         (gt:CC_FP (match_operand:SF 0 "register_operand" "f")
3886                   (match_operand:SF 1 "register_operand" "f")))]
3887   ""
3888   "*
3889 {
3890   rtx xoperands[10];
3891   xoperands[0] = gen_rtx (REG, CC_FPmode, FPSW_REGNUM);
3892   xoperands[1] = operands[0];
3893   xoperands[2] = operands[1];
3894
3895   return mips_fill_delay_slot (\"c.lt.s\\t%1,%0\", DELAY_FCMP, xoperands, insn);
3896 }"
3897  [(set_attr "type"      "fcmp")
3898   (set_attr "mode"      "FPSW")
3899   (set_attr "length"    "1")])
3900
3901 (define_insn "sge_sf"
3902   [(set (reg:CC_FP 66)
3903         (ge:CC_FP (match_operand:SF 0 "register_operand" "f")
3904                   (match_operand:SF 1 "register_operand" "f")))]
3905   ""
3906   "*
3907 {
3908   rtx xoperands[10];
3909   xoperands[0] = gen_rtx (REG, CC_FPmode, FPSW_REGNUM);
3910   xoperands[1] = operands[0];
3911   xoperands[2] = operands[1];
3912
3913   return mips_fill_delay_slot (\"c.le.s\\t%1,%0\", DELAY_FCMP, xoperands, insn);
3914 }"
3915  [(set_attr "type"      "fcmp")
3916   (set_attr "mode"      "FPSW")
3917   (set_attr "length"    "1")])
3918
3919 \f
3920 ;;
3921 ;;  ....................
3922 ;;
3923 ;;      UNCONDITIONAL BRANCHES
3924 ;;
3925 ;;  ....................
3926
3927 ;; Unconditional branches.
3928
3929 (define_insn "jump"
3930   [(set (pc)
3931         (label_ref (match_operand 0 "" "")))]
3932   ""
3933   "*
3934 {
3935   if (GET_CODE (operands[0]) == REG)
3936     return \"%*j\\t%0\";
3937   else
3938     return \"%*j\\t%l0\";
3939 }"
3940   [(set_attr "type"     "jump")
3941    (set_attr "mode"     "none")
3942    (set_attr "length"   "1")])
3943
3944 (define_insn "indirect_jump"
3945   [(set (pc) (match_operand:SI 0 "register_operand" "d"))]
3946   ""
3947   "%*j\\t%0"
3948   [(set_attr "type"     "jump")
3949    (set_attr "mode"     "none")
3950    (set_attr "length"   "1")])
3951
3952 (define_insn "tablejump"
3953   [(set (pc)
3954         (match_operand:SI 0 "register_operand" "d"))
3955    (use (label_ref (match_operand 1 "" "")))]
3956   ""
3957   "%*j\\t%0"
3958   [(set_attr "type"     "jump")
3959    (set_attr "mode"     "none")
3960    (set_attr "length"   "1")])
3961
3962 ;; Function return, only allow after optimization, so that we can
3963 ;; eliminate jumps to jumps if no stack space is used.
3964
3965 ;; (define_expand "return"
3966 ;;   [(set (pc) (reg:SI 31))]
3967 ;;   "simple_epilogue_p ()"
3968 ;;   "")
3969
3970 (define_expand "return"
3971   [(parallel [(return)
3972               (use (reg:SI 31))])]
3973   "simple_epilogue_p ()"
3974   "")
3975
3976 (define_insn "return_internal"
3977   [(parallel [(return)
3978               (use (match_operand:SI 0 "register_operand" "d"))])]
3979   ""
3980   "%*j\\t%0"
3981   [(set_attr "type"     "jump")
3982    (set_attr "mode"     "none")
3983    (set_attr "length"   "1")])
3984
3985 \f
3986 ;;
3987 ;;  ....................
3988 ;;
3989 ;;      Function prologue/epilogue
3990 ;;
3991 ;;  ....................
3992 ;;
3993
3994 (define_expand "prologue"
3995   [(const_int 1)]
3996   ""
3997   "
3998 {
3999   if (mips_isa >= 0)            /* avoid unused code warnings */
4000     {
4001       mips_expand_prologue ();
4002       DONE;
4003     }
4004 }")
4005
4006 ;; Block any insns from being moved before this point, since the
4007 ;; profiling call to mcount can use various registers that aren't
4008 ;; saved or used to pass arguments.
4009
4010 (define_insn "blockage"
4011   [(unspec_volatile [(const_int 0)] 0)]
4012   ""
4013   ""
4014   [(set_attr "type"     "unknown")
4015    (set_attr "mode"     "none")
4016    (set_attr "length"   "0")])
4017
4018 ;; At present, don't expand the epilogue, reorg.c will clobber the
4019 ;; return register in compiling gen_lowpart (emit-rtl.c).
4020 ;; 
4021 ;; (define_expand "epilogue"
4022 ;;   [(const_int 2)]
4023 ;;   ""
4024 ;;   "
4025 ;; {
4026 ;;   if (mips_isa >= 0)            /* avoid unused code warnings */
4027 ;;     {
4028 ;;       mips_expand_epilogue ();
4029 ;;       DONE;
4030 ;;     }
4031 ;; }")
4032
4033 \f
4034 ;;
4035 ;;  ....................
4036 ;;
4037 ;;      FUNCTION CALLS
4038 ;;
4039 ;;  ....................
4040
4041 ;; calls.c now passes a third argument, make saber happy
4042
4043 (define_expand "call"
4044   [(parallel [(call (match_operand 0 "memory_operand" "m")
4045                     (match_operand 1 "" "i"))
4046               (clobber (reg:SI 31))
4047               (use (match_operand 2 "" ""))             ;; next_arg_reg
4048               (use (match_operand 3 "" ""))])]          ;; struct_value_size_rtx
4049   ""
4050   "
4051 {
4052   rtx addr;
4053
4054   if (operands[0])              /* eliminate unused code warnings */
4055     {
4056       addr = XEXP (operands[0], 0);
4057       if ((GET_CODE (addr) != REG && (!CONSTANT_ADDRESS_P (addr) || TARGET_LONG_CALLS))
4058           || ! call_insn_operand (operands[0], VOIDmode))
4059         XEXP (operands[0], 0) = copy_to_mode_reg (Pmode, addr);
4060
4061       /* In order to pass small structures by value in registers
4062          compatibly with the MIPS compiler, we need to shift the value
4063          into the high part of the register.  Function_arg has encoded
4064          a PARALLEL rtx, holding a vector of adjustments to be made
4065          as the next_arg_reg variable, so we split up the insns,
4066          and emit them separately.  */
4067
4068       if (operands[2] != (rtx)0 && GET_CODE (operands[2]) == PARALLEL)
4069         {
4070           rtvec adjust = XVEC (operands[2], 0);
4071           int num = GET_NUM_ELEM (adjust);
4072           int i;
4073
4074           for (i = 0; i < num; i++)
4075             emit_insn (RTVEC_ELT (adjust, i));
4076         }
4077
4078       emit_call_insn (gen_call_internal1 (operands[0], operands[1],
4079                                           gen_rtx (REG, Pmode, GP_REG_FIRST + 31)));
4080       DONE;
4081     }
4082 }")
4083
4084 (define_insn "call_internal1"
4085   [(call (match_operand 0 "call_insn_operand" "m")
4086          (match_operand 1 "" "i"))
4087    (clobber (match_operand:SI 2 "register_operand" "=d"))]
4088   "!TARGET_LONG_CALLS"
4089   "*
4090 {
4091   register rtx target = XEXP (operands[0], 0);
4092
4093   if (GET_CODE (target) == SYMBOL_REF)
4094     return \"%*jal\\t%0\";
4095
4096   else if (GET_CODE (target) == CONST_INT)
4097     {
4098       operands[0] = target;
4099       return \"%*%[li\\t%@,%0\\n\\tjal\\t%2,%@%]\";
4100     }
4101
4102   else
4103     {
4104       operands[0] = target;
4105       return \"%*jal\\t%2,%0\";
4106     }
4107 }"
4108   [(set_attr "type"     "call")
4109    (set_attr "mode"     "none")
4110    (set_attr "length"   "1")])
4111
4112 (define_insn "call_internal2"
4113   [(call (mem:SI (match_operand:SI 0 "register_operand" "r"))
4114          (match_operand 1 "" "i"))
4115    (clobber (match_operand:SI 2 "register_operand" "=d"))]
4116   "TARGET_LONG_CALLS"
4117   "%*jal\\t%2,%0"
4118   [(set_attr "type"     "call")
4119    (set_attr "mode"     "none")
4120    (set_attr "length"   "1")])
4121
4122
4123 ;; calls.c now passes a fourth argument, make saber happy
4124
4125 (define_expand "call_value"
4126   [(parallel [(set (match_operand 0 "register_operand" "=df")
4127                    (call (match_operand 1 "memory_operand" "m")
4128                          (match_operand 2 "" "i")))
4129               (clobber (reg:SI 31))
4130               (use (match_operand 3 "" ""))])]          ;; next_arg_reg
4131   ""
4132   "
4133 {
4134   rtx addr;
4135
4136   if (operands[0])              /* eliminate unused code warning */
4137     {
4138       addr = XEXP (operands[1], 0);
4139       if ((GET_CODE (addr) != REG && (!CONSTANT_ADDRESS_P (addr) || TARGET_LONG_CALLS))
4140           || ! call_insn_operand (operands[1], VOIDmode))
4141         XEXP (operands[1], 0) = copy_to_mode_reg (Pmode, addr);
4142
4143       /* In order to pass small structures by value in registers
4144          compatibly with the MIPS compiler, we need to shift the value
4145          into the high part of the register.  Function_arg has encoded
4146          a PARALLEL rtx, holding a vector of adjustments to be made
4147          as the next_arg_reg variable, so we split up the insns,
4148          and emit them separately.  */
4149
4150       if (operands[3] != (rtx)0 && GET_CODE (operands[3]) == PARALLEL)
4151         {
4152           rtvec adjust = XVEC (operands[3], 0);
4153           int num = GET_NUM_ELEM (adjust);
4154           int i;
4155
4156           for (i = 0; i < num; i++)
4157             emit_insn (RTVEC_ELT (adjust, i));
4158         }
4159
4160       emit_call_insn (gen_call_value_internal1 (operands[0], operands[1], operands[2],
4161                                                 gen_rtx (REG, Pmode, GP_REG_FIRST + 31)));
4162
4163       DONE;
4164     }
4165
4166 }")
4167
4168 (define_insn "call_value_internal1"
4169   [(set (match_operand 0 "register_operand" "=df")
4170         (call (match_operand 1 "call_insn_operand" "m")
4171               (match_operand 2 "" "i")))
4172    (clobber (match_operand:SI 3 "register_operand" "=d"))]
4173   "!TARGET_LONG_CALLS"
4174   "*
4175 {
4176   register rtx target = XEXP (operands[1], 0);
4177
4178   if (GET_CODE (target) == SYMBOL_REF)
4179     return \"%*jal\\t%1\";
4180
4181   else if (GET_CODE (target) == CONST_INT)
4182     {
4183       operands[1] = target;
4184       return \"%*%[li\\t%@,%1\\n\\tjal\\t%3,%@%]\";
4185     }
4186
4187   else
4188     {
4189       operands[1] = target;
4190       return \"%*jal\\t%3,%1\";
4191     }
4192 }"
4193   [(set_attr "type"     "call")
4194    (set_attr "mode"     "none")
4195    (set_attr "length"   "1")])
4196
4197 (define_insn "call_value_internal2"
4198   [(set (match_operand 0 "register_operand" "=df")
4199         (call (mem:SI (match_operand:SI 1 "register_operand" "r"))
4200               (match_operand 2 "" "i")))
4201    (clobber (match_operand:SI 3 "register_operand" "=d"))]
4202   "TARGET_LONG_CALLS"
4203   "%*jal\\t%3,%1"
4204   [(set_attr "type"     "call")
4205    (set_attr "mode"     "none")
4206    (set_attr "length"   "1")])
4207
4208 ;; Call subroutine returning any type.
4209
4210 (define_expand "untyped_call"
4211   [(parallel [(call (match_operand 0 "" "")
4212                     (const_int 0))
4213               (match_operand 1 "" "")
4214               (match_operand 2 "" "")])]
4215   ""
4216   "
4217 {
4218   if (operands[0])              /* silence statement not reached warnings */
4219     {
4220       int i;
4221
4222       emit_call_insn (gen_call (operands[0], const0_rtx, NULL, const0_rtx));
4223
4224       for (i = 0; i < XVECLEN (operands[2], 0); i++)
4225         {
4226           rtx set = XVECEXP (operands[2], 0, i);
4227           emit_move_insn (SET_DEST (set), SET_SRC (set));
4228         }
4229
4230       emit_insn (gen_blockage ());
4231       DONE;
4232     }
4233 }")
4234 \f
4235 ;;
4236 ;;  ....................
4237 ;;
4238 ;;      MISC.
4239 ;;
4240 ;;  ....................
4241 ;;
4242
4243 (define_insn "nop"
4244   [(const_int 0)]
4245   ""
4246   "%(nop%)"
4247   [(set_attr "type"     "nop")
4248    (set_attr "mode"     "none")
4249    (set_attr "length"   "1")])
4250
4251 (define_expand "probe"
4252   [(set (match_dup 0)
4253         (match_dup 1))]
4254   ""
4255   "
4256 {
4257   operands[0] = gen_reg_rtx (SImode);
4258   operands[1] = gen_rtx (MEM, SImode, stack_pointer_rtx);
4259   MEM_VOLATILE_P (operands[1]) = TRUE;
4260
4261   /* fall through and generate default code */
4262 }")